Droid 桌面端Factory 解决BOYK无法使用第三方api接入进行对话的自动脚本
- 内容介绍
- 文章标签
- 相关推荐
image963×318 22.4 KB
由于factory自定义api官方不让在桌面端使用,并且个人比较喜欢带ui的版本,便逆向了下,写了个自动修复的版本
代码
"""
Factory Desktop v0.36.0 - 一键解除限制
用法: python patch.py [Factory安装目录]
默认目录: %LOCALAPPDATA%\\Factory\\app-0.36.0
"""
import os, sys, shutil, struct
def find_factory_dir():
if len(sys.argv) > 1:
return sys.argv[1]
default = os.path.join(os.environ.get("LOCALAPPDATA", ""), "Factory", "app-0.36.0")
if os.path.isdir(default):
return default
print("[!] 未找到 Factory 安装目录,请手动指定: python patch.py <目录路径>")
sys.exit(1)
def patch_exe(exe_path):
"""禁用 Electron ASAR 完整性校验 fuse"""
with open(exe_path, "rb") as f:
data = bytearray(f.read())
sentinel = b"dL7pKGdnNz796PbbjQWNKmHXBZaB9tsX"
idx = data.find(sentinel)
if idx < 0:
print("[!] EXE 中未找到 Electron Fuses 标记,可能版本不对")
return False
fuse_base = idx + len(sentinel) + 2 # 跳过 version(1) + length(1)
# Fuse[4] = EnableEmbeddedAsarIntegrityValidation
# Fuse[5] = OnlyLoadAppFromAsar
changed = False
for i, name in [(4, "AsarIntegrityValidation"), (5, "OnlyLoadAppFromAsar")]:
offset = fuse_base + i
if data[offset] == ord("1"):
data[offset] = ord("0")
print(f" [+] 已禁用 {name}")
changed = True
else:
print(f" [-] {name} 已经是禁用状态")
if changed:
with open(exe_path, "wb") as f:
f.write(data)
return True
def patch_asar(asar_path):
"""patch JS 代码:绕过 isLegacy 和 canUseChat 限制"""
with open(asar_path, "rb") as f:
data = f.read()
replacements = [
# isLegacy 检查
(b"o?.isLegacy||xr", b"(((false)))||xr"),
(b"o?.isLegacy&&!ln.isConnected", b"(((false)))&&!ln.isConnected"),
# canUseChat 限制(四种情况)
(b"canUseChat:!1,reason:j2.OverLimit", b"canUseChat:!0,reason:j2.OverLimit"),
(b"canUseChat:!1,reason:j2.Overdue", b"canUseChat:!0,reason:j2.Overdue"),
(b"canUseChat:!1,reason:j2.NoActiveSubscription", b"canUseChat:!0,reason:j2.NoActiveSubscription"),
(b"canUseChat:!1,reason:j2.UserOverQuota", b"canUseChat:!0,reason:j2.UserOverQuota"),
]
patched = 0
for old, new in replacements:
assert len(old) == len(new), f"长度不匹配: {old} ({len(old)}) vs {new} ({len(new)})"
count = data.count(old)
if count > 0:
data = data.replace(old, new)
print(f" [+] {old.decode()} -> {new.decode()} ({count}处)")
patched += count
else:
# 检查是否已经 patch 过
if data.count(new) > 0:
print(f" [-] {new.decode()} 已存在,跳过")
else:
print(f" [!] 未找到: {old.decode()}")
if patched > 0:
with open(asar_path, "wb") as f:
f.write(data)
return patched
def main():
factory_dir = find_factory_dir()
exe_path = os.path.join(factory_dir, "factory-desktop.exe")
asar_path = os.path.join(factory_dir, "resources", "app.asar")
if not os.path.isfile(exe_path):
print(f"[!] 未找到 {exe_path}")
sys.exit(1)
if not os.path.isfile(asar_path):
print(f"[!] 未找到 {asar_path}")
sys.exit(1)
print(f"Factory 目录: {factory_dir}\n")
# 备份
for path in [exe_path, asar_path]:
bak = path + ".bak"
if not os.path.isfile(bak):
shutil.copy2(path, bak)
print(f"[备份] {os.path.basename(path)} -> {os.path.basename(bak)}")
else:
print(f"[备份] {os.path.basename(bak)} 已存在,跳过")
# Patch EXE
print(f"\n== Patch EXE (禁用 ASAR 完整性校验) ==")
patch_exe(exe_path)
# Patch ASAR
print(f"\n== Patch ASAR (绕过 isLegacy + canUseChat) ==")
patch_asar(asar_path)
print(f"\n[完成] 正常启动 Factory Desktop 即可。")
print(f"[恢复] 用 .bak 文件覆盖回去即可还原。")
if __name__ == "__main__":
main()
--【壹】--:
楼主棒棒,它的终端也很好用
--【贰】--:
有个这个,我记的好像也是LD这里的:GitHub - Sunshow/droidgear · GitHub
--【叁】--:
感谢大佬!
image963×318 22.4 KB
由于factory自定义api官方不让在桌面端使用,并且个人比较喜欢带ui的版本,便逆向了下,写了个自动修复的版本
代码
"""
Factory Desktop v0.36.0 - 一键解除限制
用法: python patch.py [Factory安装目录]
默认目录: %LOCALAPPDATA%\\Factory\\app-0.36.0
"""
import os, sys, shutil, struct
def find_factory_dir():
if len(sys.argv) > 1:
return sys.argv[1]
default = os.path.join(os.environ.get("LOCALAPPDATA", ""), "Factory", "app-0.36.0")
if os.path.isdir(default):
return default
print("[!] 未找到 Factory 安装目录,请手动指定: python patch.py <目录路径>")
sys.exit(1)
def patch_exe(exe_path):
"""禁用 Electron ASAR 完整性校验 fuse"""
with open(exe_path, "rb") as f:
data = bytearray(f.read())
sentinel = b"dL7pKGdnNz796PbbjQWNKmHXBZaB9tsX"
idx = data.find(sentinel)
if idx < 0:
print("[!] EXE 中未找到 Electron Fuses 标记,可能版本不对")
return False
fuse_base = idx + len(sentinel) + 2 # 跳过 version(1) + length(1)
# Fuse[4] = EnableEmbeddedAsarIntegrityValidation
# Fuse[5] = OnlyLoadAppFromAsar
changed = False
for i, name in [(4, "AsarIntegrityValidation"), (5, "OnlyLoadAppFromAsar")]:
offset = fuse_base + i
if data[offset] == ord("1"):
data[offset] = ord("0")
print(f" [+] 已禁用 {name}")
changed = True
else:
print(f" [-] {name} 已经是禁用状态")
if changed:
with open(exe_path, "wb") as f:
f.write(data)
return True
def patch_asar(asar_path):
"""patch JS 代码:绕过 isLegacy 和 canUseChat 限制"""
with open(asar_path, "rb") as f:
data = f.read()
replacements = [
# isLegacy 检查
(b"o?.isLegacy||xr", b"(((false)))||xr"),
(b"o?.isLegacy&&!ln.isConnected", b"(((false)))&&!ln.isConnected"),
# canUseChat 限制(四种情况)
(b"canUseChat:!1,reason:j2.OverLimit", b"canUseChat:!0,reason:j2.OverLimit"),
(b"canUseChat:!1,reason:j2.Overdue", b"canUseChat:!0,reason:j2.Overdue"),
(b"canUseChat:!1,reason:j2.NoActiveSubscription", b"canUseChat:!0,reason:j2.NoActiveSubscription"),
(b"canUseChat:!1,reason:j2.UserOverQuota", b"canUseChat:!0,reason:j2.UserOverQuota"),
]
patched = 0
for old, new in replacements:
assert len(old) == len(new), f"长度不匹配: {old} ({len(old)}) vs {new} ({len(new)})"
count = data.count(old)
if count > 0:
data = data.replace(old, new)
print(f" [+] {old.decode()} -> {new.decode()} ({count}处)")
patched += count
else:
# 检查是否已经 patch 过
if data.count(new) > 0:
print(f" [-] {new.decode()} 已存在,跳过")
else:
print(f" [!] 未找到: {old.decode()}")
if patched > 0:
with open(asar_path, "wb") as f:
f.write(data)
return patched
def main():
factory_dir = find_factory_dir()
exe_path = os.path.join(factory_dir, "factory-desktop.exe")
asar_path = os.path.join(factory_dir, "resources", "app.asar")
if not os.path.isfile(exe_path):
print(f"[!] 未找到 {exe_path}")
sys.exit(1)
if not os.path.isfile(asar_path):
print(f"[!] 未找到 {asar_path}")
sys.exit(1)
print(f"Factory 目录: {factory_dir}\n")
# 备份
for path in [exe_path, asar_path]:
bak = path + ".bak"
if not os.path.isfile(bak):
shutil.copy2(path, bak)
print(f"[备份] {os.path.basename(path)} -> {os.path.basename(bak)}")
else:
print(f"[备份] {os.path.basename(bak)} 已存在,跳过")
# Patch EXE
print(f"\n== Patch EXE (禁用 ASAR 完整性校验) ==")
patch_exe(exe_path)
# Patch ASAR
print(f"\n== Patch ASAR (绕过 isLegacy + canUseChat) ==")
patch_asar(asar_path)
print(f"\n[完成] 正常启动 Factory Desktop 即可。")
print(f"[恢复] 用 .bak 文件覆盖回去即可还原。")
if __name__ == "__main__":
main()
--【壹】--:
楼主棒棒,它的终端也很好用
--【贰】--:
有个这个,我记的好像也是LD这里的:GitHub - Sunshow/droidgear · GitHub
--【叁】--:
感谢大佬!

