@celsoft/coordinator 0.0.0 → 0.1.0
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/CHANGELOG.md +11 -0
- package/README.md +107 -0
- package/THIRD_PARTY_NOTICES.md +2005 -0
- package/agents/console.md +20 -0
- package/agents/free.md +110 -0
- package/build/0-JP6XL6LB.js +17 -0
- package/build/1-A52YZWNS.js +17 -0
- package/build/2-CLH2NM6F.js +32 -0
- package/build/3-4N467IB6.js +45 -0
- package/build/4-WL5H4LUW.js +29 -0
- package/build/_layout.svelte-KPUSX7LQ.js +27 -0
- package/build/_page.svelte-22H56UR6.js +7972 -0
- package/build/_page.svelte-CVWUNRQC.js +135 -0
- package/build/_page.svelte-LTZXBHMT.js +57 -0
- package/build/_server.ts-3KVBYN6P.js +20 -0
- package/build/_server.ts-3POPKVEM.js +47 -0
- package/build/_server.ts-5735T2V5.js +31 -0
- package/build/_server.ts-5VXGNWV2.js +38 -0
- package/build/_server.ts-645KP7WP.js +42 -0
- package/build/_server.ts-A3AA24Z2.js +28 -0
- package/build/_server.ts-CITUOEM6.js +58 -0
- package/build/_server.ts-I7HMTPOA.js +25 -0
- package/build/_server.ts-M5BQ4LLX.js +30 -0
- package/build/_server.ts-OB4O27HF.js +683 -0
- package/build/_server.ts-OJT7HE7M.js +15 -0
- package/build/_server.ts-OYGWVLZM.js +12 -0
- package/build/_server.ts-T75UVMQP.js +38 -0
- package/build/_server.ts-WYZYNHUZ.js +28 -0
- package/build/_server.ts-Z26EB47B.js +486 -0
- package/build/chunk-4CIG53L5.js +33 -0
- package/build/chunk-BJTJS3XY.js +338 -0
- package/build/chunk-F2CNWJZM.js +14 -0
- package/build/chunk-HGYE3UTU.js +416 -0
- package/build/chunk-KAYW2W7H.js +1311 -0
- package/build/chunk-LFP3UPCM.js +10 -0
- package/build/chunk-M44JEFEH.js +62 -0
- package/build/chunk-MC5AGLMY.js +39 -0
- package/build/chunk-NCZ77J5E.js +19798 -0
- package/build/chunk-NVNLDPUJ.js +2122 -0
- package/build/chunk-PDCON4KS.js +494 -0
- package/build/chunk-Q4OQNY5M.js +25 -0
- package/build/chunk-QCUOR2U5.js +75 -0
- package/build/chunk-R6RYZZWA.js +46 -0
- package/build/chunk-SOJTASZC.js +51 -0
- package/build/chunk-SU26PJVX.js +410 -0
- package/build/chunk-U5BSBG4R.js +506 -0
- package/build/chunk-UEKOZGRO.js +37 -0
- package/build/chunk-W6EFUWJ2.js +9 -0
- package/build/chunk-WOPREK6Q.js +117 -0
- package/build/chunk-WWJ3F4QS.js +127 -0
- package/build/chunk-ZGZJEEE3.js +1091 -0
- package/build/client/_app/immutable/assets/0.BGa5ZNDM.css +1 -0
- package/build/client/_app/immutable/chunks/BUrrLYDt.js +2 -0
- package/build/client/_app/immutable/chunks/BgFr_EyZ.js +4 -0
- package/build/client/_app/immutable/chunks/Bjy-W4x2.js +82 -0
- package/build/client/_app/immutable/chunks/C8qZab0y.js +56 -0
- package/build/client/_app/immutable/chunks/C90fLsA5.js +4 -0
- package/build/client/_app/immutable/chunks/CRzLMJPS.js +1 -0
- package/build/client/_app/immutable/chunks/DLT1iIlz.js +2 -0
- package/build/client/_app/immutable/chunks/pIrVVOVY.js +2 -0
- package/build/client/_app/immutable/entry/app.0DERehLW.js +3 -0
- package/build/client/_app/immutable/entry/payload.DSmR2FwN.js +2 -0
- package/build/client/_app/immutable/entry/start.B7srFiqh.js +3 -0
- package/build/client/_app/immutable/nodes/0.aD9vJoxR.js +2 -0
- package/build/client/_app/immutable/nodes/1.Br4FL91i.js +2 -0
- package/build/client/_app/immutable/nodes/2.vl6OYfu3.js +8 -0
- package/build/client/_app/immutable/nodes/3.VYqJOLAF.js +2 -0
- package/build/client/_app/immutable/nodes/4.jF9UVlFN.js +2 -0
- package/build/client/_app/version.json +1 -0
- package/build/client/apple-touch-icon.png +0 -0
- package/build/client/favicon.ico +0 -0
- package/build/client/favicon.svg +48 -0
- package/build/client/icon-192.png +0 -0
- package/build/client/icon-512.png +0 -0
- package/build/client/icon-maskable-512.png +0 -0
- package/build/client/icon.svg +44 -0
- package/build/client/manifest.webmanifest +15 -0
- package/build/error.svelte-JXZDY65F.js +51 -0
- package/build/handler.js +716 -0
- package/build/hooks.server-34IMHRKC.js +43 -0
- package/build/instance-NP3FJIWW.js +2967 -0
- package/client/client.mjs +28 -0
- package/client/hooks.mjs +7 -0
- package/client/register.mjs +5 -0
- package/dist/cli.js +62826 -0
- package/dist/port.js +36691 -0
- package/package.json +20 -1
- package/skills/agents/.claude-plugin/plugin.json +5 -0
- package/skills/agents/hooks/hooks.json +1 -0
- package/skills/agents/hooks/register.ts +57 -0
- package/skills/agents/skills/bus-work/SKILL.md +66 -0
- package/skills/agents/skills/plan/SKILL.md +98 -0
- package/skills/console/.claude-plugin/plugin.json +5 -0
- package/skills/console/hooks/hooks.json +1 -0
- package/skills/console/hooks/register.ts +10 -0
- package/skills/console/skills/bus/SKILL.md +61 -0
- package/skills/default/.claude-plugin/plugin.json +5 -0
- package/skills/default/skills/git-workflow/SKILL.md +294 -0
- package/skills/default/skills/git-workflow/mise-tasks/_lib.sh +107 -0
- package/skills/default/skills/git-workflow/mise-tasks/clone +36 -0
- package/skills/default/skills/git-workflow/mise-tasks/repo-list +8 -0
- package/skills/default/skills/git-workflow/mise-tasks/unpushed +26 -0
- package/skills/default/skills/git-workflow/mise-tasks/worktree-add +60 -0
- package/skills/default/skills/github/SKILL.md +208 -0
- package/skills/default/skills/github/scripts/gh-org +196 -0
- package/skills/default/skills/plan-page/SKILL.md +300 -0
- package/skills/default/skills/plan-page/assets/index.html +854 -0
- package/skills/default/skills/plan-page/scripts/inline +46 -0
- package/skills/default/skills/plan-page/scripts/stage +26 -0
- package/skills/default/skills/secrets/SKILL.md +134 -0
- package/skills/default/skills/secrets/scripts/secrets-check +87 -0
- package/skills/default/skills/writing-style/SKILL.md +45 -0
- package/skills/extra/.claude-plugin/plugin.json +5 -0
- package/skills/extra/skills/artifacts/SKILL.md +52 -0
- package/skills/extra/skills/github-actions/SKILL.md +78 -0
- package/skills/extra/skills/github-actions/scan +32 -0
- package/skills/extra/skills/markdown-review/SKILL.md +70 -0
- package/skills/extra/skills/markdown-review/assets/index.html +201 -0
- package/skills/extra/skills/markdown-review/scripts/stage +36 -0
- package/skills/extra/skills/mise-usage/SKILL.md +155 -0
- package/skills/extra/skills/plugin-authoring/SKILL.md +317 -0
- package/skills/extra/skills/project-conventions/SKILL.md +64 -0
- package/skills/extra/skills/questions/SKILL.md +156 -0
- package/skills/extra/skills/questions/assets/index.html +376 -0
- package/skills/extra/skills/questions/scripts/stage +26 -0
- package/skills/extra/skills/serve/SKILL.md +165 -0
- package/skills/extra/skills/serve/scripts/serve +268 -0
- package/skills/extra/skills/serve/scripts/server.py +345 -0
- package/skills/extra/skills/skill-dependencies/SKILL.md +65 -0
- package/skills/extra/skills/skill-maintenance/SKILL.md +101 -0
- package/skills/extra/skills/ticketing/SKILL.md +125 -0
|
@@ -0,0 +1,201 @@
|
|
|
1
|
+
<title>Markdown Review</title>
|
|
2
|
+
<style>
|
|
3
|
+
:root {
|
|
4
|
+
--bg: #fbfaf8; --fg: #1f1d1a; --muted: #6b665e; --line: #e4e0d8;
|
|
5
|
+
--code-bg: #f1eee8; --accent: #2f5fbf; --table-head: #f4f1eb;
|
|
6
|
+
--panel: #f5f3ef; --current: #e8e4dc; --group: #e9eef8;
|
|
7
|
+
}
|
|
8
|
+
@media (prefers-color-scheme: dark) {
|
|
9
|
+
:root:not([data-theme="light"]) {
|
|
10
|
+
--bg: #17181a; --fg: #e6e3dd; --muted: #9a958c; --line: #2e3033;
|
|
11
|
+
--code-bg: #222427; --accent: #8fb1ff; --table-head: #1f2123;
|
|
12
|
+
--panel: #1c1d20; --current: #2a2c30; --group: #22293a;
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
:root[data-theme="dark"] {
|
|
16
|
+
--bg: #17181a; --fg: #e6e3dd; --muted: #9a958c; --line: #2e3033;
|
|
17
|
+
--code-bg: #222427; --accent: #8fb1ff; --table-head: #1f2123;
|
|
18
|
+
--panel: #1c1d20; --current: #2a2c30; --group: #22293a;
|
|
19
|
+
}
|
|
20
|
+
* { box-sizing: border-box; }
|
|
21
|
+
html, body { height: 100%; }
|
|
22
|
+
body {
|
|
23
|
+
margin: 0; background: var(--bg); color: var(--fg); overflow: hidden;
|
|
24
|
+
font: 16px/1.65 -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
|
|
25
|
+
}
|
|
26
|
+
.layout { display: grid; grid-template-columns: 280px 1fr; height: 100vh; height: 100dvh; }
|
|
27
|
+
|
|
28
|
+
nav {
|
|
29
|
+
overflow-y: auto; background: var(--panel); border-right: 1px solid var(--line);
|
|
30
|
+
padding: 24px 12px 48px; font-size: 14px; line-height: 1.4;
|
|
31
|
+
}
|
|
32
|
+
nav .doc-title { font-weight: 600; padding: 0 8px 12px; }
|
|
33
|
+
nav a {
|
|
34
|
+
display: block; color: var(--muted); text-decoration: none;
|
|
35
|
+
padding: 5px 8px; border-radius: 6px;
|
|
36
|
+
}
|
|
37
|
+
nav a:hover { color: var(--fg); }
|
|
38
|
+
nav a.current { background: var(--current); color: var(--fg); }
|
|
39
|
+
nav a.level-3 { padding-left: 22px; }
|
|
40
|
+
nav a.level-4 { padding-left: 36px; font-size: 13px; }
|
|
41
|
+
|
|
42
|
+
#content { overflow-y: auto; }
|
|
43
|
+
main { max-width: 780px; margin: 0 auto; padding: 32px 24px 96px; }
|
|
44
|
+
.file { color: var(--muted); font: 13px ui-monospace, SFMono-Regular, Menlo, monospace; margin-bottom: 24px; }
|
|
45
|
+
.toggle {
|
|
46
|
+
display: none; position: fixed; top: 12px; right: 12px; z-index: 3;
|
|
47
|
+
background: var(--panel); color: var(--fg); border: 1px solid var(--line);
|
|
48
|
+
border-radius: 8px; padding: 6px 12px; font: inherit; font-size: 14px;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
h1, h2, h3, h4 { line-height: 1.25; margin: 1.8em 0 0.6em; scroll-margin-top: 16px; }
|
|
52
|
+
h1 { font-size: 2em; margin-top: 0; }
|
|
53
|
+
h2 { font-size: 1.45em; padding-bottom: 0.3em; border-bottom: 1px solid var(--line); }
|
|
54
|
+
h3 { font-size: 1.15em; }
|
|
55
|
+
a { color: var(--accent); }
|
|
56
|
+
p, ul, ol, table, pre, blockquote { margin: 0 0 1em; }
|
|
57
|
+
li { margin: 0.25em 0; }
|
|
58
|
+
code { font: 0.9em ui-monospace, SFMono-Regular, Menlo, monospace; background: var(--code-bg); padding: 0.1em 0.35em; border-radius: 4px; }
|
|
59
|
+
pre { background: var(--code-bg); padding: 14px 16px; border-radius: 8px; overflow-x: auto; }
|
|
60
|
+
pre code { background: none; padding: 0; font-size: 0.85em; }
|
|
61
|
+
blockquote { border-left: 3px solid var(--line); margin-left: 0; padding-left: 16px; color: var(--muted); }
|
|
62
|
+
.table-wrap { overflow-x: auto; margin: 0 0 1em; }
|
|
63
|
+
table { border-collapse: collapse; width: 100%; font-size: 0.93em; margin: 0; }
|
|
64
|
+
th, td { border: 1px solid var(--line); padding: 8px 10px; text-align: left; vertical-align: top; }
|
|
65
|
+
th { background: var(--table-head); }
|
|
66
|
+
td[colspan], th[colspan] { background: var(--group); }
|
|
67
|
+
img { max-width: 100%; }
|
|
68
|
+
hr { border: 0; border-top: 1px solid var(--line); margin: 2em 0; }
|
|
69
|
+
.mermaid { display: flex; justify-content: center; margin: 0 0 1em; overflow-x: auto; }
|
|
70
|
+
.status { color: var(--muted); }
|
|
71
|
+
|
|
72
|
+
@media (max-width: 760px) {
|
|
73
|
+
.layout { grid-template-columns: 1fr; }
|
|
74
|
+
nav {
|
|
75
|
+
display: none; position: fixed; inset: 0 0 0 auto; width: min(300px, 85vw); z-index: 2;
|
|
76
|
+
border-right: 0; border-left: 1px solid var(--line); padding-top: 56px;
|
|
77
|
+
}
|
|
78
|
+
body.outline-open nav { display: block; }
|
|
79
|
+
.toggle { display: block; }
|
|
80
|
+
main { padding: 56px 16px 96px; }
|
|
81
|
+
}
|
|
82
|
+
</style>
|
|
83
|
+
|
|
84
|
+
<button class="toggle" id="toggle" type="button">Outline</button>
|
|
85
|
+
<div class="layout">
|
|
86
|
+
<nav id="outline" aria-label="Outline"></nav>
|
|
87
|
+
<div id="content">
|
|
88
|
+
<main>
|
|
89
|
+
<div class="file" id="file"></div>
|
|
90
|
+
<article id="doc"><p class="status">Loading…</p></article>
|
|
91
|
+
</main>
|
|
92
|
+
</div>
|
|
93
|
+
</div>
|
|
94
|
+
|
|
95
|
+
<script src="https://cdnjs.cloudflare.com/ajax/libs/marked/12.0.2/marked.min.js"></script>
|
|
96
|
+
<script src="https://cdnjs.cloudflare.com/ajax/libs/dompurify/3.1.6/purify.min.js"></script>
|
|
97
|
+
<script src="https://cdnjs.cloudflare.com/ajax/libs/mermaid/11.4.0/mermaid.min.js"></script>
|
|
98
|
+
<script>
|
|
99
|
+
(async () => {
|
|
100
|
+
const doc = document.getElementById("doc");
|
|
101
|
+
const outline = document.getElementById("outline");
|
|
102
|
+
const content = document.getElementById("content");
|
|
103
|
+
|
|
104
|
+
document.getElementById("toggle").addEventListener("click", () => document.body.classList.toggle("outline-open"));
|
|
105
|
+
|
|
106
|
+
const fail = (message) => {
|
|
107
|
+
doc.innerHTML = "";
|
|
108
|
+
const p = document.createElement("p");
|
|
109
|
+
p.className = "status";
|
|
110
|
+
p.textContent = message;
|
|
111
|
+
doc.append(p);
|
|
112
|
+
};
|
|
113
|
+
|
|
114
|
+
let file;
|
|
115
|
+
try {
|
|
116
|
+
const manifest = await (await fetch("document.json", { cache: "no-cache" })).json();
|
|
117
|
+
file = manifest.file;
|
|
118
|
+
if (typeof file !== "string" || !file) throw new Error("document.json has no file");
|
|
119
|
+
} catch (error) {
|
|
120
|
+
return fail("Could not read document.json: " + error.message);
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
document.getElementById("file").textContent = file;
|
|
124
|
+
const response = await fetch(encodeURI(file), { cache: "no-cache" }).catch(() => null);
|
|
125
|
+
if (!response || !response.ok) return fail("Could not load " + file + ".");
|
|
126
|
+
const markdown = await response.text();
|
|
127
|
+
|
|
128
|
+
doc.innerHTML = DOMPurify.sanitize(marked.parse(markdown, { gfm: true }));
|
|
129
|
+
|
|
130
|
+
for (const table of doc.querySelectorAll("table")) {
|
|
131
|
+
const wrap = document.createElement("div");
|
|
132
|
+
wrap.className = "table-wrap";
|
|
133
|
+
table.replaceWith(wrap);
|
|
134
|
+
wrap.append(table);
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
const title = doc.querySelector("h1");
|
|
138
|
+
document.title = title ? title.textContent : file;
|
|
139
|
+
buildOutline(title ? title.textContent : file);
|
|
140
|
+
|
|
141
|
+
const diagrams = [...doc.querySelectorAll("pre > code.language-mermaid")];
|
|
142
|
+
if (diagrams.length) {
|
|
143
|
+
for (const code of diagrams) {
|
|
144
|
+
const div = document.createElement("div");
|
|
145
|
+
div.className = "mermaid";
|
|
146
|
+
div.textContent = code.textContent;
|
|
147
|
+
code.parentElement.replaceWith(div);
|
|
148
|
+
}
|
|
149
|
+
const theme = document.documentElement.dataset.theme;
|
|
150
|
+
const dark = theme ? theme === "dark" : matchMedia("(prefers-color-scheme: dark)").matches;
|
|
151
|
+
mermaid.initialize({ startOnLoad: false, theme: dark ? "dark" : "default", securityLevel: "strict" });
|
|
152
|
+
await mermaid.run({ nodes: doc.querySelectorAll(".mermaid") });
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
function buildOutline(docTitle) {
|
|
156
|
+
const heading = document.createElement("div");
|
|
157
|
+
heading.className = "doc-title";
|
|
158
|
+
heading.textContent = docTitle;
|
|
159
|
+
outline.append(heading);
|
|
160
|
+
|
|
161
|
+
const used = new Set();
|
|
162
|
+
const entries = [];
|
|
163
|
+
for (const h of doc.querySelectorAll("h2, h3, h4")) {
|
|
164
|
+
const base = h.textContent.toLowerCase().trim().replace(/[^\w]+/g, "-").replace(/^-|-$/g, "") || "section";
|
|
165
|
+
let id = base;
|
|
166
|
+
for (let n = 2; used.has(id); n++) id = base + "-" + n;
|
|
167
|
+
used.add(id);
|
|
168
|
+
h.id = id;
|
|
169
|
+
|
|
170
|
+
const link = document.createElement("a");
|
|
171
|
+
link.href = "#" + id;
|
|
172
|
+
link.className = "level-" + h.tagName[1];
|
|
173
|
+
link.textContent = h.textContent;
|
|
174
|
+
link.addEventListener("click", (event) => {
|
|
175
|
+
event.preventDefault();
|
|
176
|
+
h.scrollIntoView({ behavior: "smooth", block: "start" });
|
|
177
|
+
document.body.classList.remove("outline-open");
|
|
178
|
+
});
|
|
179
|
+
outline.append(link);
|
|
180
|
+
entries.push({ h, link });
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
let current;
|
|
184
|
+
const mark = () => {
|
|
185
|
+
const top = content.getBoundingClientRect().top + 24;
|
|
186
|
+
let active = entries[0];
|
|
187
|
+
for (const entry of entries) {
|
|
188
|
+
if (entry.h.getBoundingClientRect().top <= top) active = entry;
|
|
189
|
+
else break;
|
|
190
|
+
}
|
|
191
|
+
if (!active || active === current) return;
|
|
192
|
+
current?.link.classList.remove("current");
|
|
193
|
+
active.link.classList.add("current");
|
|
194
|
+
active.link.scrollIntoView({ block: "nearest" });
|
|
195
|
+
current = active;
|
|
196
|
+
};
|
|
197
|
+
content.addEventListener("scroll", mark, { passive: true });
|
|
198
|
+
mark();
|
|
199
|
+
}
|
|
200
|
+
})();
|
|
201
|
+
</script>
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
#
|
|
3
|
+
# stage: prepare the renderer page and document.json for one markdown file.
|
|
4
|
+
#
|
|
5
|
+
# Usage: stage <markdown-file> <out-dir>
|
|
6
|
+
# Prints the three paths to publish, one per line.
|
|
7
|
+
|
|
8
|
+
set -euo pipefail
|
|
9
|
+
|
|
10
|
+
if [ $# -ne 2 ]; then
|
|
11
|
+
echo "usage: stage <markdown-file> <out-dir>" >&2
|
|
12
|
+
exit 2
|
|
13
|
+
fi
|
|
14
|
+
|
|
15
|
+
markdown=$1
|
|
16
|
+
out=$2
|
|
17
|
+
here=$(cd "$(dirname "$0")/.." && pwd)
|
|
18
|
+
|
|
19
|
+
if [ ! -f "$markdown" ]; then
|
|
20
|
+
echo "NOT_FOUND: $markdown" >&2
|
|
21
|
+
exit 1
|
|
22
|
+
fi
|
|
23
|
+
|
|
24
|
+
name=$(basename "$markdown")
|
|
25
|
+
case $name in
|
|
26
|
+
*\"* | *\\*) echo "BAD_NAME: rename the file without quotes or backslashes" >&2; exit 1 ;;
|
|
27
|
+
index.html | document.json) echo "BAD_NAME: $name is reserved by the renderer" >&2; exit 1 ;;
|
|
28
|
+
esac
|
|
29
|
+
|
|
30
|
+
mkdir -p "$out"
|
|
31
|
+
cp "$here/assets/index.html" "$out/index.html"
|
|
32
|
+
printf '{ "file": "%s" }\n' "$name" > "$out/document.json"
|
|
33
|
+
|
|
34
|
+
echo "PAGE: $out/index.html"
|
|
35
|
+
echo "MANIFEST: $out/document.json"
|
|
36
|
+
echo "MARKDOWN: $name <- $(cd "$(dirname "$markdown")" && pwd)/$name"
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: mise-usage
|
|
3
|
+
description: "How to use mise in a project: running commands, managing tools, .env and .venv, Python/uv setup, writing tasks, and driving tasks from Claude."
|
|
4
|
+
verified: 2026-10-16
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Mise Usage
|
|
8
|
+
|
|
9
|
+
## Claude has no mise environment
|
|
10
|
+
|
|
11
|
+
When Claude runs a Bash command, it is **not** in an activated mise shell. Tools declared in `mise.toml` (`python`, `uv`, `node`, etc.) are not on PATH, `.venv` is not activated, and `.env` is not loaded.
|
|
12
|
+
|
|
13
|
+
**Never run raw tool commands** (`python`, `uv`, `pip`, `node`, or anything else managed by
|
|
14
|
+
mise), and **never run `mise exec`.** Every command goes through a mise task:
|
|
15
|
+
|
|
16
|
+
- **Know the tasks.** Run `mise tasks` at the start of a session, and use a task over the
|
|
17
|
+
equivalent raw command whenever one exists.
|
|
18
|
+
- **No task fits.** Write a new file task for the command (see [Writing tasks](#writing-tasks))
|
|
19
|
+
and run it with `mise run`. Tasks carry the full environment: tools, `.env`, `.venv`.
|
|
20
|
+
|
|
21
|
+
## mise.toml structure
|
|
22
|
+
|
|
23
|
+
`mise.toml` at the repo root declares tools and environment:
|
|
24
|
+
|
|
25
|
+
```toml
|
|
26
|
+
[tools]
|
|
27
|
+
python = "3.13"
|
|
28
|
+
uv = "latest"
|
|
29
|
+
node = "22"
|
|
30
|
+
|
|
31
|
+
[env]
|
|
32
|
+
_.file = ".env" # autoload .env
|
|
33
|
+
_.python.venv = { path = ".venv", create = true } # manage .venv
|
|
34
|
+
UV_PYTHON = { value = "{{ tools.python.path }}", tools = true }
|
|
35
|
+
```
|
|
36
|
+
|
|
37
|
+
`mise install` installs all declared tools. After that, `mise run` has the full environment.
|
|
38
|
+
|
|
39
|
+
**Pin every tool.** Give each one an explicit version or backend (`node = "22"`,
|
|
40
|
+
`ubi:owner/repo`, `npm:pkg`), so `mise install` provisions identical versions on every
|
|
41
|
+
machine. `latest` is acceptable only where drift genuinely does not matter.
|
|
42
|
+
|
|
43
|
+
**`[env]` holds non-secret values only.** mise exports `[env]` into every interactive
|
|
44
|
+
shell in the repo and every child process, so anything there is far more widely visible
|
|
45
|
+
than it looks: a token in `[env]` can shadow an unrelated tool's own credential. Keep
|
|
46
|
+
`[env]` to identifiers such as account ids, bucket names, and hostnames. Secrets live in
|
|
47
|
+
`.env.secrets` and are sourced inside the one task that needs them, never autoloaded and
|
|
48
|
+
never declared here. See `secrets`.
|
|
49
|
+
|
|
50
|
+
## .env autoloading
|
|
51
|
+
|
|
52
|
+
Declare `_.file = ".env"` in the `[env]` block and mise loads it automatically for every `mise run` invocation. Never manually source `.env` before running commands. Gitignore `.env`; commit `.env.example` with placeholder values.
|
|
53
|
+
|
|
54
|
+
**Never autoload `.env.secrets`.** Autoloading is safe for `.env` precisely because `.env` holds no secrets. `.env.secrets` is different: it is sourced explicitly inside the task that needs it, so the values exist only in that process and never reach an interactive shell. Do not add it to `_.file`.
|
|
55
|
+
|
|
56
|
+
## .venv management
|
|
57
|
+
|
|
58
|
+
Declare `_.python.venv = { path = ".venv", create = true, uv_create = true }` in the `[env]` block and mise creates and activates the `.venv` automatically, using `uv` to create it (much faster than the stdlib `venv`). Never run `python -m venv`, `uv venv`, or any manual venv command: mise owns this.
|
|
59
|
+
|
|
60
|
+
## Python and uv conventions
|
|
61
|
+
|
|
62
|
+
- Declare `python` and `uv` in `[tools]`; set `UV_PYTHON` so uv uses mise's Python, not system Python
|
|
63
|
+
- Declare dependencies in `pyproject.toml`: never `requirements.txt`
|
|
64
|
+
- Install/sync deps with `uv sync` inside a mise task
|
|
65
|
+
- Commit `uv.lock` for reproducible installs
|
|
66
|
+
|
|
67
|
+
## Writing tasks
|
|
68
|
+
|
|
69
|
+
All scripts run by humans or Claude are mise file tasks written in zsh. Never embed script logic in `mise.toml` or skills.
|
|
70
|
+
|
|
71
|
+
```zsh
|
|
72
|
+
#!/usr/bin/env zsh
|
|
73
|
+
#MISE description="What this task does"
|
|
74
|
+
|
|
75
|
+
# task logic here
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
Requirements: `#!/usr/bin/env zsh` on line 1, `#MISE description="..."` on line 2, file executable (`chmod +x`). Add `#MISE depends=["other:task"]` for prerequisites.
|
|
79
|
+
|
|
80
|
+
**File tasks only. Never an inline `[tasks]` table in `mise.toml`.** One location for every task keeps them discoverable and reviewable, and a task that starts inline never gets moved.
|
|
81
|
+
|
|
82
|
+
Arguments come after `--` and are read as `"$@"`: `mise run deploy -- --dry-run`. List everything with `mise tasks`.
|
|
83
|
+
|
|
84
|
+
**Warning:** Some formatters add a space after `#`, turning `#MISE` into `# MISE`, which breaks parsing. Use `# [MISE]` if that happens.
|
|
85
|
+
|
|
86
|
+
### Naming
|
|
87
|
+
|
|
88
|
+
A task's name is its path under the tasks directory. Subdirectories create `:`-namespaced names; `_default` makes a namespace directly runnable:
|
|
89
|
+
|
|
90
|
+
```
|
|
91
|
+
foo # mise run foo
|
|
92
|
+
group/bar # mise run group:bar
|
|
93
|
+
group/_default # mise run group
|
|
94
|
+
```
|
|
95
|
+
|
|
96
|
+
### Shared helper library
|
|
97
|
+
|
|
98
|
+
A shared helper must be **non-executable** and named with a leading underscore. mise discovers *executable* files under `mise-tasks/` as tasks, so a `chmod +x` helper shows up as a phantom task that does nothing when run.
|
|
99
|
+
|
|
100
|
+
Source it at the top of every task: resolve it from the script's own path so it works regardless of where `mise run` is invoked:
|
|
101
|
+
|
|
102
|
+
```zsh
|
|
103
|
+
source "${0:A:h}/_lib.sh" # ${0:A} = symlink-resolved absolute path; :h = dirname
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
A helper library should provide:
|
|
107
|
+
|
|
108
|
+
```zsh
|
|
109
|
+
header "..." # bold heading
|
|
110
|
+
info "..." # informational line
|
|
111
|
+
success "..." # ✓ line
|
|
112
|
+
warn "..." # ⚠ warning line
|
|
113
|
+
error "..." # ✗ to stderr
|
|
114
|
+
dim "..." # dimmed text (e.g. echoing a command before running it)
|
|
115
|
+
ask "prompt" "default" # interactive text input → result in $REPLY
|
|
116
|
+
confirm "prompt" # yes/no prompt → returns 0 for yes, 1 for no
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
It should also restore the working directory on source, so tasks act on the directory where `mise run` was invoked:
|
|
120
|
+
|
|
121
|
+
```zsh
|
|
122
|
+
[[ -n "${MISE_ORIGINAL_CWD}" ]] && cd "$MISE_ORIGINAL_CWD"
|
|
123
|
+
```
|
|
124
|
+
|
|
125
|
+
### Idempotency
|
|
126
|
+
|
|
127
|
+
Tasks must be safe to re-run. Check before mutating: don't assume state is clean.
|
|
128
|
+
|
|
129
|
+
## Troubleshooting mise activation
|
|
130
|
+
|
|
131
|
+
If `mise run` fails because `mise` is not found, the shell is not activated. Check:
|
|
132
|
+
|
|
133
|
+
```bash
|
|
134
|
+
command -v mise # should print a path
|
|
135
|
+
echo $MISE_SHELL # should print "zsh", "bash", etc.; empty means not activated
|
|
136
|
+
```
|
|
137
|
+
|
|
138
|
+
**Do not activate it yourself.** Tell the user mise is not activated in their shell, and
|
|
139
|
+
point them at mise's own activation docs (https://mise.jdx.dev/getting-started.html). Their
|
|
140
|
+
shell startup files are theirs: a line you append may duplicate one their dotfiles already
|
|
141
|
+
manage.
|
|
142
|
+
|
|
143
|
+
After it is activated, open a new terminal; the current session will not pick it up.
|
|
144
|
+
Once activated, `mise install` installs the tools declared in `mise.toml` for the current
|
|
145
|
+
project.
|
|
146
|
+
|
|
147
|
+
## Driving tasks from Claude
|
|
148
|
+
|
|
149
|
+
When a skill drives a mise task that would otherwise trigger a Bash permission prompt, collapse the two prompts into one with `allowed-tools` in the skill's frontmatter:
|
|
150
|
+
|
|
151
|
+
```yaml
|
|
152
|
+
allowed-tools: Bash(mise run my:task:*)
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
The grant is active only while the skill runs and lapses when it finishes. The `AskUserQuestion` in the skill becomes the single decision point. Never blanket-allow mise in `settings.json` (`Bash(mise run:*)`): that silences prompts for tasks that have no approval gate.
|