Files
workphone-sdk/sdk/tests/test_companion_dispatch_contract.py

66 lines
2.7 KiB
Python

from pathlib import Path
from sdk.agent.hook.companion_dispatch import (
ACCOUNT_SETTINGS,
COMPANION_ACTIONS,
COMPANION_BATCHES,
FRIEND_GROUP,
VIDEO_CHANNEL,
dispatch_record,
)
ROOT = Path(__file__).resolve().parents[2]
HOOK = ROOT / "sdk/android-app/app/src/main/assets/wechat_hook_v2.js"
AGENT = ROOT / "sdk/agent/agent.py"
def test_companion_manifest_has_83_unique_actions_and_four_batches():
assert len(COMPANION_ACTIONS) == 83
assert len(set(COMPANION_ACTIONS)) == 83
flattened = set().union(*[set(v) for v in COMPANION_BATCHES.values()]) | {"mass_send"}
assert flattened == set(COMPANION_ACTIONS)
assert ACCOUNT_SETTINGS and FRIEND_GROUP and VIDEO_CHANNEL
def test_mass_send_is_only_first_batch_action_with_rpc():
assert dispatch_record("mass_send")["rpc"] == "massSend"
account_contracts = {
"set_nickname": "setNickname", "set_signature": "setSignature", "set_region": "setRegion",
"set_sex": "setSex", "set_gender": "setGender", "set_avatar": "setAvatar",
"set_privacy": "setPrivacy", "set_account_protection": "setAccountProtection",
"set_notification": "setNotification", "set_do_not_disturb": "setDoNotDisturb",
"toggle_do_not_disturb": "toggleDoNotDisturb", "set_what_up": "setWhatUp",
}
for action in COMPANION_ACTIONS:
if action == "mass_send":
continue
record = dispatch_record(action)
if action in account_contracts:
assert record["rpc"] == account_contracts[action]
assert "readback" in record and record["test_status"].startswith("contract_")
else:
assert record["rpc"] is None
assert record["error"] == "capability_unavailable"
assert record["readback"] is None
def test_hook_installs_companion_guards_and_keeps_no_fake_success_contract():
source = HOOK.read_text()
assert "COMPANION_CAPABILITIES" in source
assert "_companionCapabilityUnavailable" in source
assert "rpc.exports.companionCapabilities" in source
assert "status: 'capability_unavailable'" in source
assert "if (action === 'mass_send' || ACCOUNT_SETTING_CONTRACTS[action]) return;" in source
assert "ACCOUNT_SETTING_CONTRACTS" in source
assert "dry_run_no_write" in source
assert "confirm_required" in source
assert "rpc.exports[camel] = function (params)" in source
def test_agent_blocks_ui_fallback_for_companion_actions():
source = AGENT.read_text()
assert "HEADLESS_COMPANION_ACTIONS" in source
assert '"status": "capability_unavailable"' in source
assert '"channel": "frida_rpc"' in source
assert 'action not in self.HEADLESS_COMPANION_ACTIONS' in source