aboutsummaryrefslogtreecommitdiffstats
path: root/tools/post-actions-test.js
diff options
context:
space:
mode:
authorAdam Soltys <[email protected]>2026-10-07 08:27:40 -0700
committerAdam Soltys <[email protected]>2026-10-07 08:27:40 -0700
commitdfb017c1b10cb52c24f4f0bcf745c6abea11b98f (patch)
treeb8150ed4805f206947e2475fe433be953c46fb70 /tools/post-actions-test.js
parentb70e169bb5b5beccb89fd59427726e32d414b4a5 (diff)
downloadcoinosv3-dfb017c1b10cb52c24f4f0bcf745c6abea11b98f.tar.gz
coinosv3-dfb017c1b10cb52c24f4f0bcf745c6abea11b98f.zip
Feed, composer and zap tests follow today's app
- feed tests reach the Feed from the bottom nav (the chat-home row is gone) and seed this wallet's last feed as Following (new wallets open on Popular, c89050e) plus the author's profile (readiness gate) - post-actions: its picture is made locally (it read another session's scratchpad), the post's own ⋯ (not the feed header's), a real tap on the DM picture (a tap beside a fitted picture is a tap on the post) - composer-media / video-compress: intercept every public media host (ditto is first now; the tests were uploading for real) - compose-preview: Preview is one toggle button (aria-pressed) - thread-reply: harness has a wallet (else visitor: Reply asks to sign in), registers <coinos-text>, holds the root's id-only query; atomic send tap - video-unmute: stubs what videoNode reaches outside its slice; preload none means the in-view clip is told to load - zap-deep-profile: zap button scrolled to mid-screen (the bottom nav covered it) Co-Authored-By: Claude Opus 5.5 <[email protected]>
Diffstat (limited to 'tools/post-actions-test.js')
-rw-r--r--tools/post-actions-test.js19
1 files changed, 13 insertions, 6 deletions
diff --git a/tools/post-actions-test.js b/tools/post-actions-test.js
index 17f8372..4c5d92e 100644
--- a/tools/post-actions-test.js
+++ b/tools/post-actions-test.js
@@ -16,7 +16,10 @@ const sleep = (ms) => new Promise((r) => setTimeout(r, ms));
let ok = true;
const check = (n, c, d = '') => { console.log(` ${c ? '✓' : '✗'} ${n}${d ? ' — ' + d : ''}`); if (!c) ok = false; };
const html = await buildHtml({ minify: true, pwa: false });
-const png = await Bun.file('/tmp/claude-1000/-home-adam-coinosv3/61dea255-d26d-411d-be8b-92dfb0a75887/scratchpad/big.png').arrayBuffer().catch(() => null);
+// a picture served locally (a remote one that fails to load stays a link)
+const PNG = '/tmp/coinos-post-actions-test.png';
+Bun.spawnSync(['ffmpeg', '-y', '-loglevel', 'error', '-f', 'lavfi', '-i', 'color=c=green:s=600x400', '-frames:v', '1', PNG]);
+const png = await Bun.file(PNG).arrayBuffer().catch(() => null);
const server = Bun.serve({ port: 5258, async fetch(req) {
const u = new URL(req.url);
if (u.pathname === '/pic.png' && png) return new Response(png, { headers: { 'content-type': 'image/png' } });
@@ -54,12 +57,12 @@ try {
]));
// a known face: a row is admitted once its author's picture has been tried
localStorage.setItem(k + ':profiles', JSON.stringify({ [pk]: { name: 'Flower Poster', t: Date.now() } }));
+ localStorage.setItem('btc-wallet-feed:' + k, 'following'); // new wallets open on Popular
}, [base, AUTHOR, NOTE_ID]);
await page.reload({ waitUntil: 'domcontentloaded' });
await waitText('receive', 20000);
- await page.evaluate(() => { const b = [...document.querySelectorAll('button')].find((e) => /message/i.test(e.getAttribute('aria-label') || '')); if (b) b.click(); });
- await sleep(1000);
- await page.evaluate(() => { const e = [...document.querySelectorAll('.item')].find((n) => /feed/i.test(n.textContent)); if (e) e.click(); });
+ // the Feed is a tab in the bottom nav
+ await page.evaluate(() => document.querySelector('.app-nav-button[aria-label="Feed"]').click());
for (let i = 0; i < 48; i++) { if (await page.$('.note-act')) break; await sleep(250); }
await sleep(600);
@@ -105,7 +108,7 @@ try {
await sleep(1500);
// the ellipsis sheet, and muting from it
- await page.evaluate(() => { const b = [...document.querySelectorAll('.btn-sm')].find((x) => x.textContent.trim() === '⋯'); if (b) b.click(); });
+ await page.evaluate(() => { const b = [...document.querySelectorAll('.notes-feed .btn-sm')].find((x) => x.textContent.trim() === '⋯'); if (b) b.click(); });
await sleep(600);
const sheet = await page.evaluate(() => { const s = document.querySelector('.confirm-pop'); return s ? s.innerText.replace(/\n+/g, ' | ') : ''; });
check('the ellipsis offers mute and block', /Mute/.test(sheet) && /Block/.test(sheet), sheet.slice(0, 70));
@@ -139,7 +142,11 @@ try {
return 'opened';
});
await sleep(1200);
- const img = await page.evaluate(() => { const i = document.querySelector('.chat-bubble img.note-img'); if (!i) return null; i.click(); return true; });
+ // a real tap on the picture itself (a tap beside a fitted picture is a tap on the post)
+ for (let i = 0; i < 20 && !(await page.evaluate(() => { const i = document.querySelector('.chat-bubble img.note-img'); return i && i.complete && i.naturalWidth > 0; })); i++) await sleep(250);
+ const at = await page.evaluate(() => { const i = document.querySelector('.chat-bubble img.note-img'); if (!i) return null; i.scrollIntoView({ block: 'center' }); const b = i.getBoundingClientRect(); return { x: b.left + b.width / 2, y: b.top + b.height / 2 }; });
+ const img = !!at;
+ if (at) await page.mouse.click(at.x, at.y);
await sleep(600);
check('an image in a DM opens full screen too', !!img && await page.evaluate(() => !!document.querySelector('.lightbox')), img ? 'tapped' : 'no image in the bubble (' + opened + ')');