爬虫逆向实战(二十)--某99网站登录

一、数据接口分析

主页地址:某99网站

1、抓包

通过抓包可以发现登录接口是AC_userlogin
在这里插入图片描述

2、判断是否有加密参数

  1. 请求参数是否加密?
    通过查看“载荷”可以发现txtPasswordaws是加密参数
    在这里插入图片描述
  2. 请求头是否加密?
  3. 响应是否加密?
  4. cookie是否加密?

二、加密位置定位

1、看启动器

查看启动器发现有一个NDUser_Login.js文件的匿名方法,点进去查看
在这里插入图片描述
点进去后发现,此处拼接了一个登录的地址,并且上方会赋值passwordaws,大概率是在此处进行的加密。下断点,再次登录。
在这里插入图片描述发现可以断住,所以此处就是加密位置

三、扣js代码

通过定位到的加密位置,扣出加密代码,缺啥补啥即可。
aws是可以写死的,每次生成的都是一样的。

通过断点进入password的加密方法,发现是加盐的md5,通过控制台测试字符串’1’,可以看出时标准的md5
在这里插入图片描述
但是当我使用标准的md5加密加盐后的字符串时,却发现与网站加密出的密文不同
在这里插入图片描述
所以此处要将网站使用的MD5算法扣出,不能使用标准的md5

四、验证码

1、分析接口

通过不断点击图片验证码可以看出,网站每次获取验证码都会发送三个请求在这里插入图片描述
通过观察这三个请求可以发现,第二个请求会携带第一个请求返回响应中的ticket,第二个请求返回的响应中有第三个请求的地址。
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

五、登录流程

首先我们需要先请求图片验证码的第一个接口,获取到ticket,再携带ticket请求第二个接口获取到图片验证码的地址,请求该地址获取到图片,破解图片验证码(我使用的是打码平台)。生成加密参数,携带加密参数以及图片验证码请求登录接口。注意:以上请求均需要携带参数callback,写死即可。
JavaScript源码:

var CryptoJS = require('crypto-js')
var hex_chr = "0123456789abcdef";
function rhex(num) {
    str = "";
    for (j = 0; j <= 3; j++)
        str += hex_chr.charAt((num >> (j * 8 + 4)) & 0x0F) + hex_chr.charAt((num >> (j * 8)) & 0x0F);
    return str;
}
function str2blks_MD5(str) {
    nblk = ((str.length + 8) >> 6) + 1;
    blks = new Array(nblk * 16);
    for (i = 0; i < nblk * 16; i++)
        blks[i] = 0;
    for (i = 0; i < str.length; i++)
        blks[i >> 2] |= str.charCodeAt(i) << ((i % 4) * 8);
    blks[i >> 2] |= 0x80 << ((i % 4) * 8);
    blks[nblk * 16 - 2] = str.length * 8;
    return blks;
}
function add(x, y) {
    var lsw = (x & 0xFFFF) + (y & 0xFFFF);
    var msw = (x >> 16) + (y >> 16) + (lsw >> 16);
    return (msw << 16) | (lsw & 0xFFFF);
}
function rol(num, cnt) {
    return (num << cnt) | (num >>> (32 - cnt));
}
function cmn(q, a, b, x, s, t) {
    return add(rol(add(add(a, q), add(x, t)), s), b);
}
function ff(a, b, c, d, x, s, t) {
    return cmn((b & c) | ((~b) & d), a, b, x, s, t);
}
function gg(a, b, c, d, x, s, t) {
    return cmn((b & d) | (c & (~d)), a, b, x, s, t);
}
function hh(a, b, c, d, x, s, t) {
    return cmn(b ^ c ^ d, a, b, x, s, t);
}
function ii(a, b, c, d, x, s, t) {
    return cmn(c ^ (b | (~d)), a, b, x, s, t);
}

function MD5(str) {
    x = str2blks_MD5(str);
    var a = 1732584193;
    var b = -271733879;
    var c = -1732584194;
    var d = 271733878;
    for (i = 0; i < x.length; i += 16) {
        var olda = a;
        var oldb = b;
        var oldc = c;
        var oldd = d;
        a = ff(a, b, c, d, x[i + 0], 7, -680876936);
        d = ff(d, a, b, c, x[i + 1], 12, -389564586);
        c = ff(c, d, a, b, x[i + 2], 17, 606105819);
        b = ff(b, c, d, a, x[i + 3], 22, -1044525330);
        a = ff(a, b, c, d, x[i + 4], 7, -176418897);
        d = ff(d, a, b, c, x[i + 5], 12, 1200080426);
        c = ff(c, d, a, b, x[i + 6], 17, -1473231341);
        b = ff(b, c, d, a, x[i + 7], 22, -45705983);
        a = ff(a, b, c, d, x[i + 8], 7, 1770035416);
        d = ff(d, a, b, c, x[i + 9], 12, -1958414417);
        c = ff(c, d, a, b, x[i + 10], 17, -42063);
        b = ff(b, c, d, a, x[i + 11], 22, -1990404162);
        a = ff(a, b, c, d, x[i + 12], 7, 1804603682);
        d = ff(d, a, b, c, x[i + 13], 12, -40341101);
        c = ff(c, d, a, b, x[i + 14], 17, -1502002290);
        b = ff(b, c, d, a, x[i + 15], 22, 1236535329);
        a = gg(a, b, c, d, x[i + 1], 5, -165796510);
        d = gg(d, a, b, c, x[i + 6], 9, -1069501632);
        c = gg(c, d, a, b, x[i + 11], 14, 643717713);
        b = gg(b, c, d, a, x[i + 0], 20, -373897302);
        a = gg(a, b, c, d, x[i + 5], 5, -701558691);
        d = gg(d, a, b, c, x[i + 10], 9, 38016083);
        c = gg(c, d, a, b, x[i + 15], 14, -660478335);
        b = gg(b, c, d, a, x[i + 4], 20, -405537848);
        a = gg(a, b, c, d, x[i + 9], 5, 568446438);
        d = gg(d, a, b, c, x[i + 14], 9, -1019803690);
        c = gg(c, d, a, b, x[i + 3], 14, -187363961);
        b = gg(b, c, d, a, x[i + 8], 20, 1163531501);
        a = gg(a, b, c, d, x[i + 13], 5, -1444681467);
        d = gg(d, a, b, c, x[i + 2], 9, -51403784);
        c = gg(c, d, a, b, x[i + 7], 14, 1735328473);
        b = gg(b, c, d, a, x[i + 12], 20, -1926607734);
        a = hh(a, b, c, d, x[i + 5], 4, -378558);
        d = hh(d, a, b, c, x[i + 8], 11, -2022574463);
        c = hh(c, d, a, b, x[i + 11], 16, 1839030562);
        b = hh(b, c, d, a, x[i + 14], 23, -35309556);
        a = hh(a, b, c, d, x[i + 1], 4, -1530992060);
        d = hh(d, a, b, c, x[i + 4], 11, 1272893353);
        c = hh(c, d, a, b, x[i + 7], 16, -155497632);
        b = hh(b, c, d, a, x[i + 10], 23, -1094730640);
        a = hh(a, b, c, d, x[i + 13], 4, 681279174);
        d = hh(d, a, b, c, x[i + 0], 11, -358537222);
        c = hh(c, d, a, b, x[i + 3], 16, -722521979);
        b = hh(b, c, d, a, x[i + 6], 23, 76029189);
        a = hh(a, b, c, d, x[i + 9], 4, -640364487);
        d = hh(d, a, b, c, x[i + 12], 11, -421815835);
        c = hh(c, d, a, b, x[i + 15], 16, 530742520);
        b = hh(b, c, d, a, x[i + 2], 23, -995338651);
        a = ii(a, b, c, d, x[i + 0], 6, -198630844);
        d = ii(d, a, b, c, x[i + 7], 10, 1126891415);
        c = ii(c, d, a, b, x[i + 14], 15, -1416354905);
        b = ii(b, c, d, a, x[i + 5], 21, -57434055);
        a = ii(a, b, c, d, x[i + 12], 6, 1700485571);
        d = ii(d, a, b, c, x[i + 3], 10, -1894986606);
        c = ii(c, d, a, b, x[i + 10], 15, -1051523);
        b = ii(b, c, d, a, x[i + 1], 21, -2054922799);
        a = ii(a, b, c, d, x[i + 8], 6, 1873313359);
        d = ii(d, a, b, c, x[i + 15], 10, -30611744);
        c = ii(c, d, a, b, x[i + 6], 15, -1560198380);
        b = ii(b, c, d, a, x[i + 13], 21, 1309151649);
        a = ii(a, b, c, d, x[i + 4], 6, -145523070);
        d = ii(d, a, b, c, x[i + 11], 10, -1120210379);
        c = ii(c, d, a, b, x[i + 2], 15, 718787259);
        b = ii(b, c, d, a, x[i + 9], 21, -343485551);
        a = add(a, olda);
        b = add(b, oldb);
        c = add(c, oldc);
        d = add(d, oldd);
    }
    return rhex(a) + rhex(b) + rhex(c) + rhex(d);
}

function getMD5Value(data) {
    var a = data;
    var b = "\xa3\xac\xa1\xa3";
    var c = "fdjf,jkgfkl";
    var s = a + b + c;
    return MD5(s);
}

var x64Add = function(m, n) {
        m = [m[0] >>> 16, m[0] & 65535, m[1] >>> 16, m[1] & 65535];
        n = [n[0] >>> 16, n[0] & 65535, n[1] >>> 16, n[1] & 65535];
        var o = [0, 0, 0, 0];
        o[3] += m[3] + n[3];
        o[2] += o[3] >>> 16;
        o[3] &= 65535;
        o[2] += m[2] + n[2];
        o[1] += o[2] >>> 16;
        o[2] &= 65535;
        o[1] += m[1] + n[1];
        o[0] += o[1] >>> 16;
        o[1] &= 65535;
        o[0] += m[0] + n[0];
        o[0] &= 65535;
        return [(o[0] << 16) | o[1], (o[2] << 16) | o[3]]
    };
    var x64Multiply = function(m, n) {
        m = [m[0] >>> 16, m[0] & 65535, m[1] >>> 16, m[1] & 65535];
        n = [n[0] >>> 16, n[0] & 65535, n[1] >>> 16, n[1] & 65535];
        var o = [0, 0, 0, 0];
        o[3] += m[3] * n[3];
        o[2] += o[3] >>> 16;
        o[3] &= 65535;
        o[2] += m[2] * n[3];
        o[1] += o[2] >>> 16;
        o[2] &= 65535;
        o[2] += m[3] * n[2];
        o[1] += o[2] >>> 16;
        o[2] &= 65535;
        o[1] += m[1] * n[3];
        o[0] += o[1] >>> 16;
        o[1] &= 65535;
        o[1] += m[2] * n[2];
        o[0] += o[1] >>> 16;
        o[1] &= 65535;
        o[1] += m[3] * n[1];
        o[0] += o[1] >>> 16;
        o[1] &= 65535;
        o[0] += (m[0] * n[3]) + (m[1] * n[2]) + (m[2] * n[1]) + (m[3] * n[0]);
        o[0] &= 65535;
        return [(o[0] << 16) | o[1], (o[2] << 16) | o[3]]
    };
    var x64Rotl = function(m, n) {
        n %= 64;
        if (n === 32) {
            return [m[1], m[0]]
        } else {
            if (n < 32) {
                return [(m[0] << n) | (m[1] >>> (32 - n)), (m[1] << n) | (m[0] >>> (32 - n))]
            } else {
                n -= 32;
                return [(m[1] << n) | (m[0] >>> (32 - n)), (m[0] << n) | (m[1] >>> (32 - n))]
            }
        }
    };
    var x64LeftShift = function(m, n) {
        n %= 64;
        if (n === 0) {
            return m
        } else {
            if (n < 32) {
                return [(m[0] << n) | (m[1] >>> (32 - n)), m[1] << n]
            } else {
                return [m[1] << (n - 32), 0]
            }
        }
    };
    var x64Xor = function(m, n) {
        return [m[0] ^ n[0], m[1] ^ n[1]]
    };
    var x64Fmix = function(h) {
        h = x64Xor(h, [0, h[0] >>> 1]);
        h = x64Multiply(h, [4283543511, 3981806797]);
        h = x64Xor(h, [0, h[0] >>> 1]);
        h = x64Multiply(h, [3301882366, 444984403]);
        h = x64Xor(h, [0, h[0] >>> 1]);
        return h
    };

var Fingerprint2_x64hash128 = function(key, seed) {
        key = key || "";
        seed = seed || 0;
        var remainder = key.length % 16;
        var bytes = key.length - remainder;
        var h1 = [0, seed];
        var h2 = [0, seed];
        var k1 = [0, 0];
        var k2 = [0, 0];
        var c1 = [2277735313, 289559509];
        var c2 = [1291169091, 658871167];
        for (var i = 0; i < bytes; i = i + 16) {
            k1 = [((key.charCodeAt(i + 4) & 255)) | ((key.charCodeAt(i + 5) & 255) << 8) | ((key.charCodeAt(i + 6) & 255) << 16) | ((key.charCodeAt(i + 7) & 255) << 24), ((key.charCodeAt(i) & 255)) | ((key.charCodeAt(i + 1) & 255) << 8) | ((key.charCodeAt(i + 2) & 255) << 16) | ((key.charCodeAt(i + 3) & 255) << 24)];
            k2 = [((key.charCodeAt(i + 12) & 255)) | ((key.charCodeAt(i + 13) & 255) << 8) | ((key.charCodeAt(i + 14) & 255) << 16) | ((key.charCodeAt(i + 15) & 255) << 24), ((key.charCodeAt(i + 8) & 255)) | ((key.charCodeAt(i + 9) & 255) << 8) | ((key.charCodeAt(i + 10) & 255) << 16) | ((key.charCodeAt(i + 11) & 255) << 24)];
            k1 = x64Multiply(k1, c1);
            k1 = x64Rotl(k1, 31);
            k1 = x64Multiply(k1, c2);
            h1 = x64Xor(h1, k1);
            h1 = x64Rotl(h1, 27);
            h1 = x64Add(h1, h2);
            h1 = x64Add(x64Multiply(h1, [0, 5]), [0, 1390208809]);
            k2 = x64Multiply(k2, c2);
            k2 = x64Rotl(k2, 33);
            k2 = x64Multiply(k2, c1);
            h2 = x64Xor(h2, k2);
            h2 = x64Rotl(h2, 31);
            h2 = x64Add(h2, h1);
            h2 = x64Add(x64Multiply(h2, [0, 5]), [0, 944331445])
        }
        k1 = [0, 0];
        k2 = [0, 0];
        switch (remainder) {
        case 15:
            k2 = x64Xor(k2, x64LeftShift([0, key.charCodeAt(i + 14)], 48));
        case 14:
            k2 = x64Xor(k2, x64LeftShift([0, key.charCodeAt(i + 13)], 40));
        case 13:
            k2 = x64Xor(k2, x64LeftShift([0, key.charCodeAt(i + 12)], 32));
        case 12:
            k2 = x64Xor(k2, x64LeftShift([0, key.charCodeAt(i + 11)], 24));
        case 11:
            k2 = x64Xor(k2, x64LeftShift([0, key.charCodeAt(i + 10)], 16));
        case 10:
            k2 = x64Xor(k2, x64LeftShift([0, key.charCodeAt(i + 9)], 8));
        case 9:
            k2 = x64Xor(k2, [0, key.charCodeAt(i + 8)]);
            k2 = x64Multiply(k2, c2);
            k2 = x64Rotl(k2, 33);
            k2 = x64Multiply(k2, c1);
            h2 = x64Xor(h2, k2);
        case 8:
            k1 = x64Xor(k1, x64LeftShift([0, key.charCodeAt(i + 7)], 56));
        case 7:
            k1 = x64Xor(k1, x64LeftShift([0, key.charCodeAt(i + 6)], 48));
        case 6:
            k1 = x64Xor(k1, x64LeftShift([0, key.charCodeAt(i + 5)], 40));
        case 5:
            k1 = x64Xor(k1, x64LeftShift([0, key.charCodeAt(i + 4)], 32));
        case 4:
            k1 = x64Xor(k1, x64LeftShift([0, key.charCodeAt(i + 3)], 24));
        case 3:
            k1 = x64Xor(k1, x64LeftShift([0, key.charCodeAt(i + 2)], 16));
        case 2:
            k1 = x64Xor(k1, x64LeftShift([0, key.charCodeAt(i + 1)], 8));
        case 1:
            k1 = x64Xor(k1, [0, key.charCodeAt(i)]);
            k1 = x64Multiply(k1, c1);
            k1 = x64Rotl(k1, 31);
            k1 = x64Multiply(k1, c2);
            h1 = x64Xor(h1, k1)
        }
        h1 = x64Xor(h1, [0, key.length]);
        h2 = x64Xor(h2, [0, key.length]);
        h1 = x64Add(h1, h2);
        h2 = x64Add(h2, h1);
        h1 = x64Fmix(h1);
        h2 = x64Fmix(h2);
        h1 = x64Add(h1, h2);
        h2 = x64Add(h2, h1);
        return ("00000000" + (h1[0] >>> 0).toString(16)).slice(-8) + ("00000000" + (h1[1] >>> 0).toString(16)).slice(-8) + ("00000000" + (h2[0] >>> 0).toString(16)).slice(-8) + ("00000000" + (h2[1] >>> 0).toString(16)).slice(-8)
    };

function printComponents(components) {
    var values = components.map(function(component) {
        return component.value
    });
    var hash = Fingerprint2_x64hash128(values.join(''), 31);
    return hash
}

var components = [
    {
        "key": "userAgent",
        "value": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.0.0 Safari/537.36"
    },
    {
        "key": "webdriver",
        "value": false
    },
    {
        "key": "language",
        "value": "zh-CN"
    },
    {
        "key": "colorDepth",
        "value": 24
    },
    {
        "key": "deviceMemory",
        "value": 8
    },
    {
        "key": "hardwareConcurrency",
        "value": 12
    },
    {
        "key": "screenResolution",
        "value": [
            1920,
            1080
        ]
    },
    {
        "key": "availableScreenResolution",
        "value": [
            1920,
            1032
        ]
    },
    {
        "key": "timezoneOffset",
        "value": -480
    },
    {
        "key": "timezone",
        "value": "Asia/Shanghai"
    },
    {
        "key": "sessionStorage",
        "value": true
    },
    {
        "key": "localStorage",
        "value": true
    },
    {
        "key": "indexedDb",
        "value": true
    },
    {
        "key": "addBehavior",
        "value": false
    },
    {
        "key": "openDatabase",
        "value": true
    },
    {
        "key": "cpuClass",
        "value": "not available"
    },
    {
        "key": "platform",
        "value": "Win32"
    },
    {
        "key": "plugins",
        "value": [
            [
                "PDF Viewer",
                "Portable Document Format",
                [
                    [
                        "application/pdf",
                        "pdf"
                    ],
                    [
                        "text/pdf",
                        "pdf"
                    ]
                ]
            ],
            [
                "Chrome PDF Viewer",
                "Portable Document Format",
                [
                    [
                        "application/pdf",
                        "pdf"
                    ],
                    [
                        "text/pdf",
                        "pdf"
                    ]
                ]
            ],
            [
                "Chromium PDF Viewer",
                "Portable Document Format",
                [
                    [
                        "application/pdf",
                        "pdf"
                    ],
                    [
                        "text/pdf",
                        "pdf"
                    ]
                ]
            ],
            [
                "Microsoft Edge PDF Viewer",
                "Portable Document Format",
                [
                    [
                        "application/pdf",
                        "pdf"
                    ],
                    [
                        "text/pdf",
                        "pdf"
                    ]
                ]
            ],
            [
                "WebKit built-in PDF",
                "Portable Document Format",
                [
                    [
                        "application/pdf",
                        "pdf"
                    ],
                    [
                        "text/pdf",
                        "pdf"
                    ]
                ]
            ]
        ]
    },
    {
        "key": "canvas",
        "value": [
            "canvas winding:yes",
            "canvas fp:data:image/png;base64,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QGC5C5QP6PPE9Lm30o/Eis/v40Tfqzh/e2f0Tm9eEsccXTMWfafH4u7VoxFdrZV+RPOIGGpEo/W7HwIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBD4BwLLKqC3+7W9mX74x/9L7xjeESevjseZ+5uid3rLolqPrnkT/cc+xZ1L22Lm0OyvYB6NaAws6h4eRoAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQJ/FVi2Af3PT/xbUO9+3Bk9t9bG/uGuaL7dGkdnuhf0OzK26kNc2fMlVm57Frcub4+p5r2IeNiIxoMFfY5hBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQILBgAv9NQJ9P7FdUjzh4pxkXrq2Lj9ETB16uj46ZTbFrqjN+/o31v72t/i4iJuPFhq8xsvFbnH09HH3nVseT4+Px6OSkWL5g31GDCBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgsCgC/3VAXxRhDyFAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAgACBEgICeokzWZIAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIEsgUE9Gxh8wkQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQIECghICAXuJMliRAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAgACBbAEBPVvYfAIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAoISCglziTJQkQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQIEAgW0BAzxY2nwABAgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgRKCAjoJc5kSQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBDIFhDQs4XNJ0CAAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAIESAgJ6iTNZkgABAgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgSyBQT0bGHzCRAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQKCEgIBe4kyWJECAAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAIFsAQE9W9h8AgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgQIECghIKCXOJMlCRAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQCBbQEDPFjafAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBEoICOglzmRJAgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgQIEMgWENCzhc0nQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAgRICAnqJM1mSAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBLIFBPRsYfMJECBAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAoISAgF7iTJYkQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAgWwBAT1b2HwCBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQKCEgoJc4kyUJECBAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAIFtAQM8WNp8AAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIESggI6CXOZEkCBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQyBYQ0LOFzSdAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAgACBEgICeokzWZIAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIEsgUE9Gxh8wkQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQIECghICAXuJMliRAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAgACBbAEBPVvYfAIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAoISCglziTJQkQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQIEAgW0BAzxY2nwABAgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgRKCAjoJc5kSQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBDIFhDQs4XNJ0CAAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAIESAgJ6iTNZkgABAgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgSyBQT0bGHzCRAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQKCEgIBe4kyWJECAAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAIFsAQE9W9h8AgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgQIECghIKCXOJMlCRAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQCBbQEDPFjafAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBEoICOglzmRJAgQIECBAgAABAgQIECBAgAABAgQIECBAgAABAgQIEMgWENCzhc0nQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAgRICAnqJM1mSAAECBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBLIFBPRsYfMJECBAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAoISAgF7iTJYkQIAAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAgWwBAT1b2HwCBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQKCEgoJc4kyUJECBAgAABAgQIECBAgAABAgQIWgqb2wAAALBJREFUECBAgAABAgQIECBAIFtAQM8WNp8AAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIESggI6CXOZEkCBAgQIECAAAECBAgQIECAAAECBAgQIECAAAECBAgQyBYQ0LOFzSdAgAABAgQIECBAgAABAgQIECBAgAABAgQIECBAgACBEgICeokzWZIAAQIECBAgQIAAAQIECBAgQIAAAQIECBAgQIAAAQIEsgW+AwUbG20F5HdnAAAAAElFTkSuQmCC"
        ]
    },
    {
        "key": "webgl",
        "value": [
            "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAASwAAACWCAYAAABkW7XSAAAAAXNSR0IArs4c6QAADMxJREFUeF7tnV+IJUcVh0/d2UXyEFBEokjQoLIPi2IURRGxRxEJKCh5iKAgAQVFg4gKCsp00AcRiaCgQgR9UBEFFRHxDzgDghE0mWV33YGdJetmdF0TMUsSd0k2bkvd7nHu3L1/+t7bXVWnzjev2111zu93+Lb63KpuJ/yhAAqggBIFnJI4CRMFUAAFBGBRBCiAAmoUAFhqrCJQFEABgEUNoAAKqFEAYKmxikBRAAUAFjWAAiigRgGApcYqAkUBFABY1AAKoIAaBQCWGqsIFAVQAGBRAyiAAmoUAFhqrCJQFEABgEUNoAAKqFEAYKmxikBRAAUAFjWAAiigRgGApcYqAkUBFABY1AAKoIAaBQCWGqsIFAVQAGBRAyiAAmoUAFhqrCJQFEABgEUNdK5AVUkhIm9xTu7tfHAGNK0AwDJtfz/JN8DaFJF152Srn1kY1aICAMui6z3nfL2STSfDVZY4x3cDepbb1PAAy5TdYZIdBZaIlDwahtHdwiwAy4LLgXO8Xkk1VlhAK7AHuU4HsHJ1NlJe1yop1mT4SDj+B7QieZLTtAArJzcTyOXZSjYHIsWUwqIJn4BHmkMAWJrdSzD2OcCiCZ+gZ5pCAlia3FIQ67OVVAP/6+D0WLeck3UFqRBiggoArARN0RqS7185GT4SztvLQD9Lq8mR4wZYkQ3Iafprzf6rFsDyaQOtnMwPlAvACiS0hWkWBJaXhCa8hcLoMEeA1aGY1oe61uy/arnCGsrFTnjrVbNY/gBrMb24eooCVyspjjT7rxYBlojQhKeqWisAsFpLxYWzFHi6ko2B70uJyILAop9FabVWAGC1looLZynwTNNwXxJYQIvyaqUAwGolExfNU+Dpkf1XS6yw9ofnl8N5Qhv/d4BlvAC6SN/3rwYj+69WABZN+C4MyXgMgJWxuaFSu9r0r/ZBtQqwaMKHck3nPABLp29JRX21OfDcEbDoZyXlblrBAKy0/FAZzdWmf9UhsICWykroP2iA1b/GWc/wZLP/ysOqY2ABrawrZ7nkANZyunFXo4DvX/lzgT0BiyY8lXZIAYBFQaykwJWRA889rLB8bOyEX8mhvG4GWHn5GTybKyPnB3sCFo+GwV1Nd0KAla43yUfm+1f772/v65FwRAQ2lSZfEf0HCLD61zjbGf5TyYYbOT/Y4wprX0OglW01tUsMYLXTiasmKPDUyAcnAqyw9iPgHVqGqxFgGTZ/1dSfGjs/GGCFRRN+VdOU3w+wlBsYK/zHKymOjp0fDAQsmvCxTE9gXoCVgAkaQ4gMLKClsWg6iBlgdSCixSGemHB+MOAKiya8xaKb/zUmo6qQ9lwFnphwfjACsHycNOHnupXPBayw8vEyWCb+cdDvvxr/ZTASsDi+E8z5+BMBrPgeqIsgNWDxjUN1JbR0wABraens3nh5pH81uqqKtcJqnGBTqYGSBFgGTO46xcsj/auEgMUvh10bneB4ACtBU1IOyT8OupH+VWLAogmfcvF0EBvA6kBES0MoABZN+IwLEmBlbG4fqT0+9v6rBFdYPm3eodWH+QmMCbASMEFTCEqART9LU1EtECvAWkAs65c+1ry/ff/rzqnsw5rhC78cZla0ACszQ/tMRyGwaML3WRARxgZYEUTXOuW/m/6VohXWUGrnhDrXWnRjcWNkJkaGSEMrsGjCh6iOMHMArDA6q5/FPw4OJrz/KtFfCSfpTT9LfRUKS+UMPAySQgbA4pfDIJXS7ySssPrVN5vRH5vy/itFK6x9L1hpKa5KgKXYvJChZwQsmvAhC6fjuQBWx4LmONw/mv1Xk/ZdKVxheYvYCa+0UAGWUuNChp0hsOhnhSygDucCWB2KmetQj46dH9S2D2uGL/SzlBUtwFJmWIxwMwYWK60YBbXCnABrBfGs3PpoJdXoqiqjFdbQQnbC66lkgKXHqyiR+v6V/+BEzsCiCR+ltJaaFGAtJZudmy5dl81B/ZZRyehXwkkGlm5N7rXjrM5MAZZO34JFfemZ4ee8LADLn/so3VGgFay4lpgIYC0hmqVbLl2RatpeKwXvw1rcKg+tm4DW4sKFuQNghdFZ5Sx7T0pxdMKB59ya7hPMWXc3y5ZK0zIPGmBlbvAq6V28XD8Omlph1YJtuefK+iracW8/CgCsfnTNYtSL/zILrLqf9XweDVMrZICVmiMJxXPxn3X/yuAKa9+F0t0CtBIqSd6HlZIZKcWytyfF2mC4wrIMLG9J6V4MtFKpTVZYqTiRWBwXH5FNafpXhldYtSv/lXV3G034FEoUYKXgQoIxXDwPsEZtcbfxNJJCmQKsFFxIMIa/704/P2hgW8MkR0r3Ch4NY5cqwIrtQILz7+1IMXDTzw8aBVb9y+ExoBWzZAFWTPUTnXvvL7IxqKScdn7QLLC8Xx5ax4FWrNIFWLGUT3jevZOzDzybBpb37bqsu9tpwscoYYAVQ/XE59x7aPb5QfPA8gut19CEj1HGACuG6gnPef4BKY6s1fuveCScadSWez3Hd0KXMsAKrXji8114QDYGIiXAamVU6d5IP6uVUh1dBLA6EjKXYR75/fDXwZkHnnkkPOR26d4MtELVP8AKpbSSeS5szT8/CLDGzKxk3a3ThA9R4gArhMpK5jj/WykGLc4PAqwbDC3d21hlhShzgBVCZSVzXPi1bPjDvvMOPAOssUfCdwCrUCUOsEIprWCe8788eP8VTfc5hvkNpHcAqtBlDbBCK57wfOd/ftC/AlhTjPKgehegilXGACuW8onNu/tTKY4072/nkXCiOaV7D6CKXbYAK7YDicy/+2MpjriDF/axwmqM8SuqOwFVImXK8YJUjIgdx8M/PNh/xQqrOeR8F6CKXZfj87PCSs2RSPE8/P3D778yvMIq3fsAVaQynDstwJorUf4X7H6nfn97m+0K4yCbBjaFhVV6p90HgFXKFa+wrlKWU2dsu/dLsbZmGFi+T3U3oNJQvQBLg0s9x3ju/nr/lcEVVuk+BKh6Lq9OhwdYncqpc7Bz37zx/VeZ97BK9xFApbFaAZZG1zqMeefrUhxttjNkv8Lyj34fBVQdlk/woQBWcMnTmnDnqwaA5UH1cUCVVuUtFw3AWk63bO46e1/9/va2v/61vS6RwirdJwFVNsXavAU3p3zIZUEFzn558vuvVPew/Irq04BqwVJQcXki/xGq0Cq7IHe+UG9nmLSzXSWwnNR7qT4LrLIr1iYhgJWrsy3yGgJr5MCz8qZ76T4PqFrYrvoSgKXavtWCP7shm9K8v71tb6rtdcEKayCl2wBUq1WCnruD1ZUeSexEevZzqoFVui8CKjvVWmcKsKw53uS78xkpBu7wcRwVj4SVlO5LgMpo2QIsq8bvfEoZsDyovgKorNbrft6ssIxWwM4nZHPgDp8fTHSFVbr7AJXRMr0hbYBltBJ27kkeWKX7GqAyWp5T0wZYBivi1MekOFLV+69GV1VJrLCqZi/VN4CVwdKcmzLAmitRfhec+vDBBycSA1bpvgWo8qu47jICWN1pqWakMx88eH97IsAq3bcBlZoCihgowIoofqypz9ydCLD8L3/fBVSx6kDjvABLo2srxHzq/fV2hnlfxun1LKEH1fcA1Qo2mr0VYBmz/tR7pRgMogGrdD8AVMZKrtN0AVancqY/2Om7Dn9/MEgPy6+ofgSo0q+O9CMEWOl71GmEp+8MCCwPqp8Aqk4NND4YwDJWAKffffiDqX2ssNak2Uv1M2BlrLx6Txdg9S5xOhNsv1OKozL9wHMXG0cHIuXaLwBVOq7nFQnAysvPmdmcvOPG7w92tsKqpHzOrwCVoXKKkirAiiJ7nElPvn32+cFlVlj+8e+m3wCqOI7amxVgGfL85Ftv/GDqsissD6qbfweoDJVPEqkCrCRs6D+I7UKKtTkHnlutsJyUz9sCVP07xgyTFABYRurixJvq/tXSO9grKV/wB0BlpFySTRNgJWtNt4GdeMNywPKPfrf8EVB16wajLasAwFpWOWX3nXjd5A+mTu1hVVL61diL/gyslFmddbgAK2t76+S2Xy2Fa3Hg+f/wqqS89QSgMlAa6lIEWOosWzzg7VfJhpN6xTSrh+Uf/15yElAtrjB3hFIAYIVSOuI828dl01V1w30SsDyoXnYGUEW0iKlbKgCwWgql+bLtY1POD1ZSHjsLqDR7ay12gJW54396ef3+9rHmenn8HKDK3Pos0wNYWdp6kNSDL5UNfyDZG+0f/V75V0CVueVZpwewsrZX5KFbh/2rrdv/Bqgyt9pEegArc5sffKFsvPYSsMrcZjPpASwzVpMoCuhXAGDp95AMUMCMAgDLjNUkigL6FQBY+j0kAxQwowDAMmM1iaKAfgUAln4PyQAFzCgAsMxYTaIooF+B/wGUsPWmkr+6+QAAAABJRU5ErkJggg==",
            "extensions:ANGLE_instanced_arrays;EXT_blend_minmax;EXT_color_buffer_half_float;EXT_disjoint_timer_query;EXT_float_blend;EXT_frag_depth;EXT_shader_texture_lod;EXT_texture_compression_bptc;EXT_texture_compression_rgtc;EXT_texture_filter_anisotropic;EXT_sRGB;KHR_parallel_shader_compile;OES_element_index_uint;OES_fbo_render_mipmap;OES_standard_derivatives;OES_texture_float;OES_texture_float_linear;OES_texture_half_float;OES_texture_half_float_linear;OES_vertex_array_object;WEBGL_color_buffer_float;WEBGL_compressed_texture_s3tc;WEBGL_compressed_texture_s3tc_srgb;WEBGL_debug_renderer_info;WEBGL_debug_shaders;WEBGL_depth_texture;WEBGL_draw_buffers;WEBGL_lose_context;WEBGL_multi_draw",
            "webgl aliased line width range:[1, 1]",
            "webgl aliased point size range:[1, 1024]",
            "webgl alpha bits:8",
            "webgl antialiasing:yes",
            "webgl blue bits:8",
            "webgl depth bits:24",
            "webgl green bits:8",
            "webgl max anisotropy:16",
            "webgl max combined texture image units:32",
            "webgl max cube map texture size:16384",
            "webgl max fragment uniform vectors:1024",
            "webgl max render buffer size:16384",
            "webgl max texture image units:16",
            "webgl max texture size:16384",
            "webgl max varying vectors:30",
            "webgl max vertex attribs:16",
            "webgl max vertex texture image units:16",
            "webgl max vertex uniform vectors:4095",
            "webgl max viewport dims:[32767, 32767]",
            "webgl red bits:8",
            "webgl renderer:WebKit WebGL",
            "webgl shading language version:WebGL GLSL ES 1.0 (OpenGL ES GLSL ES 1.0 Chromium)",
            "webgl stencil bits:0",
            "webgl vendor:WebKit",
            "webgl version:WebGL 1.0 (OpenGL ES 2.0 Chromium)",
            "webgl unmasked vendor:Google Inc. (NVIDIA)",
            "webgl unmasked renderer:ANGLE (NVIDIA, NVIDIA GeForce GTX 1050 Ti Direct3D11 vs_5_0 ps_5_0, D3D11)",
            "webgl vertex shader high float precision:23",
            "webgl vertex shader high float precision rangeMin:127",
            "webgl vertex shader high float precision rangeMax:127",
            "webgl vertex shader medium float precision:23",
            "webgl vertex shader medium float precision rangeMin:127",
            "webgl vertex shader medium float precision rangeMax:127",
            "webgl vertex shader low float precision:23",
            "webgl vertex shader low float precision rangeMin:127",
            "webgl vertex shader low float precision rangeMax:127",
            "webgl fragment shader high float precision:23",
            "webgl fragment shader high float precision rangeMin:127",
            "webgl fragment shader high float precision rangeMax:127",
            "webgl fragment shader medium float precision:23",
            "webgl fragment shader medium float precision rangeMin:127",
            "webgl fragment shader medium float precision rangeMax:127",
            "webgl fragment shader low float precision:23",
            "webgl fragment shader low float precision rangeMin:127",
            "webgl fragment shader low float precision rangeMax:127",
            "webgl vertex shader high int precision:0",
            "webgl vertex shader high int precision rangeMin:31",
            "webgl vertex shader high int precision rangeMax:30",
            "webgl vertex shader medium int precision:0",
            "webgl vertex shader medium int precision rangeMin:31",
            "webgl vertex shader medium int precision rangeMax:30",
            "webgl vertex shader low int precision:0",
            "webgl vertex shader low int precision rangeMin:31",
            "webgl vertex shader low int precision rangeMax:30",
            "webgl fragment shader high int precision:0",
            "webgl fragment shader high int precision rangeMin:31",
            "webgl fragment shader high int precision rangeMax:30",
            "webgl fragment shader medium int precision:0",
            "webgl fragment shader medium int precision rangeMin:31",
            "webgl fragment shader medium int precision rangeMax:30",
            "webgl fragment shader low int precision:0",
            "webgl fragment shader low int precision rangeMin:31",
            "webgl fragment shader low int precision rangeMax:30"
        ]
    },
    {
        "key": "webglVendorAndRenderer",
        "value": "Google Inc. (NVIDIA)~ANGLE (NVIDIA, NVIDIA GeForce GTX 1050 Ti Direct3D11 vs_5_0 ps_5_0, D3D11)"
    },
    {
        "key": "adBlock",
        "value": false
    },
    {
        "key": "hasLiedLanguages",
        "value": false
    },
    {
        "key": "hasLiedResolution",
        "value": false
    },
    {
        "key": "hasLiedOs",
        "value": false
    },
    {
        "key": "hasLiedBrowser",
        "value": false
    },
    {
        "key": "touchSupport",
        "value": [
            0,
            false,
            false
        ]
    },
    {
        "key": "fonts",
        "value": [
            "Arial",
            "Arial Black",
            "Arial Narrow",
            "Book Antiqua",
            "Bookman Old Style",
            "Calibri",
            "Cambria",
            "Cambria Math",
            "Century",
            "Century Gothic",
            "Comic Sans MS",
            "Consolas",
            "Courier",
            "Courier New",
            "Georgia",
            "Helvetica",
            "Impact",
            "Lucida Console",
            "Lucida Handwriting",
            "Lucida Sans Unicode",
            "Microsoft Sans Serif",
            "Monotype Corsiva",
            "MS Gothic",
            "MS PGothic",
            "MS Reference Sans Serif",
            "MS Sans Serif",
            "MS Serif",
            "Palatino Linotype",
            "Segoe Print",
            "Segoe Script",
            "Segoe UI",
            "Segoe UI Light",
            "Segoe UI Semibold",
            "Segoe UI Symbol",
            "Tahoma",
            "Times",
            "Times New Roman",
            "Trebuchet MS",
            "Verdana",
            "Wingdings",
            "Wingdings 2",
            "Wingdings 3"
        ]
    },
    {
        "key": "audio",
        "value": "124.04347527516074"
    }
]
function get_login_url(CallBack, userName, checkCode, password) {
    password = getMD5Value(password)
    aws = printComponents(components)
    var url = 'https://aq.99.com/AjaxAction/AC_userlogin.ashx'
    return url + "?CallBack=" + CallBack + "&siteflag=995&nduseraction=login&txtUserName=" + userName + "&txtPassword=" + password + "&checkcode=" + checkCode + "&Rnd=" + Math.random() + "&aws=" + aws;
}

Python源码:

"""
Email:912917367@qq.com
Date: 2023/8/24 10:18
"""
import re
import time

import execjs
import requests

from utils.chaojiying import ChaojiyingClient


class Spider:
    def __init__(self, username, password):
        self.session = requests.session()
        self.session.headers = {
            "authority": "checkcode.99.com",
            "referer": "https://aq.99.com/",
            "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.0.0 Safari/537.36"
        }
        self.callback = 'jQuery112401962284678331523_1692843120473'
        self.ticket = ''
        self.img_url = ''
        self.pic_str = ''
        self.username = username
        self.password = password

    def get_ticket(self):
        url = "https://checkcode.99.com/token"
        params = {
            "action": "getticket",
            "bussiness": "aq_login",
            "callback": self.callback,
            "_": str(int(time.time() * 1000))
        }
        response = self.session.get(url, params=params)
        pattern = r'"ticket":"(.*?)"'
        self.ticket = re.findall(pattern, response.text)[0]
        print('ticket:', self.ticket)

    def get_img_url(self):
        url = "https://aq.99.com/AjaxAction/AC_verifycode.ashx"
        params = {
            "CallBack": self.callback,
            "nduseraction": "getverifycodestate",
            "verifycodetype": "UserLogin",
            "bussiness": "aq_login",
            "ticket": self.ticket,
            "SiteFlag": "995",
            "RND": "0.7099289496089389",
            "_": str(int(time.time() * 1000))
        }
        response = self.session.get(url, params=params)
        pattern = r'"VerifyCodeUrl":"(.*?)"'
        self.img_url = re.findall(pattern, response.text)[0]
        print('img_url:', self.img_url)

    def get_img_code(self):
        response = self.session.get(self.img_url)
        with open('img.png', 'wb') as f:
            f.write(response.content)

        cjy = ChaojiyingClient('打码平台账号', '打码平台密码', '946014')
        im = open('img.png', 'rb').read()
        pic_data = cjy.post_pic(im, 1902)
        self.pic_str = pic_data['pic_str']
        print('pic_str:', self.pic_str)

    def login(self):
        with open('get_params.js', 'r', encoding='utf-8') as f:
            js_obj = execjs.compile(f.read())
        url = js_obj.call('get_login_url', self.callback, self.username, self.pic_str, self.password)
        response = self.session.get(url)
        print(response.text)
        print(response)


if __name__ == '__main__':
    s = Spider('账号', '密码')
    s.get_ticket()
    s.get_img_url()
    s.get_img_code()
    s.login()

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/88775.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

【Git版本控制工具使用---讲解一】

Git版本控制工具使用 安装设置用户名签名和邮箱Git常用的命令 初始化本地库查看本地状态Git 命令添加暂存区提交本地库查看版本信息修改文件版本穿梭 安装 首先根据自身电脑的配置选择性的安装是32位的还是64位的Git版本控制工具 我这边安装的是64位的 以下是我安装的时候的过…

C语言:选择+编程(每日一练Day8)

目录 选择题&#xff1a; 题一&#xff1a; 题二&#xff1a; 题三&#xff1a; 题四&#xff1a; 题五&#xff1a; 编程题&#xff1a; 题一&#xff1a;字符个数统计 思路一&#xff1a; 题二&#xff1a;多数元素 思路一&#xff1a; 本人实力有限可能对一些…

事件捕获和事件冒泡

事件捕获和事件冒泡与事件流有关系。 以下代码&#xff0c;点击 aa &#xff0c;控制台会打印什么呢&#xff1f; <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8" /><meta name"viewport" content&q…

Docker(一)-安装、架构、业务开发常用命令、Dockerile、镜像卷、镜像仓库

基于业务开发使用Docker Docker是一个开源的容器引擎&#xff0c;它有助于更快地交付应用。Docker可将应用程序和基础设施层隔离&#xff0c;并且能将基础设施当作程序一样进行管理。使用 Docker可更快地打包、测试以及部署应用程序&#xff0c;并可以缩短从编写到部署运行代码…

App Inventor 2 开发 ChatGPT 对话App

ChatGPT大家应该不会陌生&#xff0c;它的回答内容非常的专业及深入&#xff0c;具有实际的可指导性。我们通过App Inventor 2开发一个简单的对话App&#xff0c;先看效果&#xff1a; App Inventor 2 ChatGPT教育领域对话演示 代码块如下&#xff1a; 用到的核心组件“ChatBot…

kafka--技术文档--spring-boot集成基础简单使用

阿丹&#xff1a; 查阅了很多资料了解到&#xff0c;使用了spring-boot中整合的kafka的使用是被封装好的。也就是说这些使用其实和在linux中的使用kafka代码的使用其实没有太大关系。但是逻辑是一样的。这点要注意&#xff01; 使用spring-boot整合kafka 1、导入依赖 核心配…

Web3和去中心化:互联网的下一个演化阶段

文章目录 Web3和去中心化的定义Web3&#xff1a;去中心化&#xff1a; 为什么Web3和去中心化如此重要&#xff1f;数据隐私和安全&#xff1a;去中心化的创新&#xff1a;去除中间商&#xff1a; Web3和去中心化的应用领域去中心化金融&#xff08;DeFi&#xff09;&#xff1a…

掌握AI助手的魔法工具:解密Prompt(提示)在AIGC时代的应用「上篇」

在当今的AIGC时代&#xff0c;我们面临着越来越多的人工智能技术和应用。其中一个引人注目的工具就是Prompt&#xff08;提示&#xff09;。它就像是一种魔法&#xff0c;可以让我们与AI助手进行更加互动和有针对性的对话。那么&#xff0c;让我们一起来了解一下Prompt&#xf…

长胜证券:货币政策什么意思?

钱银政策是指国家钱银当局经过调控钱银供给量和利率等手法&#xff0c;以到达操控通货膨胀、坚持经济稳定、促进经济增长等目的的一种宏观经济政策。简而言之&#xff0c;钱银政策便是国家中央银行对钱银供给和利率进行调控的政策。那么具体来说&#xff0c;钱银政策到底有哪些…

windwos系统如何创建typecho个人博客并通过内网穿透实现无公网IP访问

文章目录 前言1. 环境安装2.安装Typecho3.安装cpolar内网穿透4. 固定公网地址5.配置Typecho 前言 Typecho是一款PHP语言编写的开源博客程序&#xff0c;它是一个轻量级的内容管理系统&#xff0c;专注于博客领域。支持多用户、多站点、多语言等功能&#xff0c;可以满足不同用…

水库大坝安全监测的主要内容包括哪些?

在水库大坝的实时监测中&#xff0c;主要任务是通过无线传感网络监测各个监测点的水位、水压、渗流、流量、扬压力等数据&#xff0c;并在计算机上用数据模式或图形模式进行实时反映&#xff0c;以掌握整个水库大坝的各项变化情况。大坝安全监测系统能实现全天候远程自动监测&a…

CSS中的vertical-align属性

vertical-align 1.CSS属性 - vertical-align 2.深入理解vertical-align – line boxes This property affects the vertical positioning inside a line box of the boxes generated by an inline-levelelement. 官方文档的翻译&#xff1a;vertical-align会影响 行内块级元素…

Python“牵手”速卖通商品列表数据,关键词搜索速卖通API接口数据,速卖通API接口申请指南

速卖通平台API接口是为开发电商类应用程序而设计的一套完整的、跨浏览器、跨平台的接口规范&#xff0c;速卖通API接口是指通过编程的方式&#xff0c;让开发者能够通过HTTP协议直接访问速卖通平台的数据&#xff0c;包括商品信息、店铺信息、物流信息等&#xff0c;从而实现速…

Unity 之transform.LookAt() 调整一个物体的旋转,使其朝向指定的位置

文章目录 总的介绍补充&#xff08;用于摄像机跟随的场景&#xff09; 总的介绍 transform.LookAt 是 Unity 引擎中 Transform 组件的一个方法&#xff0c;用于调整一个物体的旋转&#xff0c;使其朝向指定的位置。通常情况下&#xff0c;它被用来使一个物体&#xff08;如摄像…

HarmonyOS开发:超详细了解项目的工程结构

前言 系列文章目录&#xff1a; HarmonyOS开发第一步&#xff0c;熟知开发工具DevEco Studio 当我们熟练的掌握了DevEco Studio之后&#xff0c;就可以创建项目进行练习了&#xff0c;和市场上大多数IDE一样&#xff0c;DevEco Studio也给我们提供了很多的实例模板&#xff0c…

如何远程管理服务器详解

文章目录 前言一、远程管理类型二、远程桌面三、telnet 命令行远程四、查看本地开放端口 前言 很多公司是有自己的机房的&#xff0c;机房里面会有若干个服务器为员工和用户提供服务。大家可以想想&#xff1a;假设这家公司有上百台服务器&#xff0c;我们作为网络工程师&…

行业追踪,2023-08-24

自动复盘 2023-08-24 凡所有相&#xff0c;皆是虚妄。若见诸相非相&#xff0c;即见如来。 k 线图是最好的老师&#xff0c;每天持续发布板块的rps排名&#xff0c;追踪板块&#xff0c;板块来开仓&#xff0c;板块去清仓&#xff0c;丢弃自以为是的想法&#xff0c;板块去留让…

流媒体服务器SRS的搭建及QT下RTMP推流客户端的编写

一、前言 目前市面上有很多开源的流媒体服务器解决方案&#xff0c;常见的有SRS、EasyDarwin、ZLMediaKit和Monibuca。这几种的对比如下&#xff1a; &#xff08;本图来源&#xff1a;https://www.ngui.cc/zz/1781086.html?actiononClick&#xff09; 二、SRS的介绍 SRS&am…

十一、hadoop应用

1.上传数据集 27.19.74.143,2015/3/30 17:38,/static/image/common/faq.gif 110.52.250.126,2015/3/30 17:38,/data/cache/style_1_widthauto.css?y7a 27.19.74.143,2015/3/30 17:38,/static/image/common/hot_1.gif 27.19.74.143,2015/3/30 17:38,/static/image/common/hot_2…

MyBatid动态语句且模糊查询

目录 什么是MyBtais动态语句&#xff1f;&#xff1f;&#xff1f; MyBatis常用的动态标签和表达式 if标签 Choose标签 where标签 MyBatis模糊查询 #与$的区别 ​编辑 MyBatis映射 resultType resultMap 什么是MyBtais动态语句&#xff1f;&#xff1f;&#xff1f;…