PythonシミュレーションログインTaobao

インターネット上にはシミュレートされたログインTaobaoがたくさんあるのを見ましたが、基本的にはスクレイプ、ピペティア、セレンなどのライブラリを使用してログインをシミュレートしますが、これらのライブラリについてはまだ説明していません。リクエストライブラリについてのみ説明します。ライブラリシミュレーションログインタオバオ!

Taobaoへのシミュレートされたログインについて説明する前に、リクエストライブラリを使用してDoubanとSina Weiboへのログインをシミュレートする以前のプロセスを確認しましょう。このタイプのシミュレートされたログインは比較的単純なログインです。ログインをリクエストするときに、ユーザー名とパスワードをアップロードするだけで済みます。 、つまり、ワンステップで!

Taobaoのログインはもっと複雑ですが、なぜ複雑なのですか?Taobaoログインには多くのパラメータとリクエストが複数回含まれるためです!まず、Taobaoのログインプロセスについて説明し、最初にプロセスの原則を理解してから、コードを入力して、誰もが簡単に理解できるようにします。

1.タオバオのログインプロセス

Taobao uaパラメーター:ua(User-Agent)、つまりユーザーエージェントという名前のTaobaoのuaパラメーターは、ブラウザー、IP、コンピューター、時間などの情報を追加し、暗号化して生成し、ログインだけでなく多くの場所で使用します。

上の図は、より詳細なフローチャートです。コードレベルを考慮して、Taobaoへのシミュレートされたログインは次の4つのステップに分けられます。

ユーザー名を入力すると、ブラウザはTaobao(taobao.com)への投稿リクエストを開始して、スライダーの検証があるかどうかを判断します。
ユーザーがパスワードを入力すると、ブラウザーはTaobao(taobao.com)への別の投稿要求を開始して、ユーザー名とパスワードが正しいかどうかを確認し、正しい場合はトークンを返します。
ブラウザはトークンをAlibaba(alibaba.com)に渡して、stコードを交換します。
ブラウザがstコードを取得した後、stコードを取得してCookieを取得します。ログインが成功した後、
一部の学生は質問をする場合があります。Taobao(taobao.com)の検証に合格した後、トークンをAlibaba(alibaba.com)とstコードと交換する必要があるのはなぜですか。何?これについては後で話します!
次に、シミュレートされたログインの実装。
上記では、おおよそのログインプロセスについてのみ説明しました。ここでは、Brother Pigが最初に操作の各ステップを詳細に説明し、次に実装コードを投稿します。

1.確認コードが必要かどうかを判断します。
現在、タオバオにログインすると、スライダー確認コードが表示されない場合がほとんどです。ブラザーピッグのログインとログアウトは何度も試行され、途中で1回しか表示されませんでした。コントロールにはスライダー検証コードが必要ですか?

上の図からわかるように、ブラザーピッグがユーザー名(携帯電話番号である必要があります)を入力すると、ブラウザーはスライダー検証コードが必要かどうかを確認するための投稿リクエストを開始します。trueを返すと、スライダー確認コードが表示されます。 !それ以外の場合は表示されません。通常は表示されません。

この図では、この投稿リクエストで2つのパラメーターがアップロードされたことがわかります:usernameとua!

以前、ブラザーピッグは、uaがブラウザー、IP、デバイス情報などの複数の情報のパラメーターを暗号化すると述べたため、ブラザーピッグは、アカウントの観点からだけでなく、IPと機器の観点からもTaobaoの検証コードが表示されるかどうかを推測しました。

例:デバイスに多数のアカウントがログインしている可能性があります。このとき、Taobaoはuaパラメーターからデバイス番号を取得して、デバイスを制限できます。

2.ユーザー名とパスワードを確認します

ここでのステ​​ップは、上記のシーケンス図の5番目のステップです。ログインの要求です。ここでは、ユーザー名、uaパラメーター、暗号化されたパスワードなど、30を超えるパラメーターが検証のためにTaobao(taobao.com)に送信されます。コードを使って実装しましょう。たくさんのパラメータに怖がらないでください。すべてブラウザからコピーされます。

アプリケーションのstコードリンクの後ろにトークンがあることがわかります。後で特定のトークンを分析します。

3.stコードを申請する

上記のTaobao(taobao.com)のトークンはすでに申請済みです。この手順では、トークンをstコードに交換します。

ここの多くの人々は質問をするかもしれません:なぜタオバオにログインするのがとても面倒なのですか?taobao.comに直接ログインできますか?最初にTaobaoでユーザー名とパスワードを確認してから、alibaba.comにアクセスしてstコードログインと交換する必要があるのはなぜですか?

どの会社のフレームワークもゆっくりとした進化の結果です。最初のTaobaoログインは確かにそれほど複雑ではないと思います。しかし、Alibabaの成長に伴い、多くのビジネスラインが分割されましたが、これらのビジネスラインは関連しています。たとえば、ユーザーがTaobaoアカウントにログインした後、Tmallはログインする必要がなくなりますか?(TaobaoとTmallはトップレベルのドメイン名が異なるため、cookisを共有できないことに注意してください。)この問題を解決するために、シングルサインオンが表示されます。

シングルサインオン(シングルサインオン)は、略してSSOと呼ばれ、エンタープライズビジネス統合で最も一般的なソリューションの1つです。SSOの定義は、複数のアプリケーションシステムでは、ユーザーは一度ログインするだけで、相互に信頼できるすべてのアプリケーションシステムにアクセスできるということです。-バイドゥ百科事典

ほとんどの大企業がシングルサインオンを実行し、Aliのシングルサインオンシステムは親会社のAlibaba(alibaba.com)が実行する必要があり、すべての子会社が親会社のインターフェイスを呼び出します。

Taobaoのログインが非常に複雑な理由を分析してみましょう。ユーザーデータはここTaobaoにあるため、Taobao(taobao.com)は今すぐユーザー名とパスワードを確認する必要があります。確認するとトークンが生成され、ブラウザはトークンを保持してAliに連絡します。 Baba(alibaba.com)はシングルサインオンコード(stコード)を申請し、Alibabaはトークンの検証要求を受信した後にstコードを返すため、トークンを使用してstコードを変更する理由はシングルサインオンです!

設計原理を理解した後、コードの実装は非常に明確です!


4.stコードでログインします

stコードを正常に取得したら、ログインできます。この手順では、stコードを使用してログインCookieを取得します。

この時点で、Taobaoへのログインのシミュレーションに成功しました。

5.タオバオのニックネームを取得する

実際、上記では、Taobaoに正常にログインし、ユーザーホームページのリンクに戻りました。ログインが成功したことをさらに確認するために、Taobaoユーザーホームページをリクエストし、Taobaoのニックネームを抽出します。

3、まとめ

全体的なプレゼンテーションの後で、主に2つの側面からそれを少し要約しましょう:コード構造と既存の問題:

1.コード構造

誰もが直感的に理解できるようにコード構造図を公開する

これらは、前述のTaobaoへのシミュレートされたログインの4つのステップですが、ここではコードを使用して実装しました。

2.問題があります

このチュートリアルを書く前に、インターネットでそれについて学び、ブラウザとパケットキャプチャツール(Charles)を使用して段階的に練習する必要があります。最も重要なことは、最初にTaobaoログインの一般的なフローを理解する必要があることです。そうしないと、実際の操作で混乱します。水、現在の問題と既存の問題について話しましょう。

まず、最初の問題はタオバオのスライダーのロック解除です。現在、リクエストをクラックする良い方法はありません。いくつかのクローラーフレームワークを導入した後、それをクラックしましょう!
ブラザーピッグは何度も(50回以上)ログインとログアウトを試みましたが、スライダー検証コードが表示されませんでした。
インターネットでプロキシIPを使用する人もいますが、ここではブラザーピッグは役に立ちません。あなたが超超頻繁で大量のデータをクロールしない限り、一般的に大規模なメーカーは、誤った傷害率があり、ユーザーの影響が広すぎるため、IPをブロックする可能性はありません。閉鎖はコミュニティ全体です。
ユーザー名とパスワードを確認する2番目のステップでは、30近くのパラメーターがアップロードされました。ユーザー名、ua、暗号化されたパスワードを確認にコピーすると、これらの30のパラメーターをブラウザーに置き換えることができます。
3番目と4番目のステップでエラーが発生することがあります。もう一度やり直してください。
ここを見ると、タオバオのシミュレートされたログインがはるかに明確であり、興味のある学生はそれらをブックマークして転送し、週末に試すことができると思います。Taobaoログインを征服し、他のログインは比較的簡単です!

以下はソースコードです

# -*- coding:utf-8 -*-
import re
import os
import json
import requests


s = requests.Session()
# cookies序列化文件
COOKIES_FILE_PATH = 'taobao_login_cookies.txt'


class UsernameLogin:

    def __init__(self, username, ua, TPL_password2):
        """
        账号登录对象
        :param username: 用户名
        :param ua: 淘宝的ua参数
        :param TPL_password2: 加密后的密码
        """
        # 检测是否需要验证码的URL
        self.user_check_url = 'https://login.taobao.com/member/request_nick_check.do?_input_charset=utf-8'
        # 验证淘宝用户名密码URL
        self.verify_password_url = "https://login.taobao.com/member/login.jhtml"
        # 访问st码URL
        self.vst_url = 'https://login.taobao.com/member/vst.htm?st={}'
        # 淘宝个人 主页
        self.my_taobao_url = 'https://i.taobao.com/my_taobao.htm'

        # 淘宝用户名
        self.username = "手机号"
        # 淘宝关键参数,包含用户浏览器等一些信息,很多地方会使用,从浏览器或抓包工具中复制,可重复使用
        self.ua = ""
        # 加密后的密码,从浏览器或抓包工具中复制,可重复使用
        self.TPL_password2 = ""

        # 请求超时时间
        self.timeout = 3

    def _user_check(self):
        """
        检测账号是否需要验证码
        :return:
        """
        data = {
            'username': self.username,
            'ua': self.ua
        }
        try:
            response = s.post(self.user_check_url, data=data, timeout=self.timeout)
            response.raise_for_status()
        except Exception as e:
            print('检测是否需要验证码请求失败,原因:')
            raise e
        needcode = response.json()['needcode']
        print('是否需要滑块验证:{}'.format(needcode))
        return needcode

    def _verify_password(self):
        """
        验证用户名密码,并获取st码申请URL
        :return: 验证成功返回st码申请地址
        """
        verify_password_headers = {
redirectURL=https%3A%2F%2Fi.taobao.com%2Fmy_taobao.htm%3Fspm%3Da2d00.7723416.754894437.1.61531fc917M0p9%26ad_id%3D%26am_id%3D%26cm_id%3D%26pm_id%3D1501036000a02c5c3739',
            # ':scheme': 'https',
            'accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3',
            'accept-encoding': 'gzip, deflate, br',
            'accept-language': 'zh-CN,zh;q=0.9',
            'cache-control': 'max-age=0',
            'content-length': '2858',
            'content-type': 'application/x-www-form-urlencoded',
            'sec-fetch-mode': 'navigate',
            'sec-fetch-site': 'same-origin',
            'sec-fetch-user': '?1',
            'Cache-Control': 'max-age=0',
            'Origin': 'https://login.taobao.com',
            'Upgrade-Insecure-Requests': '1',
            'User-Agent': '5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.70 Safari/537.36',
            'Content-Type': 'application/x-www-form-urlencoded',
            'Referer': 'https://login.taobao.com/member/login.jhtml?redirectURL=https%3A%2F%2Fi.taobao.com%2Fmy_taobao.htm%3Fspm%3Da2d00.7723416.754894437.1.61531fc917M0p9%26ad_id%3D%26am_id%3D%26cm_id%3D%26pm_id%3D1501036000a02c5c3739',
        }
        # 登录toabao.com提交的数据,如果登录失败,可以从浏览器复制你的form data
        verify_password_data = {
            'TPL_username': self.username,
            'ncoToken': '1f1389fac2a670101d8a09de4c99795e8023b341',
            'slideCodeShow': 'false',
            'useMobile': 'false',
            'lang': 'zh_CN',
            'loginsite': 0,
            'newlogin': 0,
            'TPL_redirect_url': 'https://i.taobao.com/my_taobao.htm?spm=a2d00.7723416.754894437.1.61531fc917M0p9&ad_id=&am_id=&cm_id=&pm_id=1501036000a02c5c3739',
            'from': 'tb',
            'fc': 'default',
            'style': 'default',
            'keyLogin': 'false',
            'qrLogin': 'true',
            'newMini': 'false',
            'newMini2': 'false',
            'loginType': '3',
            'gvfdcname': '10',
            # 'gvfdcre': '68747470733A2F2F6C6F67696E2E74616F62616F2E636F6D2F6D656D6265722F6C6F676F75742E6A68746D6C3F73706D3D613231626F2E323031372E3735343839343433372E372E356166393131643970714B52693126663D746F70266F75743D7472756526726564697265637455524C3D68747470732533412532462532467777772E74616F62616F2E636F6D253246',
            'TPL_password_2': self.TPL_password2,
            'loginASR': '1',
            'loginASRSuc': '1',
            'oslanguage': 'zh-CN',
            'sr': '1920*1080',
            # 'osVer': 'macos|10.145',
            'naviVer': 'chrome|78.039047',
            'osACN': 'Mozilla',
            'osAV': '5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.70 Safari/537.36',
            'osPF': 'Win32',
            'appkey': '00000000',
            'mobileLoginLink': 'https://login.taobao.com/member/login.jhtml?redirectURL=https://i.taobao.com/my_taobao.htm?spm=a2d00.7723416.754894437.1.61531fc917M0p9&ad_id=&am_id=&cm_id=&pm_id=1501036000a02c5c3739&useMobile=true',
            'showAssistantLink': 'false',
            'um_token': 'T274D86E0BEB4F2F2F527C889BADD92868CE10177BeFF895DE627CFE2D52A',
            'ua': self.ua
        }
        try:
            response = s.post(self.verify_password_url, headers=verify_password_headers, data=verify_password_data,
                              timeout=self.timeout)
            response.raise_for_status()
            # 从返回的页面中提取申请st码地址
        except Exception as e:
            print('验证用户名和密码请求失败,原因:')
            raise e
        # 提取申请st码url
        apply_st_url_match = re.search(r'<script src="(.*?)"></script>', response.text)
        # 存在则返回
        if apply_st_url_match:
            print('验证用户名密码成功,st码申请地址:{}'.format(apply_st_url_match.group(1)))
            return apply_st_url_match.group(1)
        else:
            raise RuntimeError('用户名密码验证失败!response:{}'.format(response.text))

    def _apply_st(self):
        """
        申请st码
        :return: st码
        """
        apply_st_url = self._verify_password()
        try:
            response = s.get(apply_st_url)
            # response.raise_for_status()
        except Exception as e:
            print('申请st码请求失败,原因:')
            raise e
        st_match = re.search(r'"data":{"st":"(.*?)"}', response.text)
        if st_match:
            print('获取st码成功,st码:{}'.format(st_match.group(1)))
            return st_match.group(1)
        else:
            raise RuntimeError('获取st码失败!response:{}'.format(response.text))
            # raise RuntimeError('获取st码失败!')

    def login(self):
        """
        使用st码登录
        :return:
        """
        # 加载cookies文件
        if self._load_cookies():
            return True
        # 判断是否需要滑块验证
        self._user_check()
        st = self._apply_st()
        headers = {
            'Host': 'login.taobao.com',
            'Connection': 'Keep-Alive',
            'User-Agent': '5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.70 Safari/537.36'
        }
        try:
            response = s.get(self.vst_url.format(st), headers=headers)
            response.raise_for_status()
        except Exception as e:
            print('st码登录请求,原因:')
            raise e
        # 登录成功,提取跳转淘宝用户主页url
        my_taobao_match = re.search(r'top.location.href = "(.*?)"', response.text)
        if my_taobao_match:
            print('登录淘宝成功,跳转链接:{}'.format(my_taobao_match.group(1)))
            self._serialization_cookies()
            return True
        else:
            raise RuntimeError('登录失败!response:{}'.format(response.text))

    def _load_cookies(self):
        # 1、判断cookies序列化文件是否存在
        if not os.path.exists(COOKIES_FILE_PATH):
            return False
        # 2、加载cookies
        s.cookies = self._deserialization_cookies()
        # 3、判断cookies是否过期
        try:
            self.get_taobao_nick_name()
        except Exception as e:
            os.remove(COOKIES_FILE_PATH)
            print('cookies过期,删除cookies文件!')
            return False
        print('加载淘宝登录cookies成功!!!')
        return True

    def _serialization_cookies(self):
        """
        序列化cookies
        :return:
        """
        cookies_dict = requests.utils.dict_from_cookiejar(s.cookies)
        with open(COOKIES_FILE_PATH, 'w+', encoding='utf-8') as file:
            json.dump(cookies_dict, file)
            print('保存cookies文件成功!')

    def _deserialization_cookies(self):
        """
        反序列化cookies
        :return:
        """
        with open(COOKIES_FILE_PATH, 'r+', encoding='utf-8') as file:
            cookies_dict = json.load(file)
            cookies = requests.utils.cookiejar_from_dict(cookies_dict)
            return cookies

    def get_taobao_nick_name(self):
        """
        获取淘宝昵称
        :return: 淘宝昵称
        """
        headers = {
            'User-Agent': '5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/78.0.3904.70 Safari/537.36'
        }
        try:
            response = s.get(self.my_taobao_url, headers=headers)
            response.raise_for_status()
        except Exception as e:
            print('获取淘宝主页请求失败!原因:')
            raise e
        # 提取淘宝昵称
        nick_name_match = re.search(r'<input id="mtb-nickname" type="hidden" value="(.*?)"/>', response.text)
        if nick_name_match:
            print('登录淘宝成功,你的用户名是:{}'.format(nick_name_match.group(1)))
            return nick_name_match.group(1)
        else:
            raise RuntimeError('获取淘宝昵称失败!response:{}'.format(response.text))


if __name__ == '__main__':
    # 淘宝用户名
    username = '手机号'
    # 淘宝重要参数,从浏览器或抓包工具中复制,可重复使用
    ua = ''
    # 加密后的密码,从浏览器或抓包工具中复制,可重复使用
    TPL_password2 = ''
    ul = UsernameLogin(username, ua, TPL_password2)
    ul.login()

 

おすすめ

転載: blog.csdn.net/weixin_43407092/article/details/102975955