mirror of
https://github.com/MikuLeaks/KianaBH3.git
synced 2025-12-13 21:34:43 +01:00
feat: Implement dispatch encryption
This commit is contained in:
@@ -1,13 +1,20 @@
|
||||
from game_server.config import *
|
||||
from enum import Enum
|
||||
import logging
|
||||
from pathlib import Path
|
||||
|
||||
from flask import Flask, send_from_directory
|
||||
from sdk_server.controllers.account_controller import account_blueprint
|
||||
from sdk_server.controllers.config_controller import config_blueprint
|
||||
from sdk_server.controllers.dispatch_controller import dispatch_blueprint
|
||||
from utils.logger import Info
|
||||
|
||||
|
||||
class VerboseLevel(Enum):
|
||||
SILENT = 0
|
||||
NORMAL = 1
|
||||
DEBUG = 2
|
||||
|
||||
|
||||
class RequestLoggingMiddleware:
|
||||
suppressed_routes = ["/report", "/sdk/dataUpload"]
|
||||
|
||||
@@ -16,15 +23,18 @@ class RequestLoggingMiddleware:
|
||||
self.verbose_level = verbose_level
|
||||
|
||||
def __call__(self, environ, start_response):
|
||||
path = environ.get('PATH_INFO', '')
|
||||
method = environ.get('REQUEST_METHOD', '').upper()
|
||||
path = environ.get("PATH_INFO", "")
|
||||
method = environ.get("REQUEST_METHOD", "").upper()
|
||||
|
||||
def custom_start_response(status, headers, *args):
|
||||
status_code = int(status.split()[0])
|
||||
|
||||
if self.verbose_level.value > VerboseLevel.NORMAL.value:
|
||||
Info(f"{status_code} {method} {path}")
|
||||
elif self.verbose_level.value > VerboseLevel.SILENT.value and path not in self.suppressed_routes:
|
||||
elif (
|
||||
self.verbose_level.value > VerboseLevel.SILENT.value
|
||||
and path not in self.suppressed_routes
|
||||
):
|
||||
Info(f"{status_code} {method} {path}")
|
||||
|
||||
return start_response(status, headers, *args)
|
||||
@@ -32,7 +42,6 @@ class RequestLoggingMiddleware:
|
||||
return self.app(environ, custom_start_response)
|
||||
|
||||
|
||||
|
||||
app = Flask(__name__)
|
||||
|
||||
|
||||
@@ -43,27 +52,31 @@ resources_path = Path(__file__).resolve().parent.parent / "resources/statics"
|
||||
if not resources_path.exists():
|
||||
resources_path.mkdir(parents=True)
|
||||
|
||||
@app.route('/statics/<path:filename>')
|
||||
|
||||
@app.route("/statics/<path:filename>")
|
||||
def serve_statics(filename):
|
||||
return send_from_directory(resources_path, filename)
|
||||
|
||||
|
||||
app.register_blueprint(account_blueprint)
|
||||
app.register_blueprint(config_blueprint)
|
||||
app.register_blueprint(dispatch_blueprint)
|
||||
|
||||
def HandleSdkServer(ServerIp, GameServerPort, SdkServerPort):
|
||||
app.config['SERVER_IP'] = ServerIp
|
||||
app.config['GAME_SERVER_PORT'] = GameServerPort
|
||||
|
||||
log = logging.getLogger('werkzeug')
|
||||
def HandleSdkServer(ServerIp, GameServerPort, SdkServerPort):
|
||||
app.config["SERVER_IP"] = ServerIp
|
||||
app.config["GAME_SERVER_PORT"] = GameServerPort
|
||||
|
||||
log = logging.getLogger("werkzeug")
|
||||
log.setLevel(logging.ERROR)
|
||||
|
||||
Info("HTTP server started on port 80")
|
||||
Info(f"HTTP server started on port {SdkServerPort}")
|
||||
|
||||
app.run(host=ServerIp, port=SdkServerPort)
|
||||
|
||||
|
||||
def HandleSslSdkServer():
|
||||
log = logging.getLogger('werkzeug')
|
||||
log = logging.getLogger("werkzeug")
|
||||
log.setLevel(logging.ERROR)
|
||||
Info("HTTPS server started on port 443")
|
||||
app.run(host='127.0.0.1', port=443,ssl_context='adhoc')
|
||||
app.run(host="127.0.0.1", port=443, ssl_context="adhoc")
|
||||
|
||||
@@ -1,90 +1,111 @@
|
||||
from game_server.config import *
|
||||
import json
|
||||
import re
|
||||
import time
|
||||
from flask import Blueprint, Response, jsonify, request
|
||||
from utils.aes import encrypt_ecb
|
||||
from utils.config import Config
|
||||
|
||||
dispatch_blueprint = Blueprint('dispatch', __name__)
|
||||
dispatch_blueprint = Blueprint("dispatch", __name__)
|
||||
|
||||
@dispatch_blueprint.route('/query_dispatch', methods=['GET'])
|
||||
|
||||
@dispatch_blueprint.route("/query_dispatch", methods=["GET"])
|
||||
def query_dispatch():
|
||||
version = request.args.get('version')
|
||||
version = request.args.get("version")
|
||||
response_data = {
|
||||
'retcode': 0,
|
||||
'region_list': [{
|
||||
'retcode': 0,
|
||||
'dispatch_url': f"http://{Config.GameServer.Ip}/query_gateway",
|
||||
'name': Config.RegionName,
|
||||
'title': "",
|
||||
'ext': get_ext(version)
|
||||
}]
|
||||
"retcode": 0,
|
||||
"region_list": [
|
||||
{
|
||||
"retcode": 0,
|
||||
"dispatch_url": f"http://{Config.GameServer.IP}/query_gateway",
|
||||
"name": Config.RegionName,
|
||||
"title": "",
|
||||
"ext": get_ext(version),
|
||||
}
|
||||
],
|
||||
}
|
||||
|
||||
if Config.EnableDispatchEncryption:
|
||||
return Response(
|
||||
encrypt_ecb(Config.AESKeys.get(version), json.dumps(response_data)),
|
||||
mimetype="text/plain",
|
||||
)
|
||||
|
||||
return jsonify(response_data)
|
||||
|
||||
@dispatch_blueprint.route('/query_gateway', methods=['GET'])
|
||||
|
||||
@dispatch_blueprint.route("/query_gateway", methods=["GET"])
|
||||
def query_gateway():
|
||||
version = request.args.get('version')
|
||||
gameserver = {
|
||||
'ip': Config.GameServer.Ip,
|
||||
'port': Config.GameServer.Port
|
||||
}
|
||||
|
||||
version = request.args.get("version")
|
||||
gameserver = {"ip": Config.GameServer.IP, "port": Config.GameServer.Port}
|
||||
|
||||
response_data = {
|
||||
'retcode': 0,
|
||||
'msg': "",
|
||||
'region_name': Config.RegionName,
|
||||
'account_url': f"http://{Config.GameServer.Ip}/account",
|
||||
'account_url_backup': f"http://{Config.GameServer.Ip}/account",
|
||||
'asset_bundle_url_list': get_asset_bundle_url_list(version),
|
||||
'ex_audio_and_video_url_list': get_ex_audio_and_video_url_list(version),
|
||||
'ex_resource_url_list': get_ex_resource_url_list(version),
|
||||
'ext': get_ext(version),
|
||||
'gameserver': gameserver,
|
||||
'gateway': gameserver,
|
||||
'is_data_ready': True,
|
||||
'oaserver_url': f"http://{Config.GameServer.Ip}/oaserver",
|
||||
'server_cur_time': int(time.time()),
|
||||
'server_cur_timezone': 8,
|
||||
'server_ext': {
|
||||
'cdkey_url': f"http://{Config.GameServer.Ip}/common",
|
||||
'mihoyo_sdk_env': "2"
|
||||
}
|
||||
"retcode": 0,
|
||||
"msg": "",
|
||||
"region_name": Config.RegionName,
|
||||
"account_url": f"http://{Config.GameServer.IP}/account",
|
||||
"account_url_backup": f"http://{Config.GameServer.IP}/account",
|
||||
"asset_bundle_url_list": get_asset_bundle_url_list(version),
|
||||
"ex_audio_and_video_url_list": get_ex_audio_and_video_url_list(version),
|
||||
"ex_resource_url_list": get_ex_resource_url_list(version),
|
||||
"ext": get_ext(version),
|
||||
"gameserver": gameserver,
|
||||
"gateway": gameserver,
|
||||
"is_data_ready": True,
|
||||
"oaserver_url": f"http://{Config.GameServer.IP}/oaserver",
|
||||
"server_cur_time": int(time.time()),
|
||||
"server_cur_timezone": 8,
|
||||
"server_ext": {
|
||||
"cdkey_url": f"http://{Config.GameServer.IP}/common",
|
||||
"mihoyo_sdk_env": "2",
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
if Config.EnableDispatchEncryption:
|
||||
return Response(
|
||||
encrypt_ecb(Config.AESKeys.get(version), json.dumps(response_data)),
|
||||
mimetype="text/plain",
|
||||
)
|
||||
|
||||
return jsonify(response_data)
|
||||
|
||||
|
||||
def get_ext(version):
|
||||
return {
|
||||
'ai_use_asset_bundle': "0" if Config.UseLocalCache else "1",
|
||||
'apm_log_level': "0",
|
||||
'apm_log_dest': "2",
|
||||
'apm_switch': "0",
|
||||
'apm_switch_game_log': "1",
|
||||
'apm_switch_crash': "1",
|
||||
'block_error_dialog': "1",
|
||||
'elevator_model_path': "GameEntry/EVA/StartLoading_Model",
|
||||
'data_use_asset_bundle': "1",
|
||||
'enable_watermark': "1",
|
||||
'ex_audio_and_video_url_list': get_ex_audio_and_video_url_list(version),
|
||||
'ex_res_buff_size': "10485760",
|
||||
'ex_res_pre_publish': "0",
|
||||
'ex_res_use_http': "1",
|
||||
'ex_resource_url_list': get_ex_resource_url_list(version),
|
||||
'is_xxxx': "0",
|
||||
'mtp_switch': "0",
|
||||
'network_feedback_enable': "0",
|
||||
'offline_report_switch': "0",
|
||||
'forbid_recharge': "1",
|
||||
'is_checksum_off': "0" if Config.UseLocalCache else "1",
|
||||
'res_use_asset_bundle': "1",
|
||||
'show_version_text': "0",
|
||||
'update_streaming_asb': "0",
|
||||
'use_multy_cdn': "1",
|
||||
'show_bulletin_button': "1",
|
||||
'show_bulletin_empty_dialog_bg': "0"
|
||||
"ai_use_asset_bundle": "0" if Config.UseLocalCache else "1",
|
||||
"apm_log_level": "0",
|
||||
"apm_log_dest": "2",
|
||||
"apm_switch": "0",
|
||||
"apm_switch_game_log": "1",
|
||||
"apm_switch_crash": "1",
|
||||
"block_error_dialog": "1",
|
||||
"elevator_model_path": "GameEntry/EVA/StartLoading_Model",
|
||||
"data_use_asset_bundle": "1",
|
||||
"enable_watermark": "1",
|
||||
"ex_audio_and_video_url_list": get_ex_audio_and_video_url_list(version),
|
||||
"ex_res_buff_size": "10485760",
|
||||
"ex_res_pre_publish": "0",
|
||||
"ex_res_use_http": "1",
|
||||
"ex_resource_url_list": get_ex_resource_url_list(version),
|
||||
"is_xxxx": "0",
|
||||
"mtp_switch": "0",
|
||||
"network_feedback_enable": "0",
|
||||
"offline_report_switch": "0",
|
||||
"forbid_recharge": "1",
|
||||
"is_checksum_off": "0" if Config.UseLocalCache else "1",
|
||||
"res_use_asset_bundle": "1",
|
||||
"show_version_text": "0",
|
||||
"update_streaming_asb": "0",
|
||||
"use_multy_cdn": "1",
|
||||
"show_bulletin_button": "1",
|
||||
"show_bulletin_empty_dialog_bg": "0",
|
||||
}
|
||||
|
||||
|
||||
def get_asset_bundle_url_list(version):
|
||||
# Compile the regex pattern
|
||||
regex = re.compile(r"^(.*?)_(os|gf|global)_(.*?)$")
|
||||
match = regex.match(version)
|
||||
value = match.group(2)
|
||||
value = match.group(2)
|
||||
if Config.UseLocalCache:
|
||||
return get_local_url_list(value, version)
|
||||
# Proceed if there's a match
|
||||
@@ -93,35 +114,36 @@ def get_asset_bundle_url_list(version):
|
||||
if value == "os":
|
||||
return [
|
||||
"https://bundle-aliyun-os.honkaiimpact3.com/asset_bundle/overseas01/1.1",
|
||||
"https://hk-bundle-os-mihayo.akamaized.net/asset_bundle/overseas01/1.1"
|
||||
"https://hk-bundle-os-mihayo.akamaized.net/asset_bundle/overseas01/1.1",
|
||||
]
|
||||
elif value == "gf":
|
||||
if "beta" in version:
|
||||
return [
|
||||
"https://autopatchbeta.bh3.com/asset_bundle/beta_release/1.0",
|
||||
"https://autopatchbeta.bh3.com/asset_bundle/beta_release/1.0"
|
||||
"https://autopatchbeta.bh3.com/asset_bundle/beta_release/1.0",
|
||||
]
|
||||
return [
|
||||
"https://bundle-qcloud.bh3.com/asset_bundle/android01/1.0",
|
||||
"https://bundle.bh3.com/asset_bundle/android01/1.0"
|
||||
"https://bundle.bh3.com/asset_bundle/android01/1.0",
|
||||
]
|
||||
elif value == "global":
|
||||
return [
|
||||
"http://hk-bundle-west-mihayo.akamaized.net/asset_bundle/usa01/1.1",
|
||||
"http://bundle-aliyun-usa.honkaiimpact3.com/asset_bundle/usa01/1.1"
|
||||
"http://bundle-aliyun-usa.honkaiimpact3.com/asset_bundle/usa01/1.1",
|
||||
]
|
||||
else:
|
||||
return [
|
||||
"https://bundle-aliyun-os.honkaiimpact3.com/asset_bundle/overseas01/1.1",
|
||||
"https://hk-bundle-os-mihayo.akamaized.net/asset_bundle/overseas01/1.1"
|
||||
"https://hk-bundle-os-mihayo.akamaized.net/asset_bundle/overseas01/1.1",
|
||||
]
|
||||
return []
|
||||
|
||||
|
||||
def get_ex_audio_and_video_url_list(version):
|
||||
# Compile the regex pattern
|
||||
regex = re.compile(r"^(.*?)_(os|gf|global)_(.*?)$")
|
||||
match = regex.match(version)
|
||||
value = match.group(2)
|
||||
value = match.group(2)
|
||||
if Config.UseLocalCache:
|
||||
return get_local_url_list(value, version)
|
||||
if match:
|
||||
@@ -129,35 +151,36 @@ def get_ex_audio_and_video_url_list(version):
|
||||
if value == "os":
|
||||
return [
|
||||
"bigfile-aliyun-os.honkaiimpact3.com/com.miHoYo.bh3oversea",
|
||||
"hk-bigfile-os-mihayo.akamaized.net/com.miHoYo.bh3oversea"
|
||||
"hk-bigfile-os-mihayo.akamaized.net/com.miHoYo.bh3oversea",
|
||||
]
|
||||
elif value == "gf":
|
||||
if "beta" in version:
|
||||
return [
|
||||
"autopatchbeta.bh3.com/tmp/CGAudio",
|
||||
"autopatchbeta.bh3.com/tmp/CGAudio"
|
||||
"autopatchbeta.bh3.com/tmp/CGAudio",
|
||||
]
|
||||
return [
|
||||
"bh3rd-beta-qcloud.bh3.com/tmp/CGAudio",
|
||||
"bh3rd-beta.bh3.com/tmp/CGAudio"
|
||||
"bh3rd-beta.bh3.com/tmp/CGAudio",
|
||||
]
|
||||
elif value == "global":
|
||||
return [
|
||||
"bh3rd-beta-qcloud.bh3.com/tmp/CGAudio",
|
||||
"bh3rd-beta.bh3.com/tmp/CGAudio"
|
||||
"bh3rd-beta.bh3.com/tmp/CGAudio",
|
||||
]
|
||||
else:
|
||||
return [
|
||||
"bh3rd-beta-qcloud.bh3.com/tmp/CGAudio",
|
||||
"bh3rd-beta.bh3.com/tmp/CGAudio"
|
||||
"bh3rd-beta.bh3.com/tmp/CGAudio",
|
||||
]
|
||||
return []
|
||||
|
||||
|
||||
def get_ex_resource_url_list(version):
|
||||
# Compile the regex pattern
|
||||
# Compile the regex pattern
|
||||
regex = re.compile(r"^(.*?)_(os|gf|global)_(.*?)$")
|
||||
match = regex.match(version)
|
||||
value = match.group(2)
|
||||
value = match.group(2)
|
||||
if Config.UseLocalCache:
|
||||
return get_local_url_list(value, version)
|
||||
# Proceed if there's a match
|
||||
@@ -166,33 +189,30 @@ def get_ex_resource_url_list(version):
|
||||
if value == "os":
|
||||
return [
|
||||
"bigfile-aliyun-os.honkaiimpact3.com/com.miHoYo.bh3oversea",
|
||||
"hk-bigfile-os-mihayo.akamaized.net/com.miHoYo.bh3oversea"
|
||||
"hk-bigfile-os-mihayo.akamaized.net/com.miHoYo.bh3oversea",
|
||||
]
|
||||
elif value == "gf":
|
||||
if "beta" in version:
|
||||
return [
|
||||
"autopatchbeta.bh3.com/tmp/beta",
|
||||
"autopatchbeta.bh3.com/tmp/beta"
|
||||
"autopatchbeta.bh3.com/tmp/beta",
|
||||
]
|
||||
return [
|
||||
"bundle-qcloud.bh3.com/tmp/Original",
|
||||
"bundle.bh3.com/tmp/Original"
|
||||
]
|
||||
return ["bundle-qcloud.bh3.com/tmp/Original", "bundle.bh3.com/tmp/Original"]
|
||||
elif value == "global":
|
||||
return [
|
||||
"hk-bundle-west-mihayo.akamaized.net/tmp/com.miHoYo.bh3global",
|
||||
"bigfile-aliyun-usa.honkaiimpact3.com/tmp/com.miHoYo.bh3global"
|
||||
"bigfile-aliyun-usa.honkaiimpact3.com/tmp/com.miHoYo.bh3global",
|
||||
]
|
||||
else:
|
||||
return [
|
||||
"bigfile-aliyun-os.honkaiimpact3.com/com.miHoYo.bh3oversea",
|
||||
"hk-bigfile-os-mihayo.akamaized.net/com.miHoYo.bh3oversea"
|
||||
"hk-bigfile-os-mihayo.akamaized.net/com.miHoYo.bh3oversea",
|
||||
]
|
||||
return []
|
||||
|
||||
|
||||
def get_local_url_list(type, version):
|
||||
return [
|
||||
f"http://{Config.GameServer.Ip}/statics/{type}/{version.replace('.', '_')}",
|
||||
f"http://{Config.GameServer.Ip}/statics/{type}/{version.replace('.', '_')}"
|
||||
f"http://{Config.GameServer.IP}/statics/{type}/{version.replace('.', '_')}",
|
||||
f"http://{Config.GameServer.IP}/statics/{type}/{version.replace('.', '_')}",
|
||||
]
|
||||
|
||||
|
||||
@@ -1,13 +1,12 @@
|
||||
# sdkserver/models/granter_login_body.py
|
||||
|
||||
from pydantic import BaseModel
|
||||
from typing import Optional
|
||||
|
||||
|
||||
class GranterLoginBodyData(BaseModel):
|
||||
uid: str
|
||||
guest: bool
|
||||
token: str
|
||||
|
||||
|
||||
class GranterLoginBody(BaseModel):
|
||||
app_id: int
|
||||
channel_id: int
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
# sdkserver/models/risky_check.py
|
||||
|
||||
from pydantic import BaseModel
|
||||
from typing import Optional
|
||||
|
||||
|
||||
class DataScheme(BaseModel):
|
||||
id: str
|
||||
action: str
|
||||
geetest: Optional[object]
|
||||
|
||||
|
||||
class RiskyCheck(BaseModel):
|
||||
retcode: int
|
||||
message: str
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
from pydantic import BaseModel
|
||||
|
||||
|
||||
class ShieldVerifyBody(BaseModel):
|
||||
token: str
|
||||
uid: str
|
||||
uid: str
|
||||
|
||||
Reference in New Issue
Block a user