websocket直接绕过JS加密示例及思路原理

目录
  • websocket--hook
  • 服务端--WebSocketServer.js
  • 客户端注入JS代码
  • python开端口
  • get_data.py 文件方式
  • get_user_id.py 文件方式
  • get_data.py 终端方式
  • get_user_id.py 终端方式
  • 爬虫调用者

websocket--hook

大致思路

原理:

浏览器(客户端):在浏览器中注入一段JS代码,与服务端建立连接。调用浏览器中的js方法,把返回的数据发送给服务端

node启动js代码,监听某端口(客户端):服务端把参数(python发过来的)发送给客户端处理,并接收处理结果,再次把接收的结果返回给python处理

python(调用者):把参数发送给node,接收node传回来的数据

优点:

1.对于js混淆加密较深的,可以采用此方法。

2.不用扣js加密代码,直接调用浏览器环境

缺点:
1.如果有selenium监测,要想使用此方法,必须先绕过selenium监测,否则只能使用真机进行js注入

2.需要node环境,写一个websocket服务端和客户端

3.速度没有直接破解js快

服务端--WebSocketServer.js

let iconv = require('iconv-lite')
var ws = require("nodejs-websocket");
console.log("开始建立连接...")
var server = ws.createServer(function(conn){
      let cached = {};
    conn.on("text", function (msg) {
        if (!msg) return;
        // console.log("msg", msg);
        var key = conn.key;
        if ((msg === "Browser") || (msg === "Python")){
            // browser或者python第一次连接
            cached[msg] = key;
            // console.log("cached",cached);
            return;
        }
        if (Object.values(cached).includes(key)){
            // console.log(server.connections.forEach(conn=>conn.key));
            var targetConn = server.connections.filter(function(conn){
                return conn.key !== key;
            })
            // console.log("将要发送的实参:",msg);
            targetConn.forEach(conn=>{
                conn.send(msg);
            })
        }
    })
    conn.on("close", function (code, reason) {
        // console.log("关闭连接")
    });
    conn.on("error", function (code, reason) {
        console.log("异常关闭")
    });
    conn.on("connection", function (conn) {
        console.log(conn)
    });
}).listen(10512)
console.log("WebSocket建立完毕")

客户端注入JS代码

createSocket();
function createSocket() {
    window.ws = new WebSocket('ws://127.0.0.1:10512/');
    window.ws.onopen = function (e) {
        console.log("连接服务器成功");
        window.ws.send("Browser");
    }
    window.ws.onclose = function (e) {
        console.log("服务器关闭");
        setTimeout(createSocket, 60000);
    }
    window.ws.onerror = function () {
        console.log("连接出错");
    }
    window.ws.onmessage = function (e) {
        var xmlhttp = new glb.XMLHttpRequest();
        function state_Change() {
            if (xmlhttp.readyState == 4) {
                if (xmlhttp.status == 200) {

                    let result = xmlhttp.responseText
                    result = JSON.parse(result)
                    result = JSON.stringify(result)
                    // result = String.fromCharCode(result)
                    //发送给Python
                    // console.log(result);
                    window.ws.send(result);
                } else {
                    alert("Problem retrieving XML data");
                }
            }
        }
        xmlhttp.onreadystatechange = state_Change;
        xmlhttp.open('GET', e.data, true);
        xmlhttp.send(null);
    }
}

python开端口

# -*- coding: utf-8 -*-
from sanic import Sanic
from sanic.response import json
import os
import urllib3
from toutiao2_文件方式.get_data import get_data
from toutiao2_文件方式.get_user_id import get_user
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
app = Sanic(__name__)
@app.route("/get_user_id", methods=["GET"])
def captcha_server(request):
    try:
        data = request.args
        media_id = data['media_id'][0]
        return get_user_id(media_id)
    except Exception as e:
        pass
@app.route("/get_data", methods=["GET"])
def captcha_server(request):
    try:
        data = request.args
        user_id = data['user_id'][0]
        offset = data['offset'][0]
        return get_res(user_id, offset)
    except Exception as e:
        pass
def get_user_id(media_id):
    html = get_user(media_id)
    return html
def get_res(user_id, offset):
    html = get_data(user_id,offset)
    return html
if __name__ == "__main__":
    app.run(host="127.0.0.1", port=4007)

get_data.py 文件方式

# -*- coding: utf-8 -*-
import time
from ws4py.client.threadedclient import WebSocketClient
import _locale
_locale._getdefaultlocale = (lambda *args: ['zh_CN', 'utf8'])
import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
class CG_Client(WebSocketClient):
    def opened(self):
        self.max_cursor = 0
        self.send("Python")
    def closed(self, code, reason=None):
        # print("Closed down:", code, reason)
        pass
    def received_message(self, resp):
        data = resp.data.decode("utf-8")
        write_data(data)
        ws.close()
def write_data(data):
    with open('./data.txt', 'w', encoding='utf-8') as f:
        f.write(data)
        f.close()
def get_data(user_id, offset):
    ws = CG_Client('ws://127.0.0.1:10512/')
    ws.connect()
    try:
        real_arg = f"/api/feed_backflow/profile_share/v1/?category=profile_article&visited_uid={user_id}&stream_api_version=82&request_source=1&offset={offset}&user_id={user_id}&appId=1286&appType=mobile_detail_web&isAndroid=true&isIOS=false&isMobile=true&cookie_enabled=true&screen_width=288&screen_height=511&browser_language=zh-CN&browser_platform=MacIntel&browser_name=firefox&browser_version=85.0.4183.83&browser_online=true&timezone_name=Asia%2FShanghai"
        time.sleep(0.1)
        ws.send(real_arg)
        ws.run_forever()
    except KeyboardInterrupt:
        print('异常关闭')
        ws.close()

get_user_id.py 文件方式

# -*- coding: utf-8 -*-
import time
from ws4py.client.threadedclient import WebSocketClient
import _locale
_locale._getdefaultlocale = (lambda *args: ['zh_CN', 'utf8'])
import io
import sys
import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
# sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding='utf8')
# media_id = sys.argv[1].split(',', 1)[0]   # sys.argv--> [get_attention.py,user_id,cursor]
class CG_Client(WebSocketClient):
    def opened(self):
        self.max_cursor = 0
        self.send("Python")
    def closed(self, code, reason=None):
        # print("Closed down:", code, reason)
        pass
    def received_message(self, resp):
        data = resp.data.decode("utf-8")
        write_user(data)
        ws.close()
def write_user(data):
    with open('./user.txt', 'w', encoding='utf-8') as f:
        f.write(data)
        f.close()
def get_user(media_id):
    ws = CG_Client('ws://127.0.0.1:10512/')
    ws.connect()
    try:
        real_arg = f"/user/profile/homepage/share/v7/?media_id={media_id}&request_source=1&appId=1286&appType=mobile_detail_web&isAndroid=true&isIOS=false&isMobile=true&cookie_enabled=true&screen_width=393&screen_height=882&browser_language=zh-CN&browser_platform=MacIntel&browser_name=Chrome&browser_version=85.0.4183.83&browser_online=true&timezone_name=Asia%2FShanghai"
        time.sleep(0.1)
        ws.send(real_arg)
        ws.run_forever()
    except KeyboardInterrupt:
        print('异常关闭')
        ws.close()

get_data.py 终端方式

# -*- coding: utf-8 -*-
import time
from ws4py.client.threadedclient import WebSocketClient
import _locale
_locale._getdefaultlocale = (lambda *args: ['zh_CN', 'utf8'])
import io
import sys
import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding='utf8')
user_id = sys.argv[1].split(',', 1)[0]   # sys.argv--> [get_attention.py,user_id,cursor]
offset = str(sys.argv[2])
class CG_Client(WebSocketClient):
    def opened(self):
        print("连接成功")
        self.max_cursor = 0
        self.send("Python")
    def closed(self, code, reason=None):
        print("Closed down:", code, reason)
    def received_message(self, resp):
        data = resp.data.decode("utf-8")
        print(data)
        ws.close()
try:
    ws = CG_Client('ws://127.0.0.1:10512/')
    ws.connect()
    real_arg = f"/api/feed_backflow/profile_share/v1/?category=profile_article&visited_uid={user_id}&stream_api_version=82&request_source=1&offset={offset}&user_id={user_id}&appId=1286&appType=mobile_detail_web&isAndroid=true&isIOS=false&isMobile=true&cookie_enabled=true&screen_width=288&screen_height=511&browser_language=zh-CN&browser_platform=MacIntel&browser_name=firefox&browser_version=85.0.4183.83&browser_online=true&timezone_name=Asia%2FShanghai"
    time.sleep(0.1)
    ws.send(real_arg)
    ws.run_forever()
except KeyboardInterrupt:
    ws.close()

get_user_id.py 终端方式

# -*- coding: utf-8 -*-
import time
from ws4py.client.threadedclient import WebSocketClient
import _locale
_locale._getdefaultlocale = (lambda *args: ['zh_CN', 'utf8'])
import io
import sys
import urllib3
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding='utf8')
media_id = sys.argv[1].split(',', 1)[0]   # sys.argv--> [get_attention.py,user_id,cursor]
class CG_Client(WebSocketClient):
    def opened(self):
        print("连接成功")
        self.max_cursor = 0
        self.send("Python")
    def closed(self, code, reason=None):
        print("Closed down:", code, reason)
    def received_message(self, resp):
        data = resp.data.decode("utf-8")
        # data = resp.data.decode("gbk")
        print(data)
        ws.close()
try:
    ws = CG_Client('ws://127.0.0.1:10512/')
    ws.connect()
    real_arg = f"/user/profile/homepage/share/v7/?media_id={media_id}&request_source=1&appId=1286&appType=mobile_detail_web&isAndroid=true&isIOS=false&isMobile=true&cookie_enabled=true&screen_width=393&screen_height=882&browser_language=zh-CN&browser_platform=MacIntel&browser_name=Chrome&browser_version=85.0.4183.83&browser_online=true&timezone_name=Asia%2FShanghai"
    time.sleep(0.1)
    ws.send(real_arg)
    ws.run_forever()
except KeyboardInterrupt:
    ws.close()

爬虫调用者

import time
import requests
import json
import urllib3
from toutiao2_文件方式.get_user_id import get_user, CG_Client
urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
def open_user():
    with open('./user.txt', 'r', encoding='utf-8') as f:
        user = json.loads(f.read())
        f.close()
        return user
def open_data():
    with open('./data.txt', 'r', encoding='utf-8') as f:
        data = json.loads(f.read())
        f.close()
        return data
# media_id换user_id
def start_ocean_toutiao_user_id(media_id):
    data = {
        'media_id': media_id,
    }
    requests.get('http://127.0.0.1:4007/get_user_id', params=data, timeout=3)
    time.sleep(2)
    response = open_user()
    res_media_id = response.get('data').get('media_id')
    if int(res_media_id) == int(media_id):
        user_id = response.get('data').get('user_id')
        return user_id
    else:
        print('media不对应,请检查')
        return None
# 通过websocket获取数据
def start_ocean_toutiao_data(user_id, offset):
    if user_id == None:
        print('没有获取到user_id,请检查原因。可能消息堆积错误')
        return None
    data = {
        'user_id': user_id,
        'offset': offset
    }
    requests.get('http://127.0.0.1:4007/get_data', params=data, timeout=3)
    response = open_data()
    return response
def get_response(media_id,offset):
    user_id = start_ocean_toutiao_user_id(media_id)
    print(user_id)
    data = start_ocean_toutiao_data(user_id, offset)
    print(data)
    return data
if __name__ == '__main__':
    for i in range(1):
        offset = 1587744000
        # media_id = 6860767764
        media_id = 6989633739
        user_id = start_ocean_toutiao_user_id(media_id)
        print(user_id)
        # user_id = 6860406890
        data = start_ocean_toutiao_data(user_id, offset)
        print(data)
        get_response(media_id, offset)
    pass

以上就是websocket直接绕过JS加密示例及思路原理的详细内容,更多关于websocket绕过JS加密思路的资料请关注我们其它相关文章!

(0)

相关推荐

  • JavaScript之WebSocket技术详解

    概述 HTTP协议是一种无状态协议,服务器端本身不具有识别客户端的能力,必须借助外部机制,比如session和cookie,才能与特定客户端保持对话.这多多少少带来一些不便,尤其在服务器端与客户端需要持续交换数据的场合(比如网络聊天),更是如此.为了解决这个问题,HTML5提出了浏览器的WebSocket API. WebSocket的主要作用是,允许服务器端与客户端进行全双工(full-duplex)的通信.举例来说,HTTP协议有点像发电子邮件,发出后必须等待对方回信:WebSocket则是

  • javascript实现blob加密视频源地址的方法

     一.HTML代码: <video id="my-video" class="video-js" playsinline controls preload="auto" controlslist="nodownload" controlslist="nofullscreen" width="100%" height="240" poster="uplo

  • Js参数RSA加密传输之jsencrypt.js的使用

    注意几点: 1.参数传递的+号处理,在传输时会把+变成空格,不处理后端就报错了. 1.前端代码 <!DOCTYPE html> <html> <head> <meta name="viewport" content="width=device-width" /> <title>Login</title> <script src="~/Scripts/jquery-1.10.2.m

  • JS如何实现基于websocket的多端桥接平台

    1. 要调试什么 我们主要要知道调试什么,最终回去到什么样子的结果: 1.调试接口,传入接口地址,即可获取对应的结果:并且可以同时调试多个设备: 2.调试 jsapi,输入对应的方法,则即可在新闻客户端中展示出效果. 在调试接口方面,其实我们有一种方法可以方便地进行调试,但有两个限制条件:Android系统和测试版的客户端,这样通过 Chrome 浏览器进行桥接.但这种方式,在 iOS 系统和正式版的客户端中,就失效了. 2. websocket 的特性 WebSocket 协议的最大特点就是,

  • JS实现websocket长轮询实时消息提示的效果

    效果图如下: 参考代码如下: jsp代码: <%@ page contentType="text/html;charset=UTF-8" language="java"%> <div class="page-header navbar navbar-fixed-top"> <div class="page-header-inner"> <div class="page-log

  • websocket直接绕过JS加密示例及思路原理

    目录 websocket--hook 服务端--WebSocketServer.js 客户端注入JS代码 python开端口 get_data.py 文件方式 get_user_id.py 文件方式 get_data.py 终端方式 get_user_id.py 终端方式 爬虫调用者 websocket--hook 大致思路 原理: 浏览器(客户端):在浏览器中注入一段JS代码,与服务端建立连接.调用浏览器中的js方法,把返回的数据发送给服务端 node启动js代码,监听某端口(客户端):服务端

  • JS加密插件CryptoJS实现AES加密操作示例

    本文实例讲述了JS加密插件CryptoJS实现AES加密操作.分享给大家供大家参考,具体如下: 最近在做一个项目,考虑到数据的安全性,我们要给数据在传输过程中加密,防止一些恶意的操作以及爬虫抓取数据. 用到的库:CryptoJS 官方地址:https://code.google.com/archive/p/crypto-js/ 首先看看这个CryptoJS的目录结构 主要是两个文件夹,components和rollups 第一个是组件,第二个是汇总. 在汇总文件夹中的文件是在组件一个或多个文件夹

  • JS加密插件CryptoJS实现的Base64加密示例

    本文实例讲述了JS加密插件CryptoJS实现的Base64加密.分享给大家供大家参考,具体如下: 前面一篇<JS加密插件CryptoJS实现的DES加密>介绍了CryptoJS插件进行DES加密操作的方法,这里再来介绍一下CryptoJS进行base64加密的方法: <!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title>

  • JS加密插件CryptoJS实现的DES加密示例

    本文实例讲述了JS加密插件CryptoJS实现的DES加密.分享给大家供大家参考,具体如下: 前面一篇<JS加密插件CryptoJS实现AES加密操作>介绍了CryptoJS插件的简单配置与使用,这里再来看看CryptoJS实现DES加密的方法: <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta http-equiv="Content-Type

  • NodeJS实现客户端js加密

    思路: 服务端渲染业务代码js => 前后端约定加密算法 => 业务代码进行签名 => 客户端解密业务代码 => eval 执行 Node 路由示例: /** * 请自定义 restful API 这里以 GET 为例 * @param {req} * @param {res} * @return {next()} */ //var util = require('utility'); exports.encryption = function(req, res){ //GET v

  • JAVA 中解密RSA算法JS加密实例详解

    JAVA 中解密RSA算法JS加密实例详解 有这样一个需求,前端登录的用户名密码,密码必需加密,但不可使用MD5,因为后台要检测密码的复杂度,那么在保证安全的前提下将密码传到后台呢,答案就是使用RSA非对称加密算法解决 . java代码 需要依赖 commons-codec 包 RSACoder.Java import org.apache.commons.codec.binary.Base64; import javax.crypto.Cipher; import java.security.

  • 基于JS实现无缝滚动思路及代码分享

    原理: 1.给ul一个绝对定位使其脱离文档流,left设置为0,把图片塞进ul里,编写一个"移动"函数,函数功能能够使ul的left以一个正速度向右跑动, 2.设置一个定时器,让"移动"函数每30(参数可变)毫秒执行一次 3.因为ul的长度会"跑"完,此时可以使ul的content也就是img增加一倍, oUl.innerHTML +=oUl.innerHTML; 4.此时因为ul的content增加,其width也会随着增大,根据实际项目展示图

  • Cython编译python为so 代码加密示例

    1. 编译出来的so比网上流传的其他方法小很多. 2. language_level  是python的主版本号,如果python版本是2.x,目前的版本Cython需要人工指定language_level. 3. python setup.py build_ext --inplace  执行脚本 4. 以下是代码片段 from distutils.core import Extension, setup from Cython.Build import cythonize from Cytho

  • SpringBoot+Netty+WebSocket实现消息发送的示例代码

    一.导入Netty依赖 <dependency> <groupId>io.netty</groupId> <artifactId>netty-all</artifactId> <version>4.1.25.Final</version> </dependency> 二.搭建websocket服务器 @Component public class WebSocketServer { /** * 主线程池 */

  • Python爬虫如何破解JS加密的Cookie

    通过Fiddler抓包比较,基本可以确定是JavaScript生成加密Cookie导致原来的请求返回521. 发现问题: 打开Fiddler软件,用浏览器打开目标站点(http://www.kuaidaili.com/proxylist/2/) .可以发现浏览器对这个页面加载了两次,第一次返回521,第二次才正常返回数据.很多没有写过网站或是爬虫经验不足的童鞋,可能就会觉得奇怪为什么会这样?为什么浏览器可能正常返回数据而代码却不行? 仔细观察两次返回的结果可以发现: 1.第二次请求比第一次请求的

随机推荐