最新PDD批发Anti-Content参数逆向分析与算法还原

文章目录

  • 1. 写在前面
  • 2. 接口分析
  • 3. 分析与扣代码

【🏠作者主页】:吴秋霖
【💼作者介绍】:擅长爬虫与JS加密逆向分析!Python领域优质创作者、CSDN博客专家、阿里云博客专家、华为云享专家。一路走来长期坚守并致力于Python与爬虫领域研究与开发工作!
【🌟作者推荐】:对爬虫领域以及JS逆向分析感兴趣的朋友可以关注《爬虫JS逆向实战》《深耕爬虫领域》
未来作者会持续更新所用到、学到、看到的技术知识!包括但不限于:各类验证码突防、爬虫APP与JS逆向分析、RPA自动化、分布式爬虫、Python领域等相关文章

作者声明:文章仅供学习交流与参考!严禁用于任何商业与非法用途!否则由此产生的一切后果均与作者无关!如有侵权,请联系作者本人进行删除!

1. 写在前面

  上次周六的时候熬夜分析还原了一下商家后台的Anti-Content,那个参数是0aq开头的,本次的话应粉丝要求对批发网站进行了同样的参数分析,与其不同的是参数开头为0ar

分析目标

aHR0cHM6Ly9waWZhLnBpbmR1b2R1by5jb20v

老规矩,开局先放一张结果图,后续内容全靠编!!!

另外,对之前商家端Anti-Content参数分析感谢的,请看这篇文章:最新商家后台Anti-Content参数逆向分析与纯算法还原

在这里插入图片描述

2. 接口分析

主要通过商品搜索入口展开分析,然后到商品详情。首先,还是老规矩打开网站随便找个商品搜索一下,不出意料开局也是给了我一张图,据说多多的批发目前的风控是极其强的,我就分析测试了一下,黑了我一个号!!!

如果你看到你的页面一直是提示操作太过频繁,请稍后再试!之后页面就试一片空白,所有的功能都用不了

在这里插入图片描述

这个滑块的话,问题不大。有实力的话可以分析研究一下。我的话,没有实力,直接页面手动拖动一下,不然接口后续请求基本如下:

{result":{“verifyAuthToken”:“309dYy7ZgpWuk00cOyrgcQ3bed9a9ba4fdagfc7”},“error code”:54001, “error msa”:“”}

在此过程中我发现了一个特别迷惑的行为,就是出现滑块之后,网站页面,并没有弹出滑块的图,但是重新执行程序,接口不出滑块,正常可以请求到数据

我不知道是不是session的问题,但是就算重新执行程序,过程中比如在搜索提交一定次数后,同样会再次出现滑块反馈

直到最后,你的网页它也给你弹出了滑块,这个时候,更梦幻的就来了,你会发现浏览器触发一次滑块后,直接手过一下,拿参数下来用后续不会再出滑块

为了验证这个问题,我挂了程序一段时间,访问正常、搜索正常、详情页商品数据获取正常

说了这么多题外话,只是为了给大家一点踩过的坑。下面我们还是回到正题,如下所示:

在这里插入图片描述

参数没有啥加密的,主要的还是头部这个Anti-Content的参数加密,解决了它就迈过了第一重大山

在这里插入图片描述

再看一下响应数据,图中标注的字段在详情页接口请求中会用到

3. 分析与扣代码

跟商家端一样,我门搜索参数,然后断点开始调试分析。这里还是Webpack,所以我们找到入口,把自执行函数扣下来,Webpack最基本的组成就是自执行函数跟模块加载器!

之后把函数的实参,全部导出来放到自执行调用函数下,因为本身调用执行的就是一堆函数,只不过都是索引的方式

在这里插入图片描述

分析调试找到自执行函数,把代码扣出来,如下所示:

!function(e) {
    function t(t) {
        for (var n, o, d = t[0], f = t[1], i = t[2], u = 0, s = []; u < d.length; u++)
            o = d[u],
            Object.prototype.hasOwnProperty.call(c, o) && c[o] && s.push(c[o][0]),
            c[o] = 0;
        for (n in f)
            Object.prototype.hasOwnProperty.call(f, n) && (e[n] = f[n]);
        for (l && l(t); s.length; )
            s.shift()();
        return a.push.apply(a, i || []),
        r()
    }
    function r() {
        for (var e, t = 0; t < a.length; t++) {
            for (var r = a[t], n = !0, o = 1; o < r.length; o++) {
                var f = r[o];
                0 !== c[f] && (n = !1)
            }
            n && (a.splice(t--, 1),
            e = d(d.s = r[0]))
        }
        return e
    }
    var n = {}
      , o = {
        21: 0
    }
      , c = {
        21: 0
    }
      , a = [];
    function d(t) {
        if (n[t])
            return n[t].exports;
        var r = n[t] = {
            i: t,
            l: !1,
            exports: {}
        };
        return e[t].call(r.exports, r, r.exports, d),
        r.l = !0,
        r.exports
    }
    d.e = function(e) {
        var t = [];
        o[e] ? t.push(o[e]) : 0 !== o[e] && {
            1: 1,
            10: 1,
            11: 1,
            12: 1,
            14: 1,
            15: 1,
            17: 1
        }[e] && t.push(o[e] = new Promise((function(t, r) {
            for (var n = "static/css/" + ({
                7: "AccountCenter",
                8: "Activity",
                9: "BestGoods",
                10: "Cart",
                11: "GoodsDetail",
                12: "GoodsDropShipping",
                13: "Home",
                14: "Mall",
                15: "MallSearch",
                16: "NotFound",
                17: "Order",
                18: "Payment",
                19: "Search"
            }[e] || e) + "." + {
                0: "31d6cfe0d",
                1: "1bb732cb7",
                2: "31d6cfe0d",
                3: "31d6cfe0d",
                4: "31d6cfe0d",
                5: "31d6cfe0d",
                6: "31d6cfe0d",
                7: "31d6cfe0d",
                8: "31d6cfe0d",
                9: "31d6cfe0d",
                10: "86909bf59",
                11: "1405928aa",
                12: "9eff41d5d",
                13: "31d6cfe0d",
                14: "941e90c52",
                15: "86909bf59",
                16: "31d6cfe0d",
                17: "07dca30ce",
                18: "31d6cfe0d",
                19: "31d6cfe0d",
                23: "31d6cfe0d",
                24: "31d6cfe0d",
                25: "31d6cfe0d",
                26: "31d6cfe0d",
                27: "31d6cfe0d",
                28: "31d6cfe0d",
                29: "31d6cfe0d",
                30: "31d6cfe0d"
            }[e] + ".chunk.css", o = d.p + n, c = document.getElementsByTagName("link"), a = 0; a < c.length; a++) {
                var f = (u = c[a]).getAttribute("data-href") || u.getAttribute("href");
                if ("stylesheet" === u.rel && (f === n || f === o))
                    return t()
            }
            var i = document.getElementsByTagName("style");
            for (a = 0; a < i.length; a++) {
                var u;
                if ((f = (u = i[a]).getAttribute("data-href")) === n || f === o)
                    return t()
            }
            var l = document.createElement("link");
            l.rel = "stylesheet",
            l.type = "text/css",
            l.onload = t,
            l.onerror = function(t) {
                var n = t && t.target && t.target.src || o
                  , c = new Error("Loading CSS chunk " + e + " failed.\n(" + n + ")");
                c.request = n,
                r(c)
            }
            ,
            l.href = o,
            document.getElementsByTagName("head")[0].appendChild(l)
        }
        )).then((function() {
            o[e] = 0
        }
        )));
        var r = c[e];
        if (0 !== r)
            if (r)
                t.push(r[2]);
            else {
                var n = new Promise((function(t, n) {
                    r = c[e] = [t, n]
                }
                ));
                t.push(r[2] = n);
                var a, f = document.createElement("script");
                f.charset = "utf-8",
                f.timeout = 120,
                d.nc && f.setAttribute("nonce", d.nc),
                f.src = function(e) {
                    return d.p + "static/js/" + ({
                        7: "AccountCenter",
                        8: "Activity",
                        9: "BestGoods",
                        10: "Cart",
                        11: "GoodsDetail",
                        12: "GoodsDropShipping",
                        13: "Home",
                        14: "Mall",
                        15: "MallSearch",
                        16: "NotFound",
                        17: "Order",
                        18: "Payment",
                        19: "Search"
                    }[e] || e) + "." + {
                        0: "f10cbb13",
                        1: "1f11793f",
                        2: "377e6d6e",
                        3: "35ce66b2",
                        4: "067dc63d",
                        5: "faf75b50",
                        6: "c87ff2b9",
                        7: "5a36fa8d",
                        8: "3e335bc4",
                        9: "419b7116",
                        10: "3088d3ab",
                        11: "39a585d4",
                        12: "d07a6c4a",
                        13: "20c6d848",
                        14: "30a72180",
                        15: "53f0e801",
                        16: "bd04a08e",
                        17: "319b16be",
                        18: "135c3c2b",
                        19: "66b54e82",
                        23: "c46b72b3",
                        24: "bcfa92ac",
                        25: "dbb47e8b",
                        26: "8b9ca1c3",
                        27: "1e9746e3",
                        28: "73b775ab",
                        29: "c13c09f3",
                        30: "ca572efb"
                    }[e] + ".chunk.js"
                }(e);
                var i = new Error;
                a = function(t) {
                    f.onerror = f.onload = null,
                    clearTimeout(u);
                    var r = c[e];
                    if (0 !== r) {
                        if (r) {
                            var n = t && ("load" === t.type ? "missing" : t.type)
                              , o = t && t.target && t.target.src;
                            i.message = "Loading chunk " + e + " failed.\n(" + n + ": " + o + ")",
                            i.name = "ChunkLoadError",
                            i.type = n,
                            i.request = o,
                            r[1](i)
                        }
                        c[e] = void 0
                    }
                }
                ;
                var u = setTimeout((function() {
                    a({
                        type: "timeout",
                        target: f
                    })
                }
                ), 12e4);
                f.onerror = f.onload = a,
                document.head.appendChild(f)
            }
        return Promise.all(t)
    }
    ,
    d.m = e,
    d.c = n,
    d.d = function(e, t, r) {
        d.o(e, t) || Object.defineProperty(e, t, {
            enumerable: !0,
            get: r
        })
    }
    ,
    d.r = function(e) {
        "undefined" !== typeof Symbol && Symbol.toStringTag && Object.defineProperty(e, Symbol.toStringTag, {
            value: "Module"
        }),
        Object.defineProperty(e, "__esModule", {
            value: !0
        })
    }
    ,
    d.t = function(e, t) {
        if (1 & t && (e = d(e)),
        8 & t)
            return e;
        if (4 & t && "object" === typeof e && e && e.__esModule)
            return e;
        var r = Object.create(null);
        if (d.r(r),
        Object.defineProperty(r, "default", {
            enumerable: !0,
            value: e
        }),
        2 & t && "string" != typeof e)
            for (var n in e)
                d.d(r, n, function(t) {
                    return e[t]
                }
                .bind(null, n));
        return r
    }
    ,
    d.n = function(e) {
        var t = e && e.__esModule ? function() {
            return e.default
        }
        : function() {
            return e
        }
        ;
        return d.d(t, "a", t),
        t
    }
    ,
    d.o = function(e, t) {
        return Object.prototype.hasOwnProperty.call(e, t)
    }
    ,
    d.p = "https://mms-static.pddpic.com/wholesale/",
    d.oe = function(e) {
        throw console.error(e),
        e
    }
    ;
    var f = window.webpackJsonp = window.webpackJsonp || []
      , i = f.push.bind(f);
    f.push = t,
    f = f.slice();
    for (var u = 0; u < f.length; u++)
        t(f[u]);
    var l = i;
    r()
}([]);

如果加载器函数与执行对象在一个文件中的Webpack就会比较好扣,首先,在函数内找到模块加载器的特征位置,代码如下所示:

function d(t) {
    if (n[t])
        return n[t].exports;
    var r = n[t] = {
        i: t,
        l: !1,
        exports: {}
    };
    return e[t].call(r.exports, r, r.exports, d),
    r.l = !0,
    r.exports
}

上面这个t传入的可以是索引和对象的key,参数表示的是列表或对象的形参,接下来需要把目标扣出来,自执行函数只是其中的一步,传入的t才是关键,如下跳转:

在这里插入图片描述

直接把所有调用模块导出来,放到自执行的[]内,如下所示:

在这里插入图片描述

最后我们将算法的调用集成到Python程序中测试一下效果,如下:

在这里插入图片描述

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

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

相关文章

Day:007(1) | Python爬虫:高效数据抓取的编程技术(scrapy框架使用)

Scrapy的介绍 Scrapy 是一个用于抓取网站和提取结构化数据的应用程序框架&#xff0c;可用于各种有用的应用程序&#xff0c;如数据挖掘、信息处理或历史存档。 尽管 Scrapy 最初是为网络抓取而设计的&#xff0c;但它也可用于使用API提取数据或用作通用网络爬虫。 Scrapy的优势…

海外媒体发稿:4种旅游业媒体套餐助你宣发推广-华媒舍

在现代社会中&#xff0c;旅游业发展迅速&#xff0c;竞争也变得日益激烈。为了让自己的旅游产品或服务脱颖而出&#xff0c;宣传和推广变得至关重要。有着强大传播力的媒体平台成为了旅游行业的一项重要资源。为了更好地推广旅游业&#xff0c;提高其影响力&#xff0c;有许多…

ABAP-CPI-Odata POST-create_deep_entity 多层嵌套的处理及CPI端的调用

该文章演示怎么在OData里,创建一个多套多的请求结构,传入数据处理后,返回多层级的处理结果;以及如何在CPI里写groovy脚本,去解析它;最后如何用postman模拟外围系统,调用CPI这个接口,从而去调用Odata接口 假如想用SAP Odata去实现传入多层级的数据,进行创建或者根据传入…

word并排比较

Word并排比较是一种在Microsoft Word文档中同时显示两个文本内容并进行比较的功能。这种比较通常用于查看文档的不同版本之间的差异&#xff0c;或者比较两个不同来源的文本内容。 在Word中进行并排比较通常可以通过以下步骤实现&#xff1a; 通过这种方式&#xff0c;Word的并…

港科夜闻|叶玉如校长牵头举办大湾区国际科创峰会,与海内外教育领袖共话全球合作,教育与创新...

关注并星标 每周阅读港科夜闻 建立新视野 开启新思维 1、香港科大校长叶玉如教授牵头举办大湾区国际科创峰会&#xff0c;与海内外教育领袖共话全球合作、教育与创新。粤港澳大湾区院士联盟主办的“第二届大湾区国际科创峰会”4月3日在香港科学园举行&#xff0c;汇聚了区内及海…

跟TED演讲学英文:Why AI will spark exponential economic growth by Cathie Wood

TED英文文稿 文章目录 TED英文文稿Why AI will spark exponential economic growthIntroductionVocabularyTranscriptSummary后记 Why AI will spark exponential economic growth Link: https://www.ted.com/talks/cathie_wood_why_ai_will_spark_exponential_economic_growth…

vscode远程免密登录ssh

vscode远程免密登录ssh 1. 安装vscode2. 安装ssh3. 本地vscode配置免密登录远端开发机1. 本地配置秘钥2. 远程开发机配置秘钥 4. vscode常用小工具1. vscode怎么设置ctrl加滚轮放大字体 1. 安装vscode 2. 安装ssh 设置符号打开config配置文件&#xff0c;点击符号ssh连接新的远…

Kubernetes(k8s):深入理解 Kubernetes 中的污点(Taints)与容忍度(Tolerations)

Kubernetes&#xff08;k8s&#xff09;&#xff1a;深入理解 Kubernetes 中的污点&#xff08;Taints&#xff09;与容忍度&#xff08;Tolerations&#xff09; 1、污点&#xff08;Taints&#xff09;2、容忍度&#xff08;Tolerations&#xff09;3、示例演示-测试污点的具…

Leetcode 399. 除法求值

心路历程&#xff1a; 一开始看着挺蒙的主要是不知道这道题在考察哪个知识点&#xff0c;后来按顺序把三个示例自己模拟着做出来之后发现本质其实在考类似链表或者指针的东西。 再一想其实是一个树或者图的遍历搜索问题&#xff0c;一下子想到了回溯算法。 第一次遇到这个题从…

Rocky(Centos)数据库等高并发或高io应用linux系统调优,及硬件问题排查(含网络、磁盘、系统监控)

一、系统参数优化 默认的最大打开文件数是1024.不满足生产环境的要求。按照如下配置&#xff1a; 1、修改 systemctl管理的 servie 资源限制 编辑/etc/systemd/system.conf # 全局的打开文件数 DefaultLimitNOFILE2097152 # 全局打开进程数 DefaultLimitNPROC655352、调整系…

[管理者与领导者-159] :社交策略和智慧-2,看破不说破,如何与虚伪的人和谐相处

目录 前言&#xff1a; 一、看破不说破 二、与虚伪的愉悦相处 三、如何利用社交技巧赞扬虚伪的人&#xff0c;而不失自己的原则 前言&#xff1a; 在实现生活中&#xff0c;总与遇到一种人&#xff0c;他们说一套&#xff0c;做一套、心理想一套&#xff0c;他们把自己利己…

面试-数据库基础以及MySql、ClickHost、Redis简介

面试-数据库基础以及MySql、ClickHost、Redis简介 0.数据完整性1.数据库并发控制1.1事物1.2 并发读写错误1.3 锁1.3.1 乐观锁与悲观锁1.3.2 共享锁和排他锁1.3.3 行锁与表锁1.3.4 意向锁 1.4 封锁协议与隔离级别1.5 MVCC1.5.1 概念1.5.2 当前读与快照读1.5.3 MVCC in InnoDB 2.…

数据采集仪:自动化监测系统的核心组件

在当代的工业自动化领域&#xff0c;数据采集仪成为了一个关键的技术工具&#xff0c;它不仅仅是简单地将电信号转化为数据信号&#xff0c;而是能够实时、有效地处理和显示各种信号&#xff0c;确保整个监测系统的稳定、高效运行。 点击输入图片描述&#xff08;最多30字&…

redis-缓存穿透与雪崩

一&#xff0c;缓存穿透&#xff08;查不到&#xff09; 在默认情况下&#xff0c;用户请求数据时&#xff0c;会先在缓存(Redis)中查找&#xff0c;若没找到即缓存未命中&#xff0c;再在数据库中进行查找&#xff0c;数量少可能问题不大&#xff0c;可是一旦大量的请求数据&a…

自动化测试selenium(2)

目录 WebDriver介绍 WebDriver使用 使用WebDriver驱动操作浏览器(打开一个百度) WebDriver 相关API 定位元素 操作元素 上一篇主要介绍了自动化测试的概念以及selenium的基本原理, 这里我们来讲一下如何利用selenium来写测试用的脚本. WebDriver介绍 Selenium是一个用于…

GitHub repository - Branch - SSH clone URL - Clone in Desktop - Download ZIP

GitHub repository - Branch - SSH clone URL - Clone in Desktop - Download ZIP 1. Branch2. SSH clone URL3. Clone in Desktop4. Download ZIPReferences 1. Branch 显示当前分支的名称。从这里可以切换仓库内分支&#xff0c;查看其他分支的文件。 2. SSH clone U…

单细胞RNA测序(scRNA-seq)Cellranger流程入门和数据质控

单细胞RNA测序(scRNA-seq)Cellranger流程入门和数据质控 单细胞RNA测序(scRNA-seq)基础知识可查看以下文章: 单细胞RNA测序(scRNA-seq)工作流程入门 单细胞RNA测序(scRNA-seq)细胞分离与扩增 1. 单细胞RNA-seq样本数据说明 样本数据来源文章:Acquired cancer re…

Unity TextMeshProUGUI 获取文本尺寸·大小

一般使用ContentSizeFitter组件自动变更大小 API 渲染前 Vector2 GetPreferredValues(string text)Vector2 GetPreferredValues(string text, float width, float height)Vector2 GetPreferredValues(float width, float height) 渲染后 Vector2 GetRenderedValues()Vector…

自动化测试(selenium篇)

这次我们来介绍selenium 我们主要来讲解这几个要点 1.什么是自动化测试 2.什么是selenium 3.为什么来讲selenium 4.selenium的环境搭建 5.selenium的 API 1.什么是自动化测试 自动化测试指软件测试的自动化&#xff0c;在预设状态下运行应用程序或者系统&#xff0c;预设条…

快速掌握缓存技术:学习多个缓存供应商(ehcache,redis,memcached,jetcache,j2cache)

缓存技术 缓存模拟缓存Spring缓存技术第三方缓存技术Ehcache缓存供应Redis缓存memcached缓存&#xff08;国内&#xff09; jetcache缓存供应商jetcache的基本使用设置外部服务设置本地服务 jetcache方法缓存j2cache 缓存 什么是缓存 缓存是一种介于数据永久存储介质与数据应用…