@wular/coder 0.4.2 → 0.4.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/actions-FzDNxMFf.js +20 -0
- package/dist/{adapter-BKVzTDnn.js → adapter-7SEiVsmp.js} +1 -1
- package/dist/{adapter-B0oYCI0S.js → adapter-BLEfUqoQ.js} +1 -1
- package/dist/{adapter-DPInwbJG.js → adapter-H4GlcKQz.js} +1 -1
- package/dist/{add-DRsPpQFl.js → add-B50dIJGd.js} +1 -1
- package/dist/{add-DkpUwhtO.js → add-D7X3gxap.js} +1 -1
- package/dist/{add-C2y-mVzl.js → add-DOEUHIe7.js} +1 -1
- package/dist/{add-CLYTF_up.js → add-QExQhTzi.js} +1 -1
- package/dist/{add-json-5uPnWPoD.js → add-json-Ck4KIZrT.js} +1 -1
- package/dist/{agent-r5mMcehf.js → agent-BPtnEf1q.js} +1 -1
- package/dist/{agent-hw3zKw8y.js → agent-BlQ_dNNm.js} +2 -2
- package/dist/{alias-_0Rwf2cA.js → alias-BwQBovke.js} +1 -1
- package/dist/{app-oE8G1-bi.js → app-y6BYm2eH.js} +1 -1
- package/dist/{approvals-DbVrsxec.js → approvals-Cc9cq5T1.js} +2 -2
- package/dist/{approve-DeAhFL-m.js → approve-oO9k2fnK.js} +2 -2
- package/dist/{apps-eujHiNca.js → apps-CU2YalX8.js} +1 -1
- package/dist/{archive-BCUfymIB.js → archive-C5c_HQS1.js} +2 -2
- package/dist/{archive-DZ6vpMHb.js → archive-CemlWlVY.js} +2 -2
- package/dist/archive-sweep-ehg-fWIt.js +1 -0
- package/dist/{args-BOEEdpWk.js → args-DcBCtXhz.js} +1 -1
- package/dist/{ask-BU2WVxVM.js → ask-Chu7Twu_.js} +2 -2
- package/dist/auth-BOyXPOtu.js +1 -0
- package/dist/auth-XbqKSbcD.js +1 -0
- package/dist/{chat-bridge-BS9WtP3X.js → chat-bridge-DXgZItGP.js} +1 -1
- package/dist/{chat-B_yhNTo0.js → chat-cknlIhVh.js} +1 -1
- package/dist/{cli-DWCR7iqa.js → cli-B1ObVrL4.js} +5 -5
- package/dist/cli.d.ts +1 -1
- package/dist/cli.js +1 -1
- package/dist/{client-D9IoAuDD.js → client-31YzOj-i.js} +1 -1
- package/dist/{config-12pK4qW7.js → config-DAE_qHYA.js} +1 -1
- package/dist/{create-D3f6q0Yq.js → create-CM8B8JxD.js} +1 -1
- package/dist/credentials-BXD4Qptk.js +1 -0
- package/dist/dash/manifest.json +949 -915
- package/dist/dash/public/assets/chunks/{agent-pills-dd0b7643e125bbf1.js → agent-pills-b6a6da91c9559d9f.js} +1 -1
- package/dist/dash/public/assets/chunks/{agent-settings-form-45ae6aeaaed2b568.js → agent-settings-form-b615c677046cd6f2.js} +1 -1
- package/dist/dash/public/assets/chunks/agents-grid-f2e7b4ff9e11b6e3.js +1 -0
- package/dist/dash/public/assets/chunks/{badge-676b01e0c615bf7b.js → badge-215c7b2631dafc69.js} +1 -1
- package/dist/dash/public/assets/chunks/{card-e0901d68b79dfa93.js → card-e86dcc81326d2b14.js} +1 -1
- package/dist/dash/public/assets/chunks/{combo-952a457d52360d88.js → combo-09e246dc9a517fa8.js} +1 -1
- package/dist/dash/public/assets/chunks/composer-417166b029f48c47.js +1 -0
- package/dist/dash/public/assets/chunks/composer-645ae8fa97a35280.js +1 -0
- package/dist/dash/public/assets/chunks/{confirm-f2fe4ba9905a89c6.js → confirm-5ae484241ad888fd.js} +1 -1
- package/dist/dash/public/assets/chunks/{connect-apps-661f3b3a85f1776a.js → connect-apps-4147c45f45fde2b1.js} +1 -1
- package/dist/dash/public/assets/chunks/{connect-repositories-5389ec8701a3deac.js → connect-repositories-77591110836bdf03.js} +1 -1
- package/dist/dash/public/assets/chunks/credentials-list-e005a0783ec93465.js +2 -0
- package/dist/dash/public/assets/chunks/{custom-range-03ba6fb2ade7d282.js → custom-range-463e119af4681c61.js} +1 -1
- package/dist/dash/public/assets/chunks/{editor-34cb529d6d8a4b09.js → editor-804b84f4fe6539cd.js} +4 -4
- package/dist/dash/public/assets/chunks/{engines-list-2f1acee3ecc8461a.js → engines-list-ceab51f13c690e8c.js} +1 -1
- package/dist/dash/public/assets/chunks/{field-901f1f35c18c39c9.js → field-aa0a4b98a976781e.js} +1 -1
- package/dist/dash/public/assets/chunks/filter-91144ac2eec6297f.js +1 -0
- package/dist/dash/public/assets/chunks/format-105c706345987fb2.js +1 -0
- package/dist/dash/public/assets/chunks/heads-a42817b32d2d7f08.js +1 -0
- package/dist/dash/public/assets/chunks/{instructions-052fa45a9daf6db6.js → instructions-3a1dcaff2d868aa5.js} +1 -1
- package/dist/dash/public/assets/chunks/instructions-6c6f981fffaa31e4.js +1 -0
- package/dist/dash/public/assets/chunks/{list-87b359bebd26986a.js → list-7270361464fc3c04.js} +1 -1
- package/dist/dash/public/assets/chunks/{mcp-list-b42f0d2ee463b37d.js → mcp-list-2e715d48666b54ad.js} +1 -1
- package/dist/dash/public/assets/chunks/{models-list-0669d26fd662aec3.js → models-list-d3c40f94c761a6e5.js} +1 -1
- package/dist/dash/public/assets/chunks/paged-3ddb6077bef42752.js +1 -0
- package/dist/dash/public/assets/chunks/{platform-actions-c92ca3c6198a9387.js → platform-actions-271ec3b99a64280b.js} +1 -1
- package/dist/dash/public/assets/chunks/runners-list-767e49c7d0ec833a.js +1 -0
- package/dist/dash/public/assets/chunks/{segmented-358ff2b4992b8384.js → segmented-de4386ccaac7304d.js} +1 -1
- package/dist/dash/public/assets/chunks/{select-1013702bdfb1ade4.js → select-a90307706cffa6e0.js} +1 -1
- package/dist/dash/public/assets/chunks/{sentinel-c972a33dc69a5135.js → sentinel-b5e032b38604dfd3.js} +1 -1
- package/dist/dash/public/assets/chunks/shared-init-7f81ae7bc8c82438.js +2 -0
- package/dist/dash/public/assets/chunks/shared-init-933c7f9ee85be766.js +5 -0
- package/dist/dash/public/assets/chunks/{tail-7c27aab8ba268bd9.js → tail-4891e727ee526792.js} +1 -1
- package/dist/dash/public/assets/chunks/task-actions-ce854925a2dc78fd.js +1 -0
- package/dist/dash/public/assets/chunks/task-ddfddeaf07fb684c.js +1 -0
- package/dist/dash/public/assets/chunks/task-view-c37dcee08f21a279.js +5 -0
- package/dist/dash/public/assets/chunks/tasks-list-baef587999f322d8.js +1 -0
- package/dist/dash/public/assets/chunks/{toolbar-f964fa864699f095.js → toolbar-8d98313606ad8a2d.js} +1 -1
- package/dist/dash/public/assets/chunks/{versions-list-fc2e0d2a7382e049.js → versions-list-532690efd9f1b0ea.js} +1 -1
- package/dist/dash/public/assets/{dash-account-96fc41be318839fa.css → dash-account-edc56e85dbaaabe0.css} +1 -1
- package/dist/dash/public/assets/dash-agents-edba57b67e4005d0.css +1 -0
- package/dist/dash/public/assets/dash-agents-new-fe22253fbada2fbf.css +1 -0
- package/dist/dash/public/assets/dash-agents-param-slug-adf52e9dacb2d825.css +1 -0
- package/dist/dash/public/assets/dash-agents-param-slug-edit-a2937a347689ef29.css +1 -0
- package/dist/dash/public/assets/dash-agents-param-slug-platforms-265ba13db32a460d.css +1 -0
- package/dist/dash/public/assets/dash-agents-param-slug-settings-8afc52eb0372bc4b.css +1 -0
- package/dist/dash/public/assets/dash-agents-param-slug-tasks-6193e646be68dbd2.css +1 -0
- package/dist/dash/public/assets/dash-agents-param-slug-usage-ceadb3a1c911c402.css +1 -0
- package/dist/dash/public/assets/{dash-settings-53b8e6a8f656fa1a.css → dash-settings-cf1997cd7f72e518.css} +1 -1
- package/dist/dash/public/assets/dash-settings-param-tab-b44dac8e79a560e6.css +1 -0
- package/dist/dash/public/assets/dash-tasks-916c7100a8058aa3.css +1 -0
- package/dist/dash/public/assets/dash-tasks-param-id-194a6ffc20e872f2.css +1 -0
- package/dist/dash/public/assets/{dash-usage-884943221f76ad93.css → dash-usage-40940b289f85e0b6.css} +1 -1
- package/dist/dash/public/assets/pnext-client-13aee92bef5c9e3f.js +1 -0
- package/dist/dash/public/assets/pnext-client-1f2686b2044f0df6.js +1 -0
- package/dist/dash/public/assets/pnext-client-26130234ebad7067.js +1 -0
- package/dist/dash/public/assets/pnext-client-311e35b0076bf406.js +1 -0
- package/dist/dash/public/assets/pnext-client-4ade1bf75c9c3d87.js +1 -0
- package/dist/dash/public/assets/pnext-client-61cd31b687ede1da.js +1 -0
- package/dist/dash/public/assets/{pnext-client-2693db10b197ade1.js → pnext-client-61db65dc4223217a.js} +1 -1
- package/dist/dash/public/assets/pnext-client-6ea656e7705e3f2a.js +1 -0
- package/dist/dash/public/assets/pnext-client-7fd0f793f0322cb9.js +1 -0
- package/dist/dash/public/assets/pnext-client-88159c0840fcfa4a.js +1 -0
- package/dist/dash/public/assets/pnext-client-b03f0c47c066b4f3.js +1 -0
- package/dist/dash/public/assets/{pnext-client-1afa4148bea69ad2.js → pnext-client-d6478835f543f901.js} +1 -1
- package/dist/dash/public/assets/pnext-client-dadb8359021ed590.js +1 -0
- package/dist/dash/public/assets/pnext-client-de07532d6aaebf2c.js +1 -0
- package/dist/dash/public/assets/pnext-client-f87a31890c8ff224.js +1 -0
- package/dist/dash/public/assets/pnext-client-ffe1c123a8e2a350.js +1 -0
- package/dist/{default-CwQXCtoB.js → default-BMvUMTFp.js} +1 -1
- package/dist/default-B_nKaX0-.js +1 -0
- package/dist/{delete-cS01oOIb.js → delete-Bjteibld.js} +2 -2
- package/dist/{delete-BD6AnCLg.js → delete-riCIKZwj.js} +2 -2
- package/dist/{disable-BMWWeYFQ.js → disable-DQC56YFy.js} +1 -1
- package/dist/{discover-Dvr_3_Xr.js → discover-Qanr5TEO.js} +1 -1
- package/dist/{discover-Cfx5RPU7.js → discover-lgTYwoQp.js} +2 -2
- package/dist/dispatch-BsW_1m7e.js +14 -0
- package/dist/{docs-DWegDRiu.js → docs-DFs7lOJp.js} +1 -1
- package/dist/{docs-BX65z2Iu.js → docs-DKROso-4.js} +2 -2
- package/dist/{enable-Cfzeau2x.js → enable-D2DqZvcU.js} +1 -1
- package/dist/{env-CRf6wkM2.js → env-YRY3I60r.js} +1 -1
- package/dist/exec-DuUkLMqg.js +11 -0
- package/dist/executor-vMppVLB6.js +10 -0
- package/dist/flow/builtin/review.js +1 -1
- package/dist/flow/index.d.ts +1 -1
- package/dist/flow/index.js +1 -1
- package/dist/{flow-kAxxVOiR.js → flow-DmERAnR8.js} +1 -1
- package/dist/{github-actions-DwUzm4hC.js → github-actions-C_NkHVJq.js} +1 -1
- package/dist/http-D01Udu4u.js +1 -0
- package/dist/{index-CZjFX5zV.d.ts → index-B1L4zXZH.d.ts} +2 -1
- package/dist/{init-C4tDFH4G.js → init-Bd6JHzBc.js} +1 -1
- package/dist/integrations-B2CavXR1.js +5 -0
- package/dist/integrations-D1Dwy1kt.js +1 -0
- package/dist/lib/broker.js +2 -2
- package/dist/{list-DuPqU3fk.js → list-4Uo-0v9s.js} +1 -1
- package/dist/{list-COAo7eZd.js → list-B0ujEZhd.js} +3 -3
- package/dist/{list-5Ljf9TxF.js → list-B5oa1Bhy.js} +2 -2
- package/dist/{list-vOvIpbOH.js → list-BjE_l6la.js} +1 -1
- package/dist/{list-J8d_zh-o.js → list-Ck9ibCs1.js} +1 -1
- package/dist/{list-vpyS-hv8.js → list-DhgK4Zc4.js} +1 -1
- package/dist/{list-way5oLO0.js → list-KvL7AUhD.js} +2 -2
- package/dist/{list-DzGuMkQy.js → list-byYLBl1U.js} +1 -1
- package/dist/{load-BpEsAn51.js → load-SnZd7xG1.js} +1 -1
- package/dist/{local-H3uvqEbq.js → local-BRy1EUq2.js} +1 -1
- package/dist/log-view-DeJstSkw.js +3 -0
- package/dist/{login-BBw95-S3.js → login-C-ahtDKV.js} +1 -1
- package/dist/{login-CNmeRAL7.js → login-zpwke8g1.js} +1 -1
- package/dist/{logout-j0dTo_Ib.js → logout-CI6Kf-T6.js} +1 -1
- package/dist/{maintenance-DkLVtqM7.js → maintenance-BAzr9Jlr.js} +1 -1
- package/dist/{match-CXAjDhg7.js → match-DxV1d49D.js} +1 -1
- package/dist/{mcp-BgKb2Cdk.js → mcp-CmcL1MCG.js} +1 -1
- package/dist/{mcp-CsmBtlW9.js → mcp-mhXwtGQT.js} +1 -1
- package/dist/{migrate-N-85_N7J.js → migrate-Czh3TEK5.js} +1 -1
- package/dist/{migrate-D4nzYhk8.js → migrate-w7KfzUAR.js} +1 -1
- package/dist/{model-B79MFtRV.js → model-JRoTH9QK.js} +1 -1
- package/dist/models-C-S7HqSb.js +1 -0
- package/dist/{prompt-CEuBMNhk.js → prompt-CMXmt2l9.js} +4 -4
- package/dist/{push-DbdnbZYt.js → push-B8BhTyZs.js} +1 -1
- package/dist/queue-CirjEskI.js +117 -0
- package/dist/refresh-Bmy2r1Ee.js +1 -0
- package/dist/{remote-miQNTVRa.js → remote-CxFnEjZl.js} +1 -1
- package/dist/{remove-BNzbUhaK.js → remove-C15WLaXT.js} +1 -1
- package/dist/{remove-D-QeeZQL.js → remove-CTZYjjSr.js} +1 -1
- package/dist/{remove-CLpL12Ya.js → remove-CTl-H0f0.js} +1 -1
- package/dist/{remove-CaYH9Cna.js → remove-DX2FVo5b.js} +1 -1
- package/dist/rename-D1g4TnHQ.js +1 -0
- package/dist/{result-BfTfJayl.js → result-D49VN8PM.js} +3 -3
- package/dist/result-DGWyUHYU.js +18 -0
- package/dist/{resume-aZ8yWDBh.js → resume-ywzc7z6A.js} +2 -2
- package/dist/{review-BEhDcX4b.js → review-ZC0xG8XY.js} +2 -2
- package/dist/{rotate-key-BqnKhTK8.js → rotate-key-Bf8_99ck.js} +1 -1
- package/dist/{run-BWbabvub.js → run-D7SJ-ieT.js} +2 -2
- package/dist/run-DoRQSC_K.js +2 -0
- package/dist/{run-BdPjxaZU.js → run-ukCf2Mdy.js} +1 -1
- package/dist/runner-D-REfOUe.js +1 -0
- package/dist/{runner-sUpWJ_k0.js → runner-wDYhkVsM.js} +1 -1
- package/dist/schema-DoNO0dPh.js +1 -0
- package/dist/sdk.d.ts +4 -2
- package/dist/sdk.js +1 -1
- package/dist/serve-BJ_Mbm2m.js +8 -0
- package/dist/{serve-C0WC-QrV.js → serve-C1MMhM1F.js} +2 -2
- package/dist/{serve-CcObDKKQ.js → serve-DtrOHaoS.js} +2 -2
- package/dist/{serve-Ck95047c.js → serve-P9pFkEnE.js} +1 -1
- package/dist/{serve-BTeomYxW.js → serve-yjSw0B1a.js} +1 -1
- package/dist/{server-BxLFZL80.js → server-DDWTnmbx.js} +1 -1
- package/dist/{setup-host-DLd_j2Uw.js → setup-host-L6Rnn5Cz.js} +1 -1
- package/dist/{shared-BLkGRKty.js → shared-XsUX_ZZb.js} +1 -1
- package/dist/{show-DzoQIs75.js → show-CU-jqJ90.js} +1 -1
- package/dist/{show-FC3dJcD-.js → show-DVJmB2u-.js} +1 -1
- package/dist/{status-BU3DR1XU.js → status-CBydR7LE.js} +1 -1
- package/dist/{steer-P_38hRRD.js → steer-Cm_sHZqs.js} +2 -2
- package/dist/{stop-BJGDRPsp.js → stop-DJS7DAPJ.js} +1 -1
- package/dist/{stop-BWY6k6v5.js → stop-TrebIIuv.js} +2 -2
- package/dist/store-BrNMqJgk.js +42 -0
- package/dist/store-j8icrG0v.js +19 -0
- package/dist/task-C8lmcNsf.js +1 -0
- package/dist/{task-DeglY79z.js → task-CpUI19o2.js} +4 -4
- package/dist/task-CvSqiwxo.js +1 -0
- package/dist/{test-BrSrhop9.js → test-CDKz4jY_.js} +1 -1
- package/dist/{tools-CgswhJzh.js → tools-DBFeoosk.js} +1 -1
- package/dist/{types-I5Cwtl_K.d.ts → types-DMGBYB_K.d.ts} +3 -1
- package/dist/{unalias-mMHXqok7.js → unalias-BfQFBnuK.js} +1 -1
- package/dist/{update-DbOWToPy.js → update-C4FFOie8.js} +1 -1
- package/dist/{upgrade-D6oC9HQI.js → upgrade-DLJqMnUQ.js} +2 -2
- package/dist/{usage-Cb8Dtv9V.js → usage-CSh-xwQ2.js} +1 -1
- package/dist/{usage-DMs-IIJC.js → usage-D8mc4qXK.js} +1 -1
- package/dist/{watch-BcMQXGYO.js → watch-CQu-tJKZ.js} +2 -2
- package/dist/{watch-eE2XiwsC.js → watch-DmwaEvoi.js} +2 -2
- package/dist/{wire-BeT1Axeo.js → wire-DzGLZ3-O.js} +1 -1
- package/dist/worker-BLKTMLqa.js +1 -0
- package/dist/worker-nHemduM_.js +9 -0
- package/dist/{workflow-Cshghoas.js → workflow-IrouAus_.js} +1 -1
- package/docs/mcp.md +1 -1
- package/migrations/0000_initial.sql +8 -0
- package/migrations/meta/0000_snapshot.json +75 -1
- package/migrations/meta/_journal.json +1 -1
- package/package.json +1 -1
- package/plugins/agents/skills/coder/SKILL.md +1 -0
- package/plugins/claude/.claude-plugin/plugin.json +1 -1
- package/plugins/claude/skills/dispatch/SKILL.md +1 -1
- package/plugins/cursor/.cursor-plugin/plugin.json +1 -1
- package/plugins/cursor/skills/coder/SKILL.md +1 -0
- package/src/client/index.ts +10 -2
- package/src/client/types.ts +18 -0
- package/src/core/defaults.ts +11 -0
- package/src/core/task/log-view.ts +120 -6
- package/src/server/dash/app/dash/agents/(list)/agent-menu.tsx +4 -0
- package/src/server/dash/app/dash/agents/(list)/agents-grid.tsx +18 -35
- package/src/server/dash/app/dash/agents/(list)/loading.tsx +7 -1
- package/src/server/dash/app/dash/agents/[slug]/(tabs)/layout.tsx +2 -1
- package/src/server/dash/app/dash/layout.tsx +13 -3
- package/src/server/dash/app/dash/settings/[tab]/credentials-list.tsx +20 -13
- package/src/server/dash/app/dash/settings/[tab]/runners-list.tsx +13 -12
- package/src/server/dash/app/dash/tasks/[id]/activity.tsx +49 -4
- package/src/server/dash/app/dash/tasks/[id]/task-actions.tsx +43 -6
- package/src/server/dash/app/dash/tasks/[id]/task-view.css +52 -31
- package/src/server/dash/app/dash/tasks/[id]/task-view.tsx +143 -51
- package/src/server/dash/app/dash/tasks/composer.css +4 -0
- package/src/server/dash/app/dash/tasks/composer.tsx +6 -5
- package/src/server/dash/app/dash/tasks/list/task.ts +29 -1
- package/src/server/dash/app/dash/tasks/list/tasks-list.css +20 -7
- package/src/server/dash/app/dash/tasks/list/tasks-list.tsx +256 -109
- package/src/server/dash/app/dash/tasks/list/tasks-section.tsx +9 -13
- package/src/server/dash/app/dash/tasks/page.tsx +3 -35
- package/src/server/dash/comps/frame/loading-card.tsx +4 -3
- package/src/server/dash/comps/frame/page-head.css +10 -0
- package/src/server/dash/comps/frame/page-head.tsx +3 -2
- package/src/server/dash/comps/frame/task-toasts.tsx +196 -50
- package/src/server/dash/comps/nav/side-toggle.tsx +15 -4
- package/src/server/dash/comps/ui/card.css +1 -0
- package/src/server/dash/comps/ui/filter.css +64 -0
- package/src/server/dash/comps/ui/filter.tsx +336 -0
- package/src/server/dash/comps/ui/icons.ts +2 -0
- package/src/server/dash/comps/ui/menu.tsx +4 -0
- package/src/server/dash/comps/ui/select.tsx +2 -2
- package/src/server/dash/comps/ui/toolbar.css +14 -0
- package/src/server/dash/utils/client.ts +21 -0
- package/src/server/dash/utils/format.ts +12 -4
- package/src/server/dash/utils/paged.ts +14 -6
- package/dist/actions-Mk3FSlpJ.js +0 -20
- package/dist/archive-sweep-Cxbh8yAI.js +0 -1
- package/dist/auth-CBWTmAPA.js +0 -1
- package/dist/auth-Dmn2U7rr.js +0 -1
- package/dist/credentials-l6dsrZLL.js +0 -1
- package/dist/dash/public/assets/chunks/agents-grid-b906da80c31fc035.js +0 -1
- package/dist/dash/public/assets/chunks/composer-49f9e7c5c4dfda3b.js +0 -1
- package/dist/dash/public/assets/chunks/composer-f331d00837143aee.js +0 -1
- package/dist/dash/public/assets/chunks/credentials-list-e6177d0943517929.js +0 -2
- package/dist/dash/public/assets/chunks/format-eb03fc9d9744d960.js +0 -1
- package/dist/dash/public/assets/chunks/heads-1570a3a6db331979.js +0 -1
- package/dist/dash/public/assets/chunks/instructions-d0a4b0d95009c262.js +0 -1
- package/dist/dash/public/assets/chunks/paged-bc6fa0c2b9d52ed7.js +0 -1
- package/dist/dash/public/assets/chunks/runners-list-9fffa50432c470c9.js +0 -1
- package/dist/dash/public/assets/chunks/shared-init-20e199043ff5d00f.js +0 -2
- package/dist/dash/public/assets/chunks/shared-init-88cce66bb3cfe1e5.js +0 -5
- package/dist/dash/public/assets/chunks/task-actions-a9603d520434baab.js +0 -1
- package/dist/dash/public/assets/chunks/task-fa8b82e95e771c4a.js +0 -1
- package/dist/dash/public/assets/chunks/task-view-f7039cb330bcb0b5.js +0 -3
- package/dist/dash/public/assets/chunks/tasks-list-2a905b4a0c3a9042.js +0 -1
- package/dist/dash/public/assets/dash-agents-290a7b21c7dc0c92.css +0 -1
- package/dist/dash/public/assets/dash-agents-new-a7a07bf4ebda24c2.css +0 -1
- package/dist/dash/public/assets/dash-agents-param-slug-69a72fb0bbd14cc2.css +0 -1
- package/dist/dash/public/assets/dash-agents-param-slug-edit-397bdfb2f0ca328c.css +0 -1
- package/dist/dash/public/assets/dash-agents-param-slug-platforms-a7b3b7247c27f1d2.css +0 -1
- package/dist/dash/public/assets/dash-agents-param-slug-settings-8389b7d0555e8ccf.css +0 -1
- package/dist/dash/public/assets/dash-agents-param-slug-tasks-5987b8aea5e8f30d.css +0 -1
- package/dist/dash/public/assets/dash-agents-param-slug-usage-19abc69e1d4e6b0a.css +0 -1
- package/dist/dash/public/assets/dash-settings-param-tab-ac61fdfdd6fd533f.css +0 -1
- package/dist/dash/public/assets/dash-tasks-cc0b1d32874b731c.css +0 -1
- package/dist/dash/public/assets/dash-tasks-param-id-02b8c7bd99cc1090.css +0 -1
- package/dist/dash/public/assets/pnext-client-17ba55bb57a1f4da.js +0 -1
- package/dist/dash/public/assets/pnext-client-43f52a07f8067b1b.js +0 -1
- package/dist/dash/public/assets/pnext-client-4594b693fe612835.js +0 -1
- package/dist/dash/public/assets/pnext-client-73f73e24f8141fb6.js +0 -1
- package/dist/dash/public/assets/pnext-client-7574da4651b40eae.js +0 -1
- package/dist/dash/public/assets/pnext-client-7b3a2c1092cbbb02.js +0 -1
- package/dist/dash/public/assets/pnext-client-816fe5fc96d3f768.js +0 -1
- package/dist/dash/public/assets/pnext-client-86cb956b448b0887.js +0 -1
- package/dist/dash/public/assets/pnext-client-8b64e3c030164288.js +0 -1
- package/dist/dash/public/assets/pnext-client-8f6161084c595a22.js +0 -1
- package/dist/dash/public/assets/pnext-client-9203ec11926e5d04.js +0 -1
- package/dist/dash/public/assets/pnext-client-a38b446f941d44df.js +0 -1
- package/dist/dash/public/assets/pnext-client-bd8d51aaa095e8a4.js +0 -1
- package/dist/dash/public/assets/pnext-client-e9821d1f1bdb281d.js +0 -1
- package/dist/default-De8FXiWz.js +0 -1
- package/dist/dispatch-BKeAch9E.js +0 -14
- package/dist/exec-RZFLclKX.js +0 -11
- package/dist/executor-BvAA7Cgw.js +0 -10
- package/dist/http-Bkg_OQ6r.js +0 -1
- package/dist/integrations-BAgdVDhj.js +0 -5
- package/dist/integrations-D-L3uQRj.js +0 -1
- package/dist/log-view-dg0TlKLA.js +0 -1
- package/dist/models-_5LVGC3m.js +0 -1
- package/dist/queue-C9fSdE_X.js +0 -116
- package/dist/refresh-BDmap1RA.js +0 -1
- package/dist/rename-Bhcb4t9F.js +0 -1
- package/dist/result-D8DsvJDu.js +0 -15
- package/dist/run-Dqe38jX8.js +0 -2
- package/dist/runner-BPpiJvHx.js +0 -1
- package/dist/schema-CU2iFkp8.js +0 -1
- package/dist/serve-DA5I2qXj.js +0 -4
- package/dist/store-B3ZHoBJY.js +0 -8
- package/dist/store-BLi19UDE.js +0 -42
- package/dist/task-C6VAg5WU.js +0 -1
- package/dist/task-b2BK481M.js +0 -1
- package/dist/worker-CXndxmGF.js +0 -9
- package/dist/worker-DrucI22w.js +0 -1
|
@@ -5,7 +5,7 @@ import '@/comps/ui/toast.css';
|
|
|
5
5
|
import { useEffect, useRef, useState } from 'preact/hooks';
|
|
6
6
|
|
|
7
7
|
import { serverEvents } from '@coder/client';
|
|
8
|
-
import type { TaskRow, TaskState } from '@coder/client/types';
|
|
8
|
+
import type { TaskEvent, TaskRow, TaskState } from '@coder/client/types';
|
|
9
9
|
import { client } from '@/utils/client';
|
|
10
10
|
import { Link } from '@wular/pnext/link';
|
|
11
11
|
import { usePathname, useRouter } from '@wular/pnext/navigation/client';
|
|
@@ -13,7 +13,7 @@ import { Status, STATUS_LABEL } from '@/app/dash/tasks/list/status';
|
|
|
13
13
|
|
|
14
14
|
type Watched = { title: string; status: TaskState; at: number };
|
|
15
15
|
type Live = Pick<TaskRow, 'status' | 'result' | 'error' | 'approval'>;
|
|
16
|
-
type Toast = { key: string; id?: string; title: string; status?: TaskState; line: string };
|
|
16
|
+
type Toast = { key: string; id?: string; title: string; status?: TaskState; line: string; err?: boolean };
|
|
17
17
|
|
|
18
18
|
const WATCHED = 'coder:watched';
|
|
19
19
|
export const NOTIFY = 'coder:notify';
|
|
@@ -21,11 +21,18 @@ const TOAST = 'coder:toast';
|
|
|
21
21
|
const DONE = new Set<TaskState>(['completed', 'failed', 'cancelled']);
|
|
22
22
|
const SHOWN = new Set<TaskState>([...DONE, 'waiting']);
|
|
23
23
|
const KEEP = 20;
|
|
24
|
-
const STREAMS = 3;
|
|
25
24
|
const MAX = 3;
|
|
26
25
|
const TTL = 8000;
|
|
27
|
-
//
|
|
28
|
-
const
|
|
26
|
+
// The Web Lock that picks the one tab holding the events stream, and the channel it shares them on.
|
|
27
|
+
const EVENTS = 'coder:events';
|
|
28
|
+
const TASK = 'coder:task';
|
|
29
|
+
const REPLAY = 'coder:task-replay';
|
|
30
|
+
const RESET = 'coder:task-reset';
|
|
31
|
+
const RESYNC = 'coder:task-resync';
|
|
32
|
+
// A write that commits past the server's look-back still reaches shown pages within this, through a fresh read.
|
|
33
|
+
const RESYNC_MS = 60_000;
|
|
34
|
+
// Latest events a tab keeps, so a page that mounts later starts from them.
|
|
35
|
+
const LATEST = 200;
|
|
29
36
|
|
|
30
37
|
const read = (): Record<string, Watched> => {
|
|
31
38
|
try {
|
|
@@ -43,9 +50,11 @@ const save = (all: Record<string, Watched>) => {
|
|
|
43
50
|
dispatchEvent(new Event(WATCHED));
|
|
44
51
|
};
|
|
45
52
|
|
|
46
|
-
/**
|
|
47
|
-
export const
|
|
48
|
-
dispatchEvent(new CustomEvent(TOAST, { detail: { title, line } }));
|
|
53
|
+
/** A toast for an action whose page has no room for its outcome. */
|
|
54
|
+
export const showToast = (title: string, line: string, err?: boolean) =>
|
|
55
|
+
dispatchEvent(new CustomEvent(TOAST, { detail: { title, line, err } }));
|
|
56
|
+
|
|
57
|
+
export const toastError = (title: string, line: string) => showToast(title, line, true);
|
|
49
58
|
|
|
50
59
|
/** Remembers a task this browser started or opened, so its finish shows a toast on any page. */
|
|
51
60
|
export function watchTask(id: string, status: TaskState, title?: string) {
|
|
@@ -74,34 +83,151 @@ function lineOf(live: Live): string {
|
|
|
74
83
|
return text(live.error) || (live.status === 'failed' ? 'It failed.' : 'It was stopped.');
|
|
75
84
|
}
|
|
76
85
|
|
|
77
|
-
/**
|
|
78
|
-
function
|
|
86
|
+
/** Hears every task change from this browser's one events stream; `reset` when some may have been missed, `resync` once a minute to read again. */
|
|
87
|
+
export function useTaskEvents(
|
|
88
|
+
on: (event: TaskEvent) => void,
|
|
89
|
+
reset?: () => void,
|
|
90
|
+
resync?: () => void,
|
|
91
|
+
) {
|
|
92
|
+
const handler = useRef({ on, reset, resync });
|
|
93
|
+
handler.current = { on, reset, resync };
|
|
94
|
+
useEffect(() => {
|
|
95
|
+
const listener = (event: Event) => handler.current.on((event as CustomEvent<TaskEvent>).detail);
|
|
96
|
+
const again = () => handler.current.reset?.();
|
|
97
|
+
const read = () => handler.current.resync?.();
|
|
98
|
+
addEventListener(TASK, listener);
|
|
99
|
+
addEventListener(RESET, again);
|
|
100
|
+
addEventListener(RESYNC, read);
|
|
101
|
+
dispatchEvent(
|
|
102
|
+
new CustomEvent(REPLAY, { detail: (event: TaskEvent) => handler.current.on(event) }),
|
|
103
|
+
);
|
|
104
|
+
return () => {
|
|
105
|
+
removeEventListener(TASK, listener);
|
|
106
|
+
removeEventListener(RESET, again);
|
|
107
|
+
removeEventListener(RESYNC, read);
|
|
108
|
+
};
|
|
109
|
+
}, []);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
type Message = { hello?: true; id?: string; event?: TaskEvent; reset?: true; resync?: true };
|
|
113
|
+
|
|
114
|
+
/** One events stream per browser: the tab holding the lock reads it, shares it on a channel, and a tab that takes over resumes from the last event id. */
|
|
115
|
+
function useEventsStream(ids: string[], leading: { current: boolean }) {
|
|
116
|
+
const asked = useRef(ids);
|
|
117
|
+
asked.current = ids;
|
|
118
|
+
const current = useRef<{ key: string; abort: AbortController }>();
|
|
119
|
+
const key = [...ids].sort().join(',');
|
|
120
|
+
|
|
79
121
|
useEffect(() => {
|
|
122
|
+
const latest = new Map<string, TaskEvent>();
|
|
123
|
+
const deliver = (event: TaskEvent) => {
|
|
124
|
+
latest.delete(event.id);
|
|
125
|
+
latest.set(event.id, event);
|
|
126
|
+
if (latest.size > LATEST) latest.delete(latest.keys().next().value!);
|
|
127
|
+
dispatchEvent(new CustomEvent(TASK, { detail: event }));
|
|
128
|
+
};
|
|
129
|
+
const replay = (event: Event) => {
|
|
130
|
+
for (const each of latest.values())
|
|
131
|
+
(event as CustomEvent<(e: TaskEvent) => void>).detail(each);
|
|
132
|
+
};
|
|
133
|
+
addEventListener(REPLAY, replay);
|
|
134
|
+
const channel =
|
|
135
|
+
typeof BroadcastChannel !== 'undefined' && navigator.locks
|
|
136
|
+
? new BroadcastChannel(EVENTS)
|
|
137
|
+
: undefined;
|
|
80
138
|
const abort = new AbortController();
|
|
139
|
+
let last: string | undefined;
|
|
140
|
+
let wake = () => {};
|
|
141
|
+
let soon: ReturnType<typeof setTimeout> | undefined;
|
|
142
|
+
const receive = (message: Message) => {
|
|
143
|
+
last = message.id ?? last;
|
|
144
|
+
if (message.event) deliver(message.event);
|
|
145
|
+
if (message.resync) dispatchEvent(new Event(RESYNC));
|
|
146
|
+
if (!message.reset) return;
|
|
147
|
+
latest.clear();
|
|
148
|
+
dispatchEvent(new Event(RESET));
|
|
149
|
+
};
|
|
150
|
+
channel?.addEventListener('message', ({ data }: MessageEvent<Message>) => {
|
|
151
|
+
if (!data.hello) return receive(data);
|
|
152
|
+
// A tab that just loaded, maybe into another workspace: the next stream resumes for it too.
|
|
153
|
+
soon ??= setTimeout(() => {
|
|
154
|
+
soon = undefined;
|
|
155
|
+
current.current?.abort.abort();
|
|
156
|
+
wake();
|
|
157
|
+
}, 300);
|
|
158
|
+
});
|
|
159
|
+
channel?.postMessage({ hello: true });
|
|
160
|
+
|
|
161
|
+
const lead = async () => {
|
|
162
|
+
leading.current = true;
|
|
163
|
+
const resync = setInterval(() => {
|
|
164
|
+
channel?.postMessage({ resync: true });
|
|
165
|
+
receive({ resync: true });
|
|
166
|
+
}, RESYNC_MS);
|
|
167
|
+
try {
|
|
168
|
+
await follow();
|
|
169
|
+
} finally {
|
|
170
|
+
clearInterval(resync);
|
|
171
|
+
}
|
|
172
|
+
};
|
|
173
|
+
|
|
81
174
|
const follow = async () => {
|
|
82
175
|
while (!abort.signal.aborted) {
|
|
176
|
+
const once = new AbortController();
|
|
177
|
+
const stop = () => once.abort();
|
|
178
|
+
abort.signal.addEventListener('abort', stop);
|
|
179
|
+
const ids = asked.current;
|
|
180
|
+
current.current = { key: [...ids].sort().join(','), abort: once };
|
|
181
|
+
let wait = 1000;
|
|
83
182
|
try {
|
|
84
|
-
const response = await client.tasks.
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
183
|
+
const response = await client.tasks.events(ids, last, once.signal);
|
|
184
|
+
// A server without the events stream: nothing to follow.
|
|
185
|
+
if (response.status === 404) return void (leading.current = false);
|
|
186
|
+
// Signed out: a tab that signs in again wakes the next try.
|
|
187
|
+
if (!response.ok || !response.body)
|
|
188
|
+
wait = [401, 403].includes(response.status) ? 60_000 : 5000;
|
|
189
|
+
else
|
|
190
|
+
for await (const { event, data, id } of serverEvents(response.body)) {
|
|
191
|
+
// A stream replaced by the next one says nothing more.
|
|
192
|
+
if (once.signal.aborted) break;
|
|
193
|
+
const message: Message = {
|
|
194
|
+
...(id ? { id } : {}),
|
|
195
|
+
...(event === 'task' ? { event: JSON.parse(data) as TaskEvent } : {}),
|
|
196
|
+
...(event === 'reset' ? { reset: true as const } : {}),
|
|
197
|
+
};
|
|
198
|
+
channel?.postMessage(message);
|
|
199
|
+
receive(message);
|
|
200
|
+
}
|
|
201
|
+
} catch {}
|
|
202
|
+
abort.signal.removeEventListener('abort', stop);
|
|
203
|
+
// A new task set opens the next stream at once.
|
|
204
|
+
if (once.signal.aborted) continue;
|
|
205
|
+
await new Promise<void>(done => {
|
|
206
|
+
const timer = setTimeout(done, wait);
|
|
207
|
+
wake = () => {
|
|
208
|
+
clearTimeout(timer);
|
|
209
|
+
done();
|
|
210
|
+
};
|
|
211
|
+
});
|
|
212
|
+
wake = () => {};
|
|
99
213
|
}
|
|
100
214
|
};
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
215
|
+
|
|
216
|
+
if (channel)
|
|
217
|
+
void navigator.locks.request(EVENTS, { signal: abort.signal }, lead).catch(() => {});
|
|
218
|
+
else void lead();
|
|
219
|
+
return () => {
|
|
220
|
+
abort.abort();
|
|
221
|
+
wake();
|
|
222
|
+
clearTimeout(soon);
|
|
223
|
+
channel?.close();
|
|
224
|
+
removeEventListener(REPLAY, replay);
|
|
225
|
+
};
|
|
226
|
+
}, []);
|
|
227
|
+
|
|
228
|
+
useEffect(() => {
|
|
229
|
+
if (current.current && current.current.key !== key) current.current.abort.abort();
|
|
230
|
+
}, [key]);
|
|
105
231
|
}
|
|
106
232
|
|
|
107
233
|
function Item({ toast, dismiss }: { toast: Toast; dismiss: (key: string) => void }) {
|
|
@@ -110,7 +236,7 @@ function Item({ toast, dismiss }: { toast: Toast; dismiss: (key: string) => void
|
|
|
110
236
|
return () => clearTimeout(timer);
|
|
111
237
|
}, []);
|
|
112
238
|
return (
|
|
113
|
-
<div class={toast.
|
|
239
|
+
<div class={toast.err ? 'toast err' : 'toast'} onClick={() => dismiss(toast.key)}>
|
|
114
240
|
<p class="toast-head">
|
|
115
241
|
{toast.id ? (
|
|
116
242
|
<Link class="cover" href="/dash/tasks/[id]" params={{ id: toast.id }}>
|
|
@@ -134,9 +260,16 @@ export function TaskToasts() {
|
|
|
134
260
|
const [toasts, setToasts] = useState<Toast[]>([]);
|
|
135
261
|
const open = useRef(openTask(path));
|
|
136
262
|
open.current = openTask(path);
|
|
263
|
+
// Each tab's own last status per task, so every tab toasts a change once.
|
|
264
|
+
const known = useRef<Record<string, TaskState>>({});
|
|
265
|
+
const leading = useRef(false);
|
|
137
266
|
|
|
138
267
|
useEffect(() => {
|
|
139
|
-
const sync = () =>
|
|
268
|
+
const sync = () => {
|
|
269
|
+
const all = read();
|
|
270
|
+
for (const [id, entry] of Object.entries(all)) known.current[id] ??= entry.status;
|
|
271
|
+
setWatched(all);
|
|
272
|
+
};
|
|
140
273
|
sync();
|
|
141
274
|
addEventListener(WATCHED, sync);
|
|
142
275
|
addEventListener('storage', sync);
|
|
@@ -148,8 +281,8 @@ export function TaskToasts() {
|
|
|
148
281
|
|
|
149
282
|
useEffect(() => {
|
|
150
283
|
const onToast = (event: Event) => {
|
|
151
|
-
const
|
|
152
|
-
setToasts(list => [{ key: `${TOAST}:${Date.now()}`,
|
|
284
|
+
const detail = (event as CustomEvent<Omit<Toast, 'key'>>).detail;
|
|
285
|
+
setToasts(list => [{ key: `${TOAST}:${Date.now()}`, ...detail }, ...list].slice(0, MAX));
|
|
153
286
|
};
|
|
154
287
|
addEventListener(TOAST, onToast);
|
|
155
288
|
return () => removeEventListener(TOAST, onToast);
|
|
@@ -164,9 +297,25 @@ export function TaskToasts() {
|
|
|
164
297
|
|
|
165
298
|
const dismiss = (key: string) => setToasts(list => list.filter(toast => toast.key !== key));
|
|
166
299
|
|
|
167
|
-
|
|
168
|
-
const
|
|
169
|
-
|
|
300
|
+
useTaskEvents(event => {
|
|
301
|
+
const all = read();
|
|
302
|
+
const seen = all[event.id];
|
|
303
|
+
if (!seen) return;
|
|
304
|
+
if (event.deleted) {
|
|
305
|
+
delete all[event.id];
|
|
306
|
+
return save(all);
|
|
307
|
+
}
|
|
308
|
+
const before = known.current[event.id] ?? seen.status;
|
|
309
|
+
known.current[event.id] = event.status;
|
|
310
|
+
if (before !== event.status)
|
|
311
|
+
onStatus(
|
|
312
|
+
event.id,
|
|
313
|
+
{ ...event, result: event.result ?? undefined, error: event.error ?? undefined },
|
|
314
|
+
seen,
|
|
315
|
+
);
|
|
316
|
+
});
|
|
317
|
+
|
|
318
|
+
const onStatus = (id: string, live: Live, seen: Watched) => {
|
|
170
319
|
watchTask(id, live.status);
|
|
171
320
|
if (!SHOWN.has(live.status) || open.current === id) return;
|
|
172
321
|
const toast = {
|
|
@@ -178,6 +327,7 @@ export function TaskToasts() {
|
|
|
178
327
|
};
|
|
179
328
|
setToasts(list => [toast, ...list].slice(0, MAX));
|
|
180
329
|
if (
|
|
330
|
+
!leading.current ||
|
|
181
331
|
localStorage.getItem(NOTIFY) !== '1' ||
|
|
182
332
|
typeof Notification === 'undefined' ||
|
|
183
333
|
Notification.permission !== 'granted'
|
|
@@ -193,22 +343,18 @@ export function TaskToasts() {
|
|
|
193
343
|
};
|
|
194
344
|
};
|
|
195
345
|
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
346
|
+
useEventsStream(
|
|
347
|
+
Object.entries(watched)
|
|
348
|
+
.filter(([, entry]) => !DONE.has(entry.status))
|
|
349
|
+
.map(([id]) => id),
|
|
350
|
+
leading,
|
|
351
|
+
);
|
|
201
352
|
|
|
202
353
|
return (
|
|
203
|
-
|
|
204
|
-
{
|
|
205
|
-
<
|
|
354
|
+
<section class="toasts" aria-label="Task updates" aria-live="polite">
|
|
355
|
+
{toasts.map(toast => (
|
|
356
|
+
<Item key={toast.key} toast={toast} dismiss={dismiss} />
|
|
206
357
|
))}
|
|
207
|
-
|
|
208
|
-
{toasts.map(toast => (
|
|
209
|
-
<Item key={toast.key} toast={toast} dismiss={dismiss} />
|
|
210
|
-
))}
|
|
211
|
-
</section>
|
|
212
|
-
</>
|
|
358
|
+
</section>
|
|
213
359
|
);
|
|
214
360
|
}
|
|
@@ -1,20 +1,31 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
-
import { useState } from 'preact/hooks';
|
|
3
|
+
import { useEffect, useState } from 'preact/hooks';
|
|
4
4
|
|
|
5
5
|
import { iLeft, iRight } from '@/comps/ui/icons';
|
|
6
6
|
import { Icon } from '@/comps/ui/icon';
|
|
7
7
|
|
|
8
8
|
const COOKIE = 'side';
|
|
9
9
|
|
|
10
|
-
/** Collapses the sidebar to its icons;
|
|
10
|
+
/** Collapses the sidebar to its icons; a click is saved in a cookie so the next page renders that way at once. */
|
|
11
11
|
export function SideToggle({ collapsed: initial }: { collapsed: boolean }) {
|
|
12
12
|
const [collapsed, setCollapsed] = useState(initial);
|
|
13
|
+
|
|
14
|
+
// Without a saved choice the layout script collapses mid-width screens, so the label follows the class.
|
|
15
|
+
useEffect(() => {
|
|
16
|
+
const app = document.querySelector('.app');
|
|
17
|
+
if (!app) return;
|
|
18
|
+
const sync = () => setCollapsed(app.classList.contains('side-min'));
|
|
19
|
+
sync();
|
|
20
|
+
const watch = new MutationObserver(sync);
|
|
21
|
+
watch.observe(app, { attributes: true, attributeFilter: ['class'] });
|
|
22
|
+
return () => watch.disconnect();
|
|
23
|
+
}, []);
|
|
24
|
+
|
|
13
25
|
const toggle = () => {
|
|
14
26
|
const next = !collapsed;
|
|
15
|
-
setCollapsed(next);
|
|
16
27
|
document.querySelector('.app')?.classList.toggle('side-min', next);
|
|
17
|
-
document.cookie = `${COOKIE}=${next ? 'min' : ''}; path=/; max-age
|
|
28
|
+
document.cookie = `${COOKIE}=${next ? 'min' : 'max'}; path=/; max-age=31536000; samesite=lax`;
|
|
18
29
|
};
|
|
19
30
|
return (
|
|
20
31
|
<button
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
/* applied filters sit in the toolbar's row and scroll sideways instead of wrapping it */
|
|
2
|
+
.filter-chips {
|
|
3
|
+
display: flex;
|
|
4
|
+
flex: 1 1 0;
|
|
5
|
+
gap: 4px;
|
|
6
|
+
min-width: 0;
|
|
7
|
+
overflow-x: auto;
|
|
8
|
+
scrollbar-width: none;
|
|
9
|
+
}
|
|
10
|
+
.filters:has(> .filter-chips) > .search {
|
|
11
|
+
flex-grow: 1000;
|
|
12
|
+
}
|
|
13
|
+
/* in a page head the filters keep to the right, so chips fill in from the search's left */
|
|
14
|
+
.head.tools .filter-chips {
|
|
15
|
+
order: -1;
|
|
16
|
+
}
|
|
17
|
+
.head.tools .filter-chips > :first-child {
|
|
18
|
+
margin-left: auto;
|
|
19
|
+
}
|
|
20
|
+
.filter-chips .chip {
|
|
21
|
+
display: inline-flex;
|
|
22
|
+
flex: none;
|
|
23
|
+
align-items: center;
|
|
24
|
+
gap: 4px;
|
|
25
|
+
max-width: 200px;
|
|
26
|
+
}
|
|
27
|
+
.filter-chips .chip .grow {
|
|
28
|
+
overflow: hidden;
|
|
29
|
+
text-overflow: ellipsis;
|
|
30
|
+
white-space: nowrap;
|
|
31
|
+
}
|
|
32
|
+
.filter-chips .chip .ic {
|
|
33
|
+
width: 12px;
|
|
34
|
+
height: 12px;
|
|
35
|
+
}
|
|
36
|
+
/* brand art takes the same box as the other icons, so labels line up */
|
|
37
|
+
.filter-panel .pop-item > .brand-icon {
|
|
38
|
+
width: 16px;
|
|
39
|
+
height: 16px;
|
|
40
|
+
}
|
|
41
|
+
.filter-panel [data-facet] {
|
|
42
|
+
color: var(--muted);
|
|
43
|
+
}
|
|
44
|
+
.filter-panel .search {
|
|
45
|
+
margin: 4px 0 6px;
|
|
46
|
+
}
|
|
47
|
+
.filter-panel .search input {
|
|
48
|
+
width: 100%;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
@media (max-width: 760px) {
|
|
52
|
+
/* the button sits at the left edge here, so its menu opens rightward */
|
|
53
|
+
@supports (anchor-scope: --menu) {
|
|
54
|
+
.filters .menu.filter-more > .pop {
|
|
55
|
+
inset: anchor(bottom) auto auto anchor(left);
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
.head.tools .filter-chips {
|
|
59
|
+
order: 0;
|
|
60
|
+
}
|
|
61
|
+
.head.tools .filter-chips > :first-child {
|
|
62
|
+
margin-left: 0;
|
|
63
|
+
}
|
|
64
|
+
}
|