mirror of
https://github.com/lkeme/BiliHelper-personal.git
synced 2025-12-19 09:30:10 +08:00
[update] Login Closes #37
This commit is contained in:
parent
3c73415e31
commit
a03877ea9e
@ -1,7 +1,7 @@
|
||||
# Release Notes
|
||||
# 本项目Log
|
||||
|
||||
## v0.5.0.200624 alpha (2020-06-24)
|
||||
## v0.5.0.200625 alpha (2020-06-25)
|
||||
|
||||
### Added
|
||||
- 添加破产机(赔到破产)
|
||||
@ -19,6 +19,7 @@
|
||||
- 更新视频投币逻辑
|
||||
- 更新实物抽奖API
|
||||
- 修改硬币兑换延迟
|
||||
- 重构部分登录逻辑
|
||||
-
|
||||
|
||||
### Fixed
|
||||
@ -92,7 +93,7 @@
|
||||
|
||||
### Changed
|
||||
- 优化监控推送
|
||||
- 优化登陆参数
|
||||
- 优化登录参数
|
||||
- 同步黑屋提醒
|
||||
|
||||
### Fixed
|
||||
@ -207,7 +208,7 @@
|
||||
-
|
||||
|
||||
### Fixed
|
||||
- 修复登陆繁忙
|
||||
- 修复登录繁忙
|
||||
- 修复实物抽奖
|
||||
- 修复日志输出
|
||||
- 修复部分已知
|
||||
|
||||
4
DOC.md
4
DOC.md
@ -2,7 +2,7 @@
|
||||
<p align="center"><img width="300px" src="https://i.loli.net/2018/04/20/5ad97bd395912.jpeg"></p>
|
||||
|
||||
<p align="center">
|
||||
<img src="https://img.shields.io/badge/version-0.5.0.200624 alpha-green.svg?longCache=true&style=for-the-badge">
|
||||
<img src="https://img.shields.io/badge/version-0.5.0.200625 alpha-green.svg?longCache=true&style=for-the-badge">
|
||||
<img src="https://img.shields.io/badge/license-mit-blue.svg?longCache=true&style=for-the-badge">
|
||||
</p>
|
||||
|
||||
@ -127,7 +127,7 @@ $ php index.php
|
||||
- 通过环境变量进行传入
|
||||
|
||||
```shell script
|
||||
docker run -itd --rm -e USER_NAME=你的B站登陆账号 -e USER_PASSWORD=你的B站密码 zsnmwy/bilihelper-personal
|
||||
docker run -itd --rm -e USER_NAME=你的B站登录账号 -e USER_PASSWORD=你的B站密码 zsnmwy/bilihelper-personal
|
||||
```
|
||||
|
||||
- 通过配置文件进行传入
|
||||
|
||||
@ -7,7 +7,7 @@ Group: [55308141](https://jq.qq.com/?_wv=1027&k=5AIDaJg) | **仅用于BUG提交
|
||||
|
||||
## 公告
|
||||
|
||||
> Currently for Personal Edition **0.5.0.200624 alpha**
|
||||
> Currently for Personal Edition **0.5.0.200625 alpha**
|
||||
|
||||
```notice
|
||||
---- 免费的东西总是得不到人的珍惜。
|
||||
|
||||
@ -6,6 +6,9 @@
|
||||
APP_USER=
|
||||
APP_PASS=
|
||||
|
||||
# 登录模式|[1.账密模式 2.短信验证码模式 3.行为验证码模式(暂未开放)]
|
||||
LOGIN_MODE=1
|
||||
|
||||
# 令牌(自动生成)
|
||||
ACCESS_TOKEN=
|
||||
REFRESH_TOKEN=
|
||||
|
||||
@ -233,7 +233,8 @@ class Curl
|
||||
'Accept-Language' => 'zh-cn',
|
||||
'Connection' => 'keep-alive',
|
||||
// 'Content-Type' => 'application/x-www-form-urlencoded',
|
||||
'User-Agent' => 'Mozilla/5.0 BiliDroid/5.51.1 (bbcallen@gmail.com)',
|
||||
// 'User-Agent' => 'Mozilla/5.0 BiliDroid/5.51.1 (bbcallen@gmail.com)',
|
||||
'User-Agent' => 'Mozilla/5.0 BiliDroid/6.3.0 (bbcallen@gmail.com) os/android model/MuMu mobi_app/android build/6030600 channel/bili innerVer/6030600 osVer/6.0.1 network/2',
|
||||
// 'Referer' => 'https://live.bilibili.com/',
|
||||
];
|
||||
$pc_headers = [
|
||||
|
||||
@ -30,7 +30,7 @@ class GiftSend
|
||||
|
||||
public static function run()
|
||||
{
|
||||
if (self::getLock() > time()) {
|
||||
if (self::getLock() > time() || !self::inTime('23:50:00', '23:59:50')) {
|
||||
return;
|
||||
}
|
||||
if (!self::$uid) {
|
||||
@ -44,8 +44,8 @@ class GiftSend
|
||||
self::$medal_list = [];
|
||||
self::$tid = 0;
|
||||
// 如果在每日最后5分钟内 就50s执行一次 否则 第二天固定时间执行
|
||||
if (self::inTime('23:55:00', '23:59:59')) {
|
||||
self::setLock(50);
|
||||
if (self::inTime('23:52:00', '23:59:59')) {
|
||||
self::setLock(60);
|
||||
} else {
|
||||
self::setLock(self::timing(23, 55));
|
||||
}
|
||||
|
||||
@ -19,46 +19,95 @@ class Login
|
||||
{
|
||||
use TimeLock;
|
||||
|
||||
// 账密
|
||||
private static $username;
|
||||
private static $password;
|
||||
|
||||
public static function run()
|
||||
{
|
||||
if (self::getLock()) {
|
||||
self::check();
|
||||
self::keepAuth();
|
||||
return;
|
||||
}
|
||||
Log::info('开始启动程序...');
|
||||
Log::info('启动登录程序');
|
||||
if (getenv('ACCESS_TOKEN') == "") {
|
||||
Log::info('令牌载入中...');
|
||||
Log::info('准备载入登录令牌');
|
||||
self::login();
|
||||
}
|
||||
|
||||
Log::info('正在检查令牌合法性...');
|
||||
if (!self::info()) {
|
||||
Log::warning('令牌即将过期');
|
||||
Log::info('申请更换令牌中...');
|
||||
if (!self::refresh()) {
|
||||
Log::warning('无效令牌,正在重新申请...');
|
||||
Log::info('检查登录令牌有效性');
|
||||
if (!self::checkToken()) {
|
||||
Log::warning('登录令牌即将过期');
|
||||
Log::info('申请更换登录令牌中');
|
||||
if (!self::refreshToken()) {
|
||||
Log::warning('无效的登录令牌,尝试重新申请');
|
||||
self::login();
|
||||
}
|
||||
}
|
||||
self::setLock(3600);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 检查令牌
|
||||
* @use 登录控制中心
|
||||
*/
|
||||
private static function login()
|
||||
{
|
||||
self::checkLogin();
|
||||
switch (intval(getenv('LOGIN_MODE'))) {
|
||||
case 1:
|
||||
// 账密模式
|
||||
self::accountLogin();
|
||||
break;
|
||||
case 2:
|
||||
// 短信验证码模式
|
||||
self::smsLogin();
|
||||
break;
|
||||
case 3:
|
||||
// 行为验证码模式(暂未开放)
|
||||
// self::captchaLogin();
|
||||
Log::error('此登录模式暂未开放');
|
||||
die();
|
||||
break;
|
||||
default:
|
||||
Log::error('登录模式配置错误');
|
||||
die();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 检查登录
|
||||
*/
|
||||
private static function checkLogin()
|
||||
{
|
||||
$user = getenv('APP_USER');
|
||||
$pass = getenv('APP_PASS');
|
||||
if (empty($user) || empty($pass)) {
|
||||
Log::error('空白的帐号和口令');
|
||||
die();
|
||||
}
|
||||
self::clearAccount();
|
||||
self::$username = $user;
|
||||
self::$password = self::publicKeyEnc($pass);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 保持认证
|
||||
* @return bool
|
||||
*/
|
||||
public static function check()
|
||||
private static function keepAuth()
|
||||
{
|
||||
if (self::getLock() > time()) {
|
||||
return true;
|
||||
}
|
||||
self::setLock(7200);
|
||||
if (!self::info()) {
|
||||
if (!self::checkToken()) {
|
||||
Log::warning('令牌即将过期');
|
||||
Log::info('申请更换令牌中...');
|
||||
if (!self::refresh()) {
|
||||
if (!self::refreshToken()) {
|
||||
Log::warning('无效令牌,正在重新申请...');
|
||||
self::login();
|
||||
self::accountLogin();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
@ -69,7 +118,7 @@ class Login
|
||||
* @use 获取令牌信息
|
||||
* @return bool
|
||||
*/
|
||||
protected static function info()
|
||||
private static function checkToken()
|
||||
{
|
||||
$url = 'https://passport.bilibili.com/api/v2/oauth2/info';
|
||||
$payload = [
|
||||
@ -85,165 +134,46 @@ class Login
|
||||
return $data['data']['expires_in'] > 14400;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 刷新token
|
||||
* @return bool
|
||||
* @use 刷新Token
|
||||
*/
|
||||
public static function refresh()
|
||||
private static function refreshToken()
|
||||
{
|
||||
$url = 'https://passport.bilibili.com/api/oauth2/refreshToken';
|
||||
$url = 'https://passport.bilibili.com/api/v2/oauth2/refresh_token';
|
||||
$payload = [
|
||||
'access_token' => getenv('ACCESS_TOKEN'),
|
||||
'refresh_token' => getenv('REFRESH_TOKEN'),
|
||||
];
|
||||
$data = Curl::post('app', $url, Sign::common($payload));
|
||||
$data = json_decode($data, true);
|
||||
$raw = Curl::post('app', $url, Sign::common($payload));
|
||||
$de_raw = json_decode($raw, true);
|
||||
if (isset($data['code']) && $data['code']) {
|
||||
Log::error('重新生成令牌失败', ['msg' => $data['message']]);
|
||||
return false;
|
||||
}
|
||||
Log::info('令牌生成完毕!');
|
||||
$access_token = $data['data']['access_token'];
|
||||
Config::put('ACCESS_TOKEN', $access_token);
|
||||
Log::info(" > access token: {$access_token}");
|
||||
$refresh_token = $data['data']['refresh_token'];
|
||||
Config::put('REFRESH_TOKEN', $refresh_token);
|
||||
Log::info(" > refresh token: {$refresh_token}");
|
||||
if (!self::saveCookie()) {
|
||||
self::clearAccount();
|
||||
die();
|
||||
};
|
||||
Log::info('重新令牌生成完毕');
|
||||
$access_token = $de_raw['data']['token_info']['access_token'];
|
||||
$refresh_token = $de_raw['data']['token_info']['refresh_token'];
|
||||
self::saveConfig('ACCESS_TOKEN', $access_token);
|
||||
self::saveConfig('REFRESH_TOKEN', $refresh_token);
|
||||
self::saveCookie($de_raw);
|
||||
Log::info('重置信息配置完毕');
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 普通登陆
|
||||
* @param string $captcha
|
||||
* @param array $headers
|
||||
* @use 检查Cookie
|
||||
*/
|
||||
protected static function login($captcha = '', $headers = [])
|
||||
private static function checkCookie()
|
||||
{
|
||||
$user = getenv('APP_USER');
|
||||
$pass = getenv('APP_PASS');
|
||||
if (empty($user) || empty($pass)) {
|
||||
Log::error('空白的帐号和口令!');
|
||||
die();
|
||||
}
|
||||
self::clearAccount();
|
||||
// get PublicKey
|
||||
Log::info('正在载入安全模块...');
|
||||
$url = 'https://passport.snm0516.aisee.tv/api/oauth2/getKey';
|
||||
$payload = [];
|
||||
$data = Curl::post('app', $url, Sign::login($payload));
|
||||
$data = json_decode($data, true);
|
||||
if (isset($data['code']) && $data['code']) {
|
||||
Log::error('公钥获取失败', ['msg' => $data['message']]);
|
||||
die();
|
||||
} else {
|
||||
Log::info('安全模块载入完毕!');
|
||||
}
|
||||
$public_key = $data['data']['key'];
|
||||
$hash = $data['data']['hash'];
|
||||
openssl_public_encrypt($hash . $pass, $crypt, $public_key);
|
||||
for ($i = 0; $i < 30; $i++) {
|
||||
// login
|
||||
Log::info('正在获取令牌...');
|
||||
$url = 'https://passport.snm0516.aisee.tv/api/tv/login';
|
||||
$payload = [
|
||||
'channel' => 'master',
|
||||
'token' => '5598158bcd8511e9',
|
||||
'guid' => 'XYEBAA3E54D502E73BD606F0589A356902FCF',
|
||||
'username' => $user,
|
||||
'password' => base64_encode($crypt),
|
||||
'captcha' => $captcha,
|
||||
];
|
||||
$data = Curl::post('app', $url, Sign::login($payload), $headers);
|
||||
$data = json_decode($data, true);
|
||||
if (isset($data['code']) && $data['code'] == -105) {
|
||||
$captcha_data = self::loginWithCaptcha();
|
||||
$captcha = $captcha_data['captcha'];
|
||||
$headers = $captcha_data['headers'];
|
||||
continue;
|
||||
}
|
||||
// https://passport.bilibili.com/mobile/verifytel_h5.html
|
||||
if ($data['code'] == -2100) {
|
||||
Log::error('登录失败', ['msg' => '登录异常, 账号启用了设备锁或异地登录需验证手机!']);
|
||||
die();
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (isset($data['code']) && $data['code']) {
|
||||
Log::error('登录失败', ['msg' => $data['message']]);
|
||||
die();
|
||||
}
|
||||
Log::info('令牌获取成功!');
|
||||
$access_token = $data['data']['token_info']['access_token'];
|
||||
Config::put('ACCESS_TOKEN', $access_token);
|
||||
Log::info(" > access token: {$access_token}");
|
||||
$refresh_token = $data['data']['token_info']['refresh_token'];
|
||||
Config::put('REFRESH_TOKEN', $refresh_token);
|
||||
Log::info(" > refresh token: {$refresh_token}");
|
||||
if (!self::saveCookie()) {
|
||||
self::clearAccount();
|
||||
die();
|
||||
};
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 验证码登陆
|
||||
* @return array
|
||||
* @use 刷新Cookie
|
||||
*/
|
||||
protected static function loginWithCaptcha()
|
||||
{
|
||||
Log::info('登录需要验证, 启动验证码登录!');
|
||||
$url = 'https://passport.snm0516.aisee.tv/api/captcha';
|
||||
$payload = [
|
||||
'token' => '5598158bcd8511e9'
|
||||
];
|
||||
$headers = [
|
||||
'Accept' => 'application/json, text/plain, */*',
|
||||
'Host' => 'passport.snm0516.aisee.tv',
|
||||
'Cookie' => 'sid=blhelper'
|
||||
];
|
||||
$data = Curl::get('other', $url, $payload, $headers);
|
||||
$data = base64_encode($data);
|
||||
$captcha = self::ocrCaptcha($data);
|
||||
return [
|
||||
'captcha' => $captcha,
|
||||
'headers' => $headers,
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 识别验证码
|
||||
* @param $captcha_img
|
||||
* @return mixed
|
||||
*/
|
||||
private static function ocrCaptcha($captcha_img)
|
||||
{
|
||||
// $url = 'http://captcha-v1.mudew.com:19951/';
|
||||
$url = 'http://47.102.120.84:19951/';
|
||||
$payload = [
|
||||
'image' => (string)$captcha_img
|
||||
];
|
||||
$headers = [
|
||||
'Content-Type' => 'application/json',
|
||||
];
|
||||
$data = Curl::put('other', $url, $payload, $headers);
|
||||
$de_raw = json_decode($data, true);
|
||||
Log::info("验证码识别结果 {$de_raw['message']}");
|
||||
return $de_raw['message'];
|
||||
}
|
||||
|
||||
/**
|
||||
* @use token转cookie
|
||||
* @return string
|
||||
*/
|
||||
private static function token2cookie(): string
|
||||
private static function refreshCookie()
|
||||
{
|
||||
$url = 'https://passport.bilibili.com/api/login/sso';
|
||||
$payload = [
|
||||
@ -261,20 +191,286 @@ class Login
|
||||
|
||||
|
||||
/**
|
||||
* @use 保存cookie
|
||||
* @return bool
|
||||
* @use 公钥加密
|
||||
* @param $plaintext
|
||||
* @return string
|
||||
*/
|
||||
private static function saveCookie(): bool
|
||||
private static function publicKeyEnc($plaintext): string
|
||||
{
|
||||
$cookies = self::token2cookie();
|
||||
if ($cookies == '') {
|
||||
Log::error("COOKIE获取失败 {$cookies}");
|
||||
return false;
|
||||
Log::info('正在载入公钥');
|
||||
$url = 'https://passport.bilibili.com/api/oauth2/getKey';
|
||||
$payload = [];
|
||||
$data = Curl::post('app', $url, Sign::login($payload));
|
||||
$data = json_decode($data, true);
|
||||
if (isset($data['code']) && $data['code']) {
|
||||
Log::error('公钥载入失败', ['msg' => $data['message']]);
|
||||
die();
|
||||
} else {
|
||||
Log::info('公钥载入完毕');
|
||||
}
|
||||
Log::info("COOKIE获取成功 !");
|
||||
Log::info(" > cookie: {$cookies}");
|
||||
Config::put('COOKIE', $cookies);
|
||||
return true;
|
||||
$public_key = $data['data']['key'];
|
||||
$hash = $data['data']['hash'];
|
||||
openssl_public_encrypt($hash . $plaintext, $crypt, $public_key);
|
||||
return base64_encode($crypt);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 获取验证码
|
||||
* @return array|string[]
|
||||
*/
|
||||
private static function getCaptcha(): array
|
||||
{
|
||||
$url = 'https://passport.bilibili.com/web/captcha/combine';
|
||||
$payload = [
|
||||
'plat' => 3
|
||||
];
|
||||
$raw = Curl::get('other', $url, $payload);
|
||||
$de_raw = json_decode($raw, true);
|
||||
// {"code":0,"data":{"result":{"success":1,"gt":"b6e5b7fad7ecd37f465838689732e788","challenge":"88148a764f94e5923564b356a69277fc","key":"230509df5ce048ca9bf29e1ee323af30"},"type":1}}
|
||||
Log::info('正在获取验证码 ' . $de_raw['code']);
|
||||
if ($de_raw['code'] == 0 && isset($de_raw['data']['result'])) {
|
||||
return [
|
||||
'gt' => $de_raw['data']['result']['gt'],
|
||||
'challenge' => $de_raw['data']['result']['challenge'],
|
||||
'key' => $de_raw['data']['result']['key'],
|
||||
];
|
||||
}
|
||||
return [
|
||||
'gt' => '',
|
||||
'challenge' => '',
|
||||
'key' => ''
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 识别验证码
|
||||
* @param array $captcha
|
||||
* @return array
|
||||
*/
|
||||
private static function ocrCaptcha(array $captcha): array
|
||||
{
|
||||
$url = 'http://captcha-v1.mudew.com:19951/';
|
||||
$payload = [
|
||||
'type' => 'gt3',
|
||||
'gt' => $captcha['gt'],
|
||||
"challenge" => $captcha['challenge'],
|
||||
"referer" => "https://passport.bilibili.com/"
|
||||
];
|
||||
$headers = [
|
||||
'Content-Type' => 'application/json',
|
||||
];
|
||||
$data = Curl::post('other', $url, $payload, $headers);
|
||||
$de_raw = json_decode($data, true);
|
||||
Log::info('正在获取验证码 ' . $de_raw['code']);
|
||||
return [
|
||||
'validate' => $de_raw['data']['validate'],
|
||||
'challenge' => $de_raw['data']['challenge']
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @use 验证码登录
|
||||
* @param string $mode
|
||||
*/
|
||||
private static function captchaLogin(string $mode = '验证码模式')
|
||||
{
|
||||
$captcha_ori = self::getCaptcha();
|
||||
$captcha = self::ocrCaptcha($captcha_ori);
|
||||
self::accountLogin($captcha['validate'], $captcha['challenge'], $mode);
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 账密登录
|
||||
* @param string $validate
|
||||
* @param string $challenge
|
||||
* @param string $mode
|
||||
*/
|
||||
private static function accountLogin(string $validate = '', string $challenge = '', string $mode = '账密模式')
|
||||
{
|
||||
Log::info("尝试{$mode}登录");
|
||||
$url = 'https://passport.bilibili.com/api/v3/oauth2/login';
|
||||
$payload = [
|
||||
'seccode' => $validate ? "{$validate}|jordan" : '',
|
||||
'validate' => $validate,
|
||||
'challenge' => $challenge,
|
||||
'subid' => 1,
|
||||
'permission' => 'ALL',
|
||||
'username' => self::$username,
|
||||
'password' => self::$password,
|
||||
'captcha' => '',
|
||||
'cookies' => ''
|
||||
];
|
||||
$raw = Curl::post('app', $url, Sign::login($payload));
|
||||
$de_raw = json_decode($raw, true);
|
||||
// {"ts":1593079322,"code":-629,"message":"账号或者密码错误"}
|
||||
// {"ts":1593082268,"code":-105,"data":{"url":"https://passport.bilibili.com/register/verification.html?success=1>=b6e5b7fad7ecd37f465838689732e788&challenge=7efb4020b22c0a9ac124aea624e11ad7&ct=1&hash=7fa8282ad93047a4d6fe6111c93b308a"},"message":"验证码错误"}
|
||||
// {"ts":1593082432,"code":0,"data":{"status":0,"token_info":{"mid":123456,"access_token":"123123","refresh_token":"123123","expires_in":2592000},"cookie_info":{"cookies":[{"name":"bili_jct","value":"123123","http_only":0,"expires":1595674432},{"name":"DedeUserID","value":"123456","http_only":0,"expires":1595674432},{"name":"DedeUserID__ckMd5","value":"123123","http_only":0,"expires":1595674432},{"name":"sid","value":"bd6aagp7","http_only":0,"expires":1595674432},{"name":"SESSDATA","value":"6d74d850%123%2Cf0e36b61","http_only":1,"expires":1595674432}],"domains":[".bilibili.com",".biligame.com",".bigfunapp.cn"]},"sso":["https://passport.bilibili.com/api/v2/sso","https://passport.biligame.com/api/v2/sso","https://passport.bigfunapp.cn/api/v2/sso"]}}
|
||||
// https://passport.bilibili.com/mobile/verifytel_h5.html
|
||||
switch ($de_raw['code']) {
|
||||
case 0:
|
||||
// 正常登录
|
||||
Log::info("{$mode}登录成功");
|
||||
$access_token = $de_raw['data']['token_info']['access_token'];
|
||||
$refresh_token = $de_raw['data']['token_info']['refresh_token'];
|
||||
self::saveConfig('ACCESS_TOKEN', $access_token);
|
||||
self::saveConfig('REFRESH_TOKEN', $refresh_token);
|
||||
self::saveCookie($de_raw);
|
||||
Log::info('信息配置完毕');
|
||||
break;
|
||||
case -105:
|
||||
// 需要验证码
|
||||
Log::error('登录失败', ['msg' => '此次登录需要验证码或' . $de_raw['message']]);
|
||||
die();
|
||||
break;
|
||||
case -629:
|
||||
// 密码错误
|
||||
Log::error('登录失败', ['msg' => $de_raw['message']]);
|
||||
die();
|
||||
break;
|
||||
case -2100:
|
||||
// 验证手机号
|
||||
Log::error('登录失败', ['msg' => '账号启用了设备锁或异地登录需验证手机号']);
|
||||
die();
|
||||
break;
|
||||
default:
|
||||
Log::error('登录失败', ['msg' => '未知错误: ' . $de_raw['message']]);
|
||||
die();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 短信登录
|
||||
* @param string $mode
|
||||
*/
|
||||
private static function smsLogin(string $mode = '短信模式')
|
||||
{
|
||||
Log::info("尝试{$mode}登录");
|
||||
self::checkPhone(self::$username);
|
||||
$captcha = self::sendSms(self::$username);
|
||||
$url = 'https://passport.bilibili.com/x/passport-login/login/sms';
|
||||
$payload = [
|
||||
'captcha_key' => $captcha['captcha_key'],
|
||||
'cid' => $captcha['cid'],
|
||||
'tel' => $captcha['tel'],
|
||||
'statistics' => $captcha['statistics'],
|
||||
'code' => self::cliInput('请输入收到的短信验证码: '),
|
||||
];
|
||||
$raw = Curl::post('app', $url, Sign::login($payload));
|
||||
$de_raw = json_decode($raw, true);
|
||||
switch ($de_raw['code']) {
|
||||
case 0:
|
||||
// 正常登录
|
||||
Log::info("{$mode}登录成功");
|
||||
$access_token = $de_raw['data']['token_info']['access_token'];
|
||||
$refresh_token = $de_raw['data']['token_info']['refresh_token'];
|
||||
self::saveConfig('ACCESS_TOKEN', $access_token);
|
||||
self::saveConfig('REFRESH_TOKEN', $refresh_token);
|
||||
self::saveCookie($de_raw);
|
||||
Log::info('信息配置完毕');
|
||||
break;
|
||||
case -105:
|
||||
// 需要验证码
|
||||
Log::error('登录失败', ['msg' => '此次登录需要验证码或' . $de_raw['message']]);
|
||||
die();
|
||||
break;
|
||||
case -629:
|
||||
// 密码错误
|
||||
Log::error('登录失败', ['msg' => $de_raw['message']]);
|
||||
die();
|
||||
break;
|
||||
case -2100:
|
||||
// 验证手机号
|
||||
Log::error('登录失败', ['msg' => '账号启用了设备锁或异地登录需验证手机号']);
|
||||
die();
|
||||
break;
|
||||
default:
|
||||
Log::error('登录失败', ['msg' => '未知错误: ' . $de_raw['message']]);
|
||||
die();
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 输入短信验证码
|
||||
* @param string $msg
|
||||
* @param int $max_char
|
||||
* @return string
|
||||
*/
|
||||
private static function cliInput(string $msg, $max_char = 100): string
|
||||
{
|
||||
$stdin = fopen('php://stdin', 'r');
|
||||
echo '# ' . $msg;
|
||||
$input = fread($stdin, $max_char);
|
||||
fclose($stdin);
|
||||
return str_replace(PHP_EOL, '', $input);
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 发送短信验证码
|
||||
* @param string $phone
|
||||
* @return array
|
||||
*/
|
||||
private static function sendSms(string $phone): array
|
||||
{
|
||||
$url = 'https://passport.bilibili.com//x/passport-login/sms/send';
|
||||
$payload = [
|
||||
'cid' => '86',
|
||||
'tel' => $phone,
|
||||
'statistics' => '{"appId":1,"platform":3,"version":"6.3.0","abtest":""}',
|
||||
];
|
||||
$raw = Curl::post('app', $url, Sign::login($payload));
|
||||
$de_raw = json_decode($raw, true);
|
||||
// {"code":0,"message":"0","ttl":1,"data":{"is_new":false,"captcha_key":"4e292933816755442c1568e2043b8e41","recaptcha_url":""}}
|
||||
// {"code":0,"message":"0","ttl":1,"data":{"is_new":false,"captcha_key":"","recaptcha_url":"https://www.bilibili.com/h5/project-msg-auth/verify?ct=geetest\u0026recaptcha_token=ad520c3a4a3c46e29b1974d85efd2c4b\u0026gee_gt=1c0ea7c7d47d8126dda19ee3431a5f38\u0026gee_challenge=c772673050dce482b9f63ff45b681ceb\u0026hash=ea2850a43cc6b4f1f7b925d601098e5e"}}
|
||||
if ($de_raw['code'] == 0 && isset($de_raw['data']['captcha_key']) && $de_raw['data']['recaptcha_url'] == '') {
|
||||
Log::info("短信验证码发送成功 {$de_raw['data']['captcha_key']}");
|
||||
$payload['captcha_key'] = $de_raw['data']['captcha_key'];
|
||||
return $payload;
|
||||
}
|
||||
Log::error("短信验证码发送失败 {$raw}");
|
||||
die();
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 检查手机号格式
|
||||
* @param string $phone
|
||||
*/
|
||||
private static function checkPhone(string $phone)
|
||||
{
|
||||
if (!preg_match("/^1[3456789]{1}\d{9}$/", $phone)) {
|
||||
Log::error("当前用户名不是有效手机号格式");
|
||||
die();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 保存配置
|
||||
* @param string $key
|
||||
* @param string $value
|
||||
* @param bool $hide
|
||||
*/
|
||||
private static function saveConfig(string $key, string $value, $hide = true)
|
||||
{
|
||||
Config::put($key, $value);
|
||||
Log::info(" > {$key}: " . ($hide ? substr_replace($value, '********', mb_strlen($value / 2), 8) : $value));
|
||||
}
|
||||
|
||||
/**
|
||||
* @use 保存配置
|
||||
* @param array $data
|
||||
*/
|
||||
private static function saveCookie(array $data)
|
||||
{
|
||||
$c = '';
|
||||
$cookies = $data['data']['cookie_info']['cookies'];
|
||||
foreach ($cookies as $cookie) {
|
||||
$c .= $cookie['name'] . '=' . $cookie['value'] . ';';
|
||||
}
|
||||
self::saveConfig('COOKIE', $c);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -282,10 +478,11 @@ class Login
|
||||
*/
|
||||
private static function clearAccount()
|
||||
{
|
||||
$accounts = ['ACCESS_TOKEN', 'REFRESH_TOKEN', 'COOKIE'];
|
||||
foreach ($accounts as $account) {
|
||||
Config::put($account, '');
|
||||
$variables = ['ACCESS_TOKEN', 'REFRESH_TOKEN', 'COOKIE'];
|
||||
foreach ($variables as $variable) {
|
||||
Config::put($variable, '');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@ -15,6 +15,31 @@ use BiliHelper\Core\Log;
|
||||
class Sign
|
||||
{
|
||||
|
||||
// /**
|
||||
// * @use 登录
|
||||
// * @param $payload
|
||||
// * @return array
|
||||
// */
|
||||
// public static function login($payload)
|
||||
// {
|
||||
// # 云视听 TV
|
||||
// $appkey = '4409e2ce8ffd12b8';
|
||||
// $appsecret = '59b43e04ad6965f34319062b478f83dd';
|
||||
//
|
||||
// $default = [
|
||||
// 'access_key' => getenv('ACCESS_TOKEN'),
|
||||
// 'actionKey' => 'appkey',
|
||||
// 'appkey' => $appkey,
|
||||
// 'build' => 101800,
|
||||
// 'device' => 'android',
|
||||
// 'mobi_app' => 'android_tv_yst',
|
||||
// 'platform' => 'android',
|
||||
// 'ts' => time(),
|
||||
// ];
|
||||
// $payload = array_merge($payload, $default);
|
||||
// return self::encryption($payload, $appsecret);
|
||||
// }
|
||||
|
||||
/**
|
||||
* @use 登录
|
||||
* @param $payload
|
||||
@ -22,17 +47,18 @@ class Sign
|
||||
*/
|
||||
public static function login($payload)
|
||||
{
|
||||
# 云视听 TV
|
||||
$appkey = '4409e2ce8ffd12b8';
|
||||
$appsecret = '59b43e04ad6965f34319062b478f83dd';
|
||||
# Android 新
|
||||
$appkey = 'bca7e84c2d947ac6';
|
||||
$appsecret = '60698ba2f68e01ce44738920a0ffe768';
|
||||
|
||||
$default = [
|
||||
'access_key' => getenv('ACCESS_TOKEN'),
|
||||
'actionKey' => 'appkey',
|
||||
'appkey' => $appkey,
|
||||
'build' => 101800,
|
||||
'device' => 'android',
|
||||
'mobi_app' => 'android_tv_yst',
|
||||
'build' => 6030600,
|
||||
'channel'=>'bili',
|
||||
'device' => 'phone',
|
||||
'mobi_app' => 'android',
|
||||
'platform' => 'android',
|
||||
'ts' => time(),
|
||||
];
|
||||
@ -50,7 +76,7 @@ class Sign
|
||||
# iOS 6680
|
||||
// $appkey = '27eb53fc9058f8c3';
|
||||
// $appsecret = 'c2ed53a74eeefe3cf99fbd01d8c9c375';
|
||||
# Android
|
||||
# Android 旧
|
||||
$appkey = '1d8b6e7d45233436';
|
||||
$appsecret = '560c52ccd288fed045859ed18bffd973';
|
||||
|
||||
|
||||
@ -102,7 +102,8 @@ class Statistics
|
||||
*/
|
||||
private static function timeTran(int $the_time): string
|
||||
{
|
||||
$t = time() - $the_time - 3;//现在时间-发布时间 获取时间差
|
||||
$the_time = $the_time < 1577808000 ? time() : $the_time;
|
||||
$t = time() - $the_time + 3;//现在时间-发布时间 获取时间差
|
||||
$f = [
|
||||
'31536000' => '年',
|
||||
'2592000' => '个月',
|
||||
|
||||
Loading…
Reference in New Issue
Block a user