157 lines
6.2 KiB
Python
157 lines
6.2 KiB
Python
from __future__ import annotations
|
|
|
|
import argparse
|
|
import json
|
|
from pathlib import Path
|
|
|
|
|
|
def replace_required(text: str, old: str, new: str, label: str) -> str:
|
|
if new in text:
|
|
return text
|
|
if old not in text:
|
|
raise RuntimeError(f'{label} marker not found')
|
|
return text.replace(old, new, 1)
|
|
|
|
|
|
def patch_send_ts(text: str) -> str:
|
|
text = replace_required(
|
|
text,
|
|
'}): Promise<{ messageId: string }> {\n const { to, text, opts } = params;\n',
|
|
'}): Promise<{ messageId: string; createTimeMs: number }> {\n const { to, text, opts } = params;\n',
|
|
'TS send return type',
|
|
)
|
|
text = replace_required(
|
|
text,
|
|
' const clientId = generateClientId();\n const req = buildSendMessageReq({',
|
|
' const clientId = generateClientId();\n const createTimeMs = Date.now();\n const req = buildSendMessageReq({',
|
|
'TS create time',
|
|
)
|
|
text = replace_required(
|
|
text,
|
|
' });\n try {\n await sendMessageApi({',
|
|
' });\n if (!req.msg?.item_list?.[0]) throw new Error("sendMessageWeixin: text item missing");\n req.msg.item_list[0].create_time_ms = createTimeMs;\n try {\n await sendMessageApi({',
|
|
'TS request timestamp',
|
|
)
|
|
text = replace_required(
|
|
text,
|
|
' return { messageId: clientId };\n}\n\n/** Send a single structured MessageItem downstream. */',
|
|
' return { messageId: clientId, createTimeMs };\n}\n\n/** Send a single structured MessageItem downstream. */',
|
|
'TS send result',
|
|
)
|
|
return text
|
|
|
|
|
|
def patch_send_js(text: str) -> str:
|
|
text = replace_required(
|
|
text,
|
|
' const clientId = generateClientId();\n const req = buildSendMessageReq({',
|
|
' const clientId = generateClientId();\n const createTimeMs = Date.now();\n const req = buildSendMessageReq({',
|
|
'JS create time',
|
|
)
|
|
text = replace_required(
|
|
text,
|
|
' });\n try {\n await sendMessageApi({',
|
|
' });\n if (!req.msg?.item_list?.[0])\n throw new Error("sendMessageWeixin: text item missing");\n req.msg.item_list[0].create_time_ms = createTimeMs;\n try {\n await sendMessageApi({',
|
|
'JS request timestamp',
|
|
)
|
|
text = replace_required(
|
|
text,
|
|
' return { messageId: clientId };\n}\n/** Send a single structured MessageItem downstream. */',
|
|
' return { messageId: clientId, createTimeMs };\n}\n/** Send a single structured MessageItem downstream. */',
|
|
'JS send result',
|
|
)
|
|
return text
|
|
|
|
|
|
def patch_process_ts(text: str) -> str:
|
|
old = '''await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
}});'''
|
|
new = '''const sentText = await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
}});
|
|
rememberHermesOutboundTextMessage(deps.accountId, ctx.To, text, sentText.createTimeMs);'''
|
|
text = replace_required(text, old, new, 'TS fallback text send')
|
|
old = '''await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
}});'''
|
|
new = '''const sentText = await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
}});
|
|
rememberHermesOutboundTextMessage(deps.accountId, ctx.To, text, sentText.createTimeMs);'''
|
|
return replace_required(text, old, new, 'TS normal text send')
|
|
|
|
|
|
def patch_process_js(text: str) -> str:
|
|
old = '''await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
} });'''
|
|
new = '''const sentText = await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
} });
|
|
rememberHermesOutboundTextMessage(deps.accountId, ctx.To, text, sentText.createTimeMs);'''
|
|
text = replace_required(text, old, new, 'JS fallback text send')
|
|
old = '''await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
} });'''
|
|
new = '''const sentText = await sendMessageWeixin({ to: ctx.To, text, opts: {
|
|
baseUrl: deps.baseUrl,
|
|
token: deps.token,
|
|
contextToken,
|
|
runId,
|
|
} });
|
|
rememberHermesOutboundTextMessage(deps.accountId, ctx.To, text, sentText.createTimeMs);'''
|
|
return replace_required(text, old, new, 'JS normal text send')
|
|
|
|
|
|
def apply(root: Path) -> dict[str, bool]:
|
|
transforms = {
|
|
'src/messaging/send.ts': patch_send_ts,
|
|
'dist/src/messaging/send.js': patch_send_js,
|
|
'src/messaging/process-message.ts': patch_process_ts,
|
|
'dist/src/messaging/process-message.js': patch_process_js,
|
|
}
|
|
changed = {}
|
|
for relative, transform in transforms.items():
|
|
path = root / relative
|
|
original = path.read_text(encoding='utf-8')
|
|
updated = transform(original)
|
|
changed[relative] = updated != original
|
|
if updated != original:
|
|
path.write_text(updated, encoding='utf-8')
|
|
return changed
|
|
|
|
|
|
def main() -> int:
|
|
parser = argparse.ArgumentParser()
|
|
parser.add_argument('plugin_root', type=Path)
|
|
args = parser.parse_args()
|
|
root = args.plugin_root.resolve()
|
|
print(json.dumps({'plugin_root': str(root), 'changed': apply(root)}, ensure_ascii=False))
|
|
return 0
|
|
|
|
|
|
if __name__ == '__main__':
|
|
raise SystemExit(main())
|