omemo keyring

This commit is contained in:
nnduc
2026-10-27 23:49:59 +07:00
parent 9f44778f21
commit 1ce93d883b
16 changed files with 1327 additions and 481 deletions
+68
View File
@@ -0,0 +1,68 @@
"""Own OMEMO messages coming back from the archive (MAM) are shown decrypted, like when edited:
their local id is m_…, the browser stored the plaintext under the id it sent them with."""
import asyncio
import os
import sqlite3
import subprocess
from playwright.async_api import async_playwright
from browser import login, BASE, OUT
from browser_edit import send, edit_last, bubbles, open_chat
D = os.path.dirname(os.path.abspath(__file__))
async def main():
async with async_playwright() as p:
browser = await p.chromium.launch()
actx, alice, aerr = await login(browser, "alice@localhost", "alicepass", "historyalice")
await alice.wait_for_timeout(4000)
await open_chat(alice, "bob@localhost")
await alice.evaluate("ChatOmemo.enableContactState('bob@localhost', false)")
await alice.wait_for_timeout(5000)
await send(alice, "Lịch sử: bản gốc")
await edit_last(alice, "Lịch sử: đã sửa")
await send(alice, "Lịch sử: tin thứ hai")
bctx, bob, berr = await login(browser, "bob@localhost", "bobpass", "historybob")
await bob.wait_for_timeout(4000)
await open_chat(bob, "alice@localhost")
await bob.evaluate("ChatOmemo.enableContactState('alice@localhost', false)")
await bob.wait_for_timeout(5000)
await send(bob, "Lịch sử: trả lời của bob")
await alice.wait_for_timeout(3000)
print("before, alice:", await bubbles(alice, 3))
await bctx.close()
# The server forgets the discussion, the history comes back from MAM
subprocess.run(["kill", open(f"{D}/server.pid").read().strip()])
await alice.wait_for_timeout(1000)
db = sqlite3.connect(f"{D}/data/movim.sqlite")
for table in ("messages", "mam_earliests"):
db.execute(f"DELETE FROM {table} WHERE user_id = 'alice@localhost'")
db.commit()
db.close()
subprocess.run([f"{D}/run.sh"])
# Same browser context: the decrypted messages of IndexedDB are kept
page = await actx.new_page()
await page.goto(BASE + "/login")
await page.wait_for_timeout(3000)
if "/login" in page.url:
await page.wait_for_selector("#login_widget input[type=submit]:not([disabled])", timeout=15000)
await page.fill("input#username", "alice@localhost")
await page.fill("input#password", "alicepass")
await page.click("#login_widget input[type=submit]")
await page.wait_for_url("**/chat**", timeout=30000)
await page.wait_for_timeout(4000)
await open_chat(page, "bob@localhost")
await page.wait_for_timeout(4000)
print("ids:", await page.evaluate(
"[...document.querySelectorAll('#chat_widget .bubble > div.message')].slice(-3).map(m => m.id)"))
print("from history, alice:", await bubbles(page, 3))
await page.screenshot(path=f"{OUT}/history_alice.png")
for e in aerr:
print(e)
await browser.close()
asyncio.run(main())