aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAdam Soltys <[email protected]>2026-10-11 22:17:32 -0700
committerAdam Soltys <[email protected]>2026-10-11 22:17:32 -0700
commit4f49202c80662e617c9d666928b7e40df37cb9b8 (patch)
tree4be46a4a1aa4c3444f488c38843107beb137853c
parent8ff0bf21e308d4907cc2620d80f238a10341a28d (diff)
downloadcoinosv3-4f49202c80662e617c9d666928b7e40df37cb9b8.tar.gz
coinosv3-4f49202c80662e617c9d666928b7e40df37cb9b8.zip
Feed menu: Delete feed sits beside Edit. Dropping a feed you built meant opening its editor first (a saved timeline already had the drop in the ⋯ menu, having nothing to edit); the menu now offers Delete feed for every feed of yours, Edit above it where there is something to edit. The editor keeps its own Delete feed. feed-custom-test deletes "Coin talk" from the menu.
Co-Authored-By: Claude Fable 5.1 <[email protected]>
-rw-r--r--src/features/messages.js7
-rw-r--r--tools/feed-custom-test.js8
2 files changed, 10 insertions, 5 deletions
diff --git a/src/features/messages.js b/src/features/messages.js
index ef427eb..3bccd31 100644
--- a/src/features/messages.js
+++ b/src/features/messages.js
@@ -11024,9 +11024,10 @@ export function messagesFeature(ctx) {
def.builtin || visitor ? null
: adhocFeeds.has(def.id)
? item('\u{1F4BE}', t('feedSaveAdhoc'), () => (def.of ? saveTimelineFeed(def) : openFeedEditor(def)))
- // a saved timeline is the person, nothing to edit — only to drop
- : def.of ? item('\u{1F5D1}', t('feedDelete'), () => deleteFeed(def.id))
- : item('\u270e', t('feedEdit'), () => openFeedEditor(def)),
+ // a saved timeline is the person, nothing to edit — only to drop;
+ // the drop sits in the menu for every feed, not behind Edit
+ : [def.of ? null : item('\u270e', t('feedEdit'), () => openFeedEditor(def)),
+ item('\u{1F5D1}', t('feedDelete'), () => deleteFeed(def.id))],
h('button', { class: 'btn-ghost btn-block', onClick: close }, t('back'))));
}
// ---- a visitor at the action bar ---------------------------------------
diff --git a/tools/feed-custom-test.js b/tools/feed-custom-test.js
index c5c7c44..122cb0a 100644
--- a/tools/feed-custom-test.js
+++ b/tools/feed-custom-test.js
@@ -194,8 +194,12 @@ try {
await page.click('[aria-label="Feed options"]'); await sleep(300); // the editor lives in the feed's ⋯ menu now
await page.evaluate(() => [...document.querySelectorAll('.msg-sheet button')].find((b) => /edit feed/i.test(b.textContent)).click()); await sleep(400);
check('the editor shows what was saved', await page.evaluate(() => document.querySelector('input[placeholder="#bitcoin #nostr"]').value === '#bitcoin #lightning' && document.querySelector('input[type=checkbox]:not(.feed-all-toggle)').checked));
- await click('delete feed'); await sleep(1000);
- check('deleting it lands back on Following', JSON.stringify(await chips()) === JSON.stringify(['*Following', 'Popular', '#gardenstr', 'Pack feed', 'Everything', 'Follows + lists', '+']), JSON.stringify(await chips()));
+ await page.click('.chat-back'); await sleep(600);
+ // Delete feed sits in the ⋯ menu itself, not behind Edit
+ await page.click('[aria-label="Feed options"]'); await sleep(300);
+ check('the menu offers Delete feed beside Edit', await page.evaluate(() => { const b = [...document.querySelectorAll('.msg-sheet button')].map((x) => x.textContent); return b.some((x) => /edit feed/i.test(x)) && b.some((x) => /delete feed/i.test(x)); }));
+ await page.evaluate(() => [...document.querySelectorAll('.msg-sheet button')].find((b) => /delete feed/i.test(b.textContent)).click()); await sleep(1000);
+ check('deleting it from the menu lands back on Following', JSON.stringify(await chips()) === JSON.stringify(['*Following', 'Popular', '#gardenstr', 'Pack feed', 'Everything', 'Follows + lists', '+']), JSON.stringify(await chips()));
check('no page errors', errs.length === 0, errs.slice(0, 2).join(' | '));
} finally { await browser.close(); server.stop(true); }
console.log(ok ? '\n✅ feeds: Following is one of many' : '\n❌ failed');