네이버 로그인에 bvsd 값이 생기면서 이 값이 없으면 캡처 코드를 넣어야 합니다.
bvsd 값을 한번 알아볼까 합니다.
우선 아래 이미지에서 "bvsd.1.3.4.min.js" 파일이 되겠습니다.
이 파일을 다운로드해야 하는데 다운로드해서 소스를 보니 한 줄로 쭉 써재껴서 보기가 영 안 좋습니다.
크롬에서 아래처럼 로그인 페이지를 접속 후 F12를 눌러 네트워크에서 해당 js 파일을 선택한 후 Preview 탭에서 소스를 복사한 후 텍스트 문서에 넣고 "bvsd.1.3.4.min.js"로 저장해줍니다.
"bvsd.1.3.4.min.js" 파일을 열어서 post 값에 "endData"가 있으니 "endData"를 찾아봅니다.
"endData: r" 이 보입니다.
r을 찾아보니 아래 사진처럼 "r = i["default"].compressToEncodedURIComponent(o)"라는 줄이 보이네요...
그럼 o 변수가 원래 텍스트겠군요...
"endData: r"을 "endData: o"로 바꾸어 줍니다.
다음으로 autoset을 설치 후 루트에 nhn 폴더를 만든 후 위에서 언급한 bvsd.1.3.4.min.js 파일을 포함하여 빨간색으로 표시된 파일을 모두 다운로드합니다.
index.php 파일에는 아래처럼 네이버 로그인 페이지 소스를 넣고 일부 수정을 합니다.
스크립트도 추가해서 넣었습니다.
<?php
$toDay=date("Y-m-d");
$view=1;
?>
<!DOCTYPE html>
<html>
<head>
<title>로그인 테스트</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css">
<!--script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script-->
<!--script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js"></script-->
<link rel="stylesheet" type="text/css" href="w_20181115.css">
<!--script type="text/javascript" src="keys_js3.nhn"></script-->
<script>
var today = '<?php echo $toDay;?>';
function MeSubmit(){ // bvsd 값을 확인하기 위한 스크립트
sessionkey = 'w2okbyh3xiDIZYD1';
keyname = '100013842';
evalue = '8642e5a832c39ec285c97223288cd2ed4cce9fa1753af2f410e19bad8b644665c953e2b967d2ba5d560e4cbc7bfb9d17d666657022fbc55a485364757d889fb75c031c34081762c271d7abe64d4026139617927ae363226700bf78e53a64ffdbac55878cf425a4acd69adb0e0a245020a5dcb958f12df776487f5900f4e2fc13';
nvalue = '010001';
$('encnm').value = '100013842';
if (!sessionkey || !keyname || !evalue || !nvalue) {
//if (true) {
if ($('enctp').value == 3) {
showErrorDiv2(4);
} else {
showErrorDiv(4);
}
} else {
var rsa = new RSAKey();
rsa.setPublic(evalue, nvalue);
$('encpw').value = rsa.encrypt(getLenChar(sessionkey) + sessionkey
+ getLenChar($('id').value) + $('id').value
+ getLenChar($('pw').value) + $('pw').value);
setTimeout(function() {
//$("id").value = "";
//$("pw").value = "";
//$("bvsd").value = "timeout";
//$('frmNIDLogin').submit();
}, 5000);
bvsd.f(function(a) {
//$("id").value = "";
//$("pw").value = "";
$("bvsd").value = a;
document.getElementById("strbvsd").innerHTML = a;
//$('frmNIDLogin').submit();
});
}
}
</script>
</head>
<body>
<input onclick="MeSubmit()" value="bvsd 확인하기">
<form id="frmNIDLogin" name="frmNIDLogin" target="_top" AUTOCOMPLETE="off" action="nidlogin.php" method="post" onsubmit="return confirmSplitSubmit();">
<br>bvsd:<input name="bvsd" id="bvsd" value="">
<p name="strbvsd" id="strbvsd"></p>
<br>enctp:<input name="enctp" id="enctp" value="2">
<br>encpw:<input name="encpw" id="encpw" value="">
<br>encnm:<input name="encnm" id="encnm" value="">
<br>svctype:<input name="svctype" id="svctype" value="0">
<br>svc:<input name="svc" id="svc" value="">
<br>viewtype:<input name="viewtype" id="viewtype" value="0">
<br>locale:<input name="locale" id="locale" value="ko_KR">
<br>postDataKey:<input name="postDataKey" id="postDataKey" value="">
<br>smart_LEVEL:<input name="smart_LEVEL" id="smart_LEVEL" value="-1">
<br>logintp:<input name="logintp" id="logintp" value="">
<br>url:<input name="url" id="url" value="http://www.naver.com">
<br>localechange:<input name="localechange" id="localechange" value="">
<br>ls:<input name="ls" id="ls" value="">
<br>xid:<input name="xid" id="xid" value="">
<br>pre_id:<input name="pre_id" id="pre_id" value="">
<br>resp:<input name="resp" id="resp" value="">
<br>ru:<input name="ru" id="ru" value="">
<fieldset class="login_form">
<legend class="blind">로그인</legend>
<div class="id_area">
<div class="error_id" id="err_empty_id" style="display:none" tabindex="0">아이디를 입력해주세요.</div>
<div class="input_row" id="id_area">
<span class="input_box">
<label for="id" id="label_id_area" class="lbl" >아이디</label>
<input type="text" id="id" name="id" accesskey="L" placeholder="아이디" class="int" maxlength="41" value="">
</span>
<button type="button" disabled="" title="delete" id="id_clear" class="wrg">삭제</button>
</div>
</div>
<div class="pw_area">
<div class="error_pw" id="err_empty_pw" style="display:none" tabindex="0">비밀번호를 입력해주세요.</div>
<div class="input_row" id="pw_area">
<span class="input_box">
<label for="pw" id="label_pw_area" class="lbl">비밀번호</label>
<input type="password" id="pw" name="pw" placeholder="비밀번호" class="int" maxlength="16" onkeypress="MeSubmit();capslockevt(event);getKeysv2();" onkeyup="MeSubmit();checkShiftUp(event);" onkeydown="MeSubmit();checkShiftDown(event);" aria-describedby="err_common">
</span>
<button type="button" disabled="" title="delete" id="pw_clear" class="wrg">삭제</button>
<div class="ly_v2" id="err_capslock" style="display:none;">
<div class="ly_box">
<p role="alert"><strong>Caps Lock</strong>이 켜져 있습니다.</p> </div>
<span class="sp ly_point"></span>
</div>
</div>
</div>
<input type="submit" title="로그인" alt="로그인" value="로그인" class="btn_global" onclick="nclks('log.login',this,event)">
<!--input type="submit" title="로그인" alt="로그인" value="로그인" class="btn_global" onclick="mesubmit()"-->
<div class="check_info" >
<div class="login_check">
<span class="login_check_box">
<input type="checkbox" id="login_chk" name="nvlong" class="" value="off" onchange="savedLong(this);nclks_chk('login_chk', 'log.keepon', 'log.keepoff',this,event)" />
<label for="login_chk" id="label_login_chk" class="sp">로그인 상태 유지</label>
</span>
<div class="ly_v2" id="persist_usage" role="alert" style="display:none;">
<div class="ly_box">
<p>개인정보 보호를 위해 <strong>개인 PC에서만 사용하세요.</strong> <a href="https://help.naver.com/support/contents/contents.nhn?serviceNo=532&categoryNo=1523" target="_blank" class="sp btn_check_help">도움말보기</a></p>
</div>
<span class="sp ly_point"></span>
</div>
</div>
<div class="pc_check">
<span class="ip_check">
<a href="/login/ext/help_ip3.html" target="_blank" onclick="window.open(this.href, 'IPGUIDE', 'titlebar=1, resizable=1, scrollbars=yes, width=537, height=750'); return false;" title="" >IP보안</a>
<span class="ip_ch">
<input type="checkbox" id="ip_on" checked="checked" onchange="ipCheck(this,event);nclks_chk('ip_on', 'log.iponset', 'log.ipoffset',this,event)" class=""/>
<label for="ip_on" id="label_ip_on" class="sp"><span class="blind">on</span></label>
</span>
</span>
<span class="bar">|</span>
<div class="dis_di">
<a href="#" onclick="onetime(); nclks('log.otn',this,event); return false;" title="일회용 로그인">일회용 로그인</a><a href="javascript:viewOnetime();" onclick="nclks('log.otnhelp',this,event)" title="도움말" class="btn_help_cover"><span class="sp btn_help"></span><span class="blind">도움말</span></a>
<div class="ly" id="onetime_usage" style="display:none;" onclick="javascript:viewOnetime()">
<div class="ly_box">
<p>네이버앱에서 생성된 일회용 로그인 번호를 입력하면, 앱에 로그인된 계정으로 PC에서 로그인할 수 있어요. 아이디/비밀번호를 입력하지 않아 간편하고 더욱 안전합니다.</p> </div>
<span class="sp ly_point"></span>
</div>
</div>
</div>
</div>
</fieldset>
</form>
<script type="text/javascript" src="common.all.js"></script>
<script type="text/javascript">
var disp_stat = "20";
var session_keys = "";
var pc_keyboard_close="<span class=\"sp\">PC 키보드 닫기</span>";
var pc_keyboard_open="<span class=\"sp\">PC 키보드 보기</span>";
var view_char="한글 보기";
var view_symbol="특수기호 보기";
addInputEvent('id', 'id_area');
addInputEvent('pw', 'pw_area');
function showAlarmDiv(objname,defaultClass,addKeyword) {
$(objname).className=defaultClass + ' ' + addKeyword;
}
function hideAlarmDiv(objname,defaultClass) {
$(objname).className=defaultClass;
}
initSmartLevel();
var login_chk = $('login_chk');
if(login_chk.attachEvent) {
login_chk.attachEvent("onchange", function(){persist_usage();});
} else if (login_chk.addEventListener) {
login_chk.addEventListener("change", function(){persist_usage();}, false);
}
function persist_usage()
{
var login_chk = $("login_chk");
if (login_chk.checked==true)
{
show("persist_usage");
hide('onetime_usage');
view_onetimeusage = false;
}
else
{
hide("persist_usage");
}
}
var view_onetimeusage = false;
function viewOnetime()
{
if (view_onetimeusage)
{
hide('onetime_usage');
view_onetimeusage = false;
}
else
{
hide("persist_usage");
show('onetime_usage');
view_onetimeusage = true;
}
}
try{
if (navigator.appVersion.toLowerCase().indexOf("win") != -1) {
$('id').style.imeMode = "disabled";
document.msCapsLockWarningOff = true;
}
}catch(e) {}
try{
if ( $('id').value.length == 0 )
{
$('id').focus();
}
else
{
$('pw').focus();
}
}catch (e){}
</script>
<script type="text/javascript" src="common.util.js"></script>
<script type="text/javascript"> lcs_do();</script>
<script type="text/javascript">
var nsc = "nid.login_kr";
</script>
<script type="text/javascript" src="bvsd.1.3.4.min__.js"></script>
<script type="text/javascript">
var inSubmitProgress = false;
function confirmSplitSubmit()
{
if (inSubmitProgress) {
return false;
}
inSubmitProgress = true;
var id = $("id");
var pw = $("pw");
var encpw = $("encpw");
if(id.value == "") {
showAlarmDiv("err_empty_id","error_id","on");
hideAlarmDiv("err_empty_pw","error_pw");
show("err_empty_id");
hide("err_empty_pw");
hide("err_common");
showAlarmDiv("id_area","input_row","focus");
hideAlarmDiv("pw_area","input_row");
$("err_empty_id").focus();
inSubmitProgress = false;
return false;
} else if(pw.value == "") {
showAlarmDiv("err_empty_pw","error_pw","on");
hideAlarmDiv("err_empty_id","error_id");
show("err_empty_pw");
hide("err_empty_id");
hide("err_common");
showAlarmDiv("pw_area","input_row","focus");
hideAlarmDiv("id_area","input_row");
$("err_empty_pw").focus();
inSubmitProgress = false;
return false;
}
try{
$("ls").value = localStorage.getItem("nid_t");
}catch(e){}
return encryptIdPwSplit();
}
function encryptIdPwSplit() {
var id = $("id");
var pw = $("pw");
var encpw = $("encpw");
var rsa = new RSAKey;
if (keySplit(session_keys)) {
rsa.setPublic(evalue, nvalue);
try{
encpw.value = rsa.encrypt(
getLenChar(sessionkey) + sessionkey +
getLenChar(id.value) + id.value +
getLenChar(pw.value) + pw.value);
} catch(e) {
inSubmitProgress = false;
return false;
}
$('enctp').value = 1;
setTimeout(function() {
$("id").value = "";
$("pw").value = "";
$("bvsd").value = "timeout";
$('frmNIDLogin').submit();
}, 5000);
try {
if (bvsd){
bvsd.f(function(a) {
$("id").value = "";
$("pw").value = "";
$("bvsd").value = a;
$('frmNIDLogin').submit();
});
}
} catch (e) {
$("id").value = "";
$("pw").value = "";
$("bvsd").value = "error1|"+e.name+"|"+e.message;
$('frmNIDLogin').submit();
}
}
else
{
getKeyByRuntimeIncludeSplit();
}
inSubmitProgress = false;
return false;
}
function getKeyByRuntimeIncludeSplit() {
try {
var keyjs = document.createElement('script');
keyjs.type = 'text/javascript';
keyjs.src = '/login/ext/keys_js3.nhn';
document.getElementsByTagName('head')[0].appendChild(keyjs);
} catch (e) {
}
}
</script>
<script type="text/javascript">
var porperties = {
keyboard: [{
id: "id"
}, {
id: "pw",
secureMode: true
}],
modeProperties: {
mode: 4
}
};
bvsd = new sofa.Koop(porperties);
MeSubmit(); // 페이지 로딩시 bvsd 값을 뿌려줌
</script>
<div id="nv_stat" style="display:none;">20</div>
</body>
</html>
아래 사진처럼 encData 값이 원본 텍스트 그대로 보이네요.
이 encData중 여러번의 로그인 테스트로 필요한 값만 추려보았습니다.
{"a":"6b84006b-c8c2-420e-b00b-f49866a233a0-4","b":"1.3.4","d":[{"i":"id","b":{"a":["0,program1472"]},"d":"program1472","e":false,"f":false},{"i":"pw","e":true,"f":false}],"h":"1f","i":{"a":"Mozilla/5.0 (Windows NT 6.1; WOW64; rv:64.0) Gecko/20100101 Firefox/64.0"}}
이걸 vb 코드로 변환하면 아래처럼 bvsd 값을 만들 수 있습니다.
js 파일에서 compressToEncodedURIComponent 은 아래 링크의 compressToBase64 함수를 이용하시면 됩니다.
https://github.com/gsemac/lz-string-vb/blob/master/LZString%20VB.NET/LZString.vb
Dim bvsd_uuid As Guid = System.Guid.NewGuid()
Dim encData As String = "{""a"":""" & bvsd_uuid.ToString() & "-4"",""b"":""1.3.4"",""d"":[{""i"":""id"",""b"":{""a"":[""0," & id & """]},""d"":""" & id & """,""e"":false,""f"":false},{""i"":""pw"",""e"":true,""f"":false}],""h"":""1f"",""i"":{""a"":""Mozilla/5.0 (Windows NT 6.1; WOW64; rv:64.0) Gecko/20100101 Firefox/64.0""}}"
Dim bvsd As String = "{""uuid"":""" & bvsd_uuid.ToString() & """,""encData"":""" & LZString.compressToBase64(encData) & """}"
이제 bvsd 값이 만들어 졌습니다.
나머지 post 값은 기존 rsa 로그인에 위의 bvsd 값을 추가해서 보내주면 됩니다
'자료' 카테고리의 다른 글
다익스트라(Dijkstra)의 최단 경로 알고리즘 (0) | 2020.09.05 |
---|---|
[Python3] 기본 자료형(Built-in Types) (0) | 2020.09.05 |
[VB.NET/C#] 아프리카 TV 라이브 방송링크 받아오기 (0) | 2020.09.03 |
[VB.net/C#] 아프리카티비 여러개 시청 (0) | 2020.09.03 |
[VB.net/C#] 아프리카TV 채팅방 접속/채팅전송/채팅복호화 (1) | 2020.09.03 |