@dudasaus/shaders-app-cli 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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Austin Dudas
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,195 @@
1
+ # Shader CLI
2
+
3
+ `@dudasaus/shaders-app-cli` lets you manage your owned shaders from a terminal, script, or coding agent.
4
+
5
+ ## Requirements
6
+
7
+ - Node.js 22 or newer
8
+ - A Shader Web App API token
9
+
10
+ ## Install
11
+
12
+ ```sh
13
+ npm install --global @dudasaus/shaders-app-cli
14
+ ```
15
+
16
+ Verify the installation:
17
+
18
+ ```sh
19
+ shader --help
20
+ ```
21
+
22
+ ## Authenticate
23
+
24
+ Create an API token while signed in at [API tokens](https://shaders.chillysoftware.com/app/settings/api-tokens). The token is shown only once.
25
+
26
+ For an interactive setup, run:
27
+
28
+ ```sh
29
+ shader init
30
+ ```
31
+
32
+ The CLI stores the token in:
33
+
34
+ ```text
35
+ ~/.config/shaders-app/.env.shaders
36
+ ```
37
+
38
+ For automation or a non-interactive setup, pipe the token through standard input:
39
+
40
+ ```sh
41
+ printf '%s\n' "$SHADER_API_KEY" | shader init --api-key-stdin
42
+ ```
43
+
44
+ You can also provide the token through the environment:
45
+
46
+ ```sh
47
+ export SHADER_API_KEY='your-token'
48
+ ```
49
+
50
+ Never pass API tokens as command-line arguments, commit them to source control, or include them in logs.
51
+
52
+ ## API target
53
+
54
+ The production API is used by default. To use another API origin, set `SHADER_API_URL`:
55
+
56
+ ```sh
57
+ export SHADER_API_URL=http://localhost:8787
58
+ ```
59
+
60
+ Or pass `--api-url` before the command:
61
+
62
+ ```sh
63
+ shader --api-url http://localhost:8787 list --json
64
+ ```
65
+
66
+ Non-loopback API URLs must use HTTPS.
67
+
68
+ ## Quick start
69
+
70
+ ```sh
71
+ shader create --title "Aurora" --source-file aurora.glsl
72
+ shader list
73
+ shader get SHADER_ID
74
+ shader get SHADER_ID --source > aurora.glsl
75
+ shader edit SHADER_ID --source-file aurora.glsl
76
+ shader delete SHADER_ID --yes
77
+ ```
78
+
79
+ Create and edit commands print the shader's share URL after a successful mutation.
80
+
81
+ ## Commands
82
+
83
+ ### `shader init`
84
+
85
+ Create the local credential file. The API key is entered through a hidden prompt:
86
+
87
+ ```sh
88
+ shader init
89
+ ```
90
+
91
+ Use `--api-key-stdin` for piped input and `--force` to replace an existing credential file.
92
+
93
+ ### `shader create`
94
+
95
+ Create a shader:
96
+
97
+ ```sh
98
+ shader create \
99
+ --title "Aurora" \
100
+ --description "A procedural gradient" \
101
+ --source-file aurora.glsl \
102
+ --json
103
+ ```
104
+
105
+ If `--source-file` is omitted, the CLI uses a small example shader. Use `--source-file -` to read source from standard input.
106
+
107
+ ### `shader list`
108
+
109
+ List your shaders:
110
+
111
+ ```sh
112
+ shader list
113
+ shader list --limit 20 --json
114
+ shader list --all --json
115
+ ```
116
+
117
+ Results are paginated by default. Use `--cursor` to request a subsequent page or `--all` to retrieve every page.
118
+
119
+ ### `shader get`
120
+
121
+ Read a shader by ID:
122
+
123
+ ```sh
124
+ shader get SHADER_ID
125
+ shader get SHADER_ID --source > shader.glsl
126
+ ```
127
+
128
+ `--source` writes only the GLSL source, making it convenient to redirect to a file.
129
+
130
+ ### `shader edit`
131
+
132
+ Update a shader:
133
+
134
+ ```sh
135
+ shader edit SHADER_ID --title "Aurora Updated"
136
+ shader edit SHADER_ID --description "A new description" --source-file aurora.glsl
137
+ ```
138
+
139
+ To replace the complete document from JSON, use `--document-file`:
140
+
141
+ ```json
142
+ {
143
+ "title": "Aurora",
144
+ "description": "A procedural gradient",
145
+ "source": "precision highp float;\n..."
146
+ }
147
+ ```
148
+
149
+ ```sh
150
+ shader edit SHADER_ID --document-file document.json
151
+ ```
152
+
153
+ Use `--dry-run` to validate an operation without sending it to the API.
154
+
155
+ ### `shader delete`
156
+
157
+ Deletion requires an explicit confirmation flag:
158
+
159
+ ```sh
160
+ shader delete SHADER_ID --yes
161
+ ```
162
+
163
+ Use `--dry-run` to preview the operation.
164
+
165
+ ## Output
166
+
167
+ Use `--json` for stable machine-readable output. It can appear before the command or after command options:
168
+
169
+ ```sh
170
+ shader --json list
171
+ shader list --json
172
+ ```
173
+
174
+ The CLI writes normal results to standard output and errors to standard error. It exits with a non-zero status when a command fails.
175
+
176
+ ## Shader limits
177
+
178
+ - Title: 1–100 UTF-8 bytes
179
+ - Description: up to 500 UTF-8 bytes
180
+ - Source: up to 128 KiB UTF-8 bytes
181
+ - List page size: 1–100 shaders
182
+
183
+ Shaders use GLSL ES 1.00 fragment source. The renderer provides `u_resolution` and `u_time` uniforms. A shader should declare a precision, for example:
184
+
185
+ ```glsl
186
+ precision highp float;
187
+
188
+ uniform vec2 u_resolution;
189
+ uniform float u_time;
190
+
191
+ void main() {
192
+ vec2 uv = gl_FragCoord.xy / u_resolution;
193
+ gl_FragColor = vec4(uv, 0.5 + 0.5 * sin(u_time), 1.0);
194
+ }
195
+ ```
@@ -0,0 +1,2 @@
1
+ #!/usr/bin/env node
2
+ export {};
package/dist/index.js ADDED
@@ -0,0 +1,632 @@
1
+ #!/usr/bin/env node
2
+ import { chmodSync, existsSync, mkdirSync, readFileSync, renameSync, statSync, writeFileSync, } from 'node:fs';
3
+ import { homedir } from 'node:os';
4
+ import { join } from 'node:path';
5
+ const DEFAULT_API_URL = 'https://shaders.chillysoftware.com';
6
+ const DEFAULT_ENV_FILE = join(homedir(), '.config', 'shaders-app', '.env.shaders');
7
+ const DEFAULT_TIMEOUT_MS = 15_000;
8
+ const UUID_V4 = /^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/;
9
+ const TITLE_MAX_BYTES = 100;
10
+ const DESCRIPTION_MAX_BYTES = 500;
11
+ const SOURCE_MAX_BYTES = 128 * 1024;
12
+ const DEFAULT_SHADER_SOURCE = `precision highp float;
13
+
14
+ uniform vec2 u_resolution;
15
+ uniform float u_time;
16
+
17
+ void main() {
18
+ vec2 uv = gl_FragCoord.xy / u_resolution;
19
+ vec3 color = 0.5 + 0.5 * cos(u_time + uv.xyx + vec3(0.0, 2.0, 4.0));
20
+ gl_FragColor = vec4(color, 1.0);
21
+ }`;
22
+ class CliError extends Error {
23
+ exitCode;
24
+ constructor(message, exitCode = 1) {
25
+ super(message);
26
+ this.name = 'CliError';
27
+ this.exitCode = exitCode;
28
+ }
29
+ }
30
+ const isRecord = (value) => typeof value === 'object' && value !== null && !Array.isArray(value);
31
+ const bytes = (value) => new TextEncoder().encode(value).byteLength;
32
+ const parseEnvValue = (value) => {
33
+ const trimmed = value.trim();
34
+ if (trimmed.length >= 2 && trimmed.startsWith("'") && trimmed.endsWith("'")) {
35
+ return trimmed.slice(1, -1).replaceAll("'\\''", "'");
36
+ }
37
+ if (trimmed.length >= 2 && trimmed.startsWith('"') && trimmed.endsWith('"')) {
38
+ try {
39
+ return JSON.parse(trimmed);
40
+ }
41
+ catch {
42
+ throw new CliError(`Invalid quoted value in ${DEFAULT_ENV_FILE}.`);
43
+ }
44
+ }
45
+ return trimmed.replace(/\s+#.*$/, '');
46
+ };
47
+ const loadCredentialFile = (filePath) => {
48
+ if (!existsSync(filePath))
49
+ return {};
50
+ if (process.platform !== 'win32' && (statSync(filePath).mode & 0o077) !== 0) {
51
+ throw new CliError(`Credential file ${filePath} must be readable only by its owner (chmod 600).`);
52
+ }
53
+ const values = {};
54
+ for (const line of readFileSync(filePath, 'utf8').split(/\r?\n/)) {
55
+ const trimmed = line.trim();
56
+ if (!trimmed || trimmed.startsWith('#'))
57
+ continue;
58
+ const match = /^(?:export\s+)?([A-Za-z_][A-Za-z0-9_]*)\s*=\s*(.*)$/.exec(trimmed);
59
+ if (!match)
60
+ throw new CliError(`Invalid credential-file line in ${filePath}.`);
61
+ const [, key, rawValue] = match;
62
+ if (key !== 'SHADER_API_KEY' && key !== 'SHADER_API_URL')
63
+ continue;
64
+ values[key] = parseEnvValue(rawValue);
65
+ }
66
+ return values;
67
+ };
68
+ const normalizeApiUrl = (value) => {
69
+ let url;
70
+ try {
71
+ url = new URL(value);
72
+ }
73
+ catch {
74
+ throw new CliError(`Invalid API URL: ${value}`);
75
+ }
76
+ if (url.username ||
77
+ url.password ||
78
+ url.search ||
79
+ url.hash ||
80
+ (url.pathname !== '/' && url.pathname !== '')) {
81
+ throw new CliError('API URL must contain only an origin, without credentials, a path, query, or hash.');
82
+ }
83
+ const isLoopback = ['localhost', '127.0.0.1', '[::1]'].includes(url.hostname);
84
+ if (url.protocol !== 'https:' && !(url.protocol === 'http:' && isLoopback)) {
85
+ throw new CliError('Non-loopback API URLs must use HTTPS.');
86
+ }
87
+ url.pathname = '/';
88
+ return url;
89
+ };
90
+ const loadConfig = (format, apiUrlOverride) => {
91
+ const fileEnv = loadCredentialFile(DEFAULT_ENV_FILE);
92
+ const apiToken = process.env.SHADER_API_KEY ?? fileEnv.SHADER_API_KEY;
93
+ if (!apiToken) {
94
+ throw new CliError(`SHADER_API_KEY is required. Set it in the environment or ${DEFAULT_ENV_FILE}.`);
95
+ }
96
+ const apiUrl = normalizeApiUrl(apiUrlOverride ?? process.env.SHADER_API_URL ?? fileEnv.SHADER_API_URL ?? DEFAULT_API_URL);
97
+ return { apiUrl, apiToken, format, timeoutMs: DEFAULT_TIMEOUT_MS };
98
+ };
99
+ const parseOptions = (args, valueNames, flagNames) => {
100
+ const values = new Map();
101
+ const flags = new Set();
102
+ const positionals = [];
103
+ for (let index = 0; index < args.length; index += 1) {
104
+ const token = args[index];
105
+ if (!token.startsWith('--')) {
106
+ positionals.push(token);
107
+ continue;
108
+ }
109
+ const equals = token.indexOf('=');
110
+ const name = equals === -1 ? token.slice(2) : token.slice(2, equals);
111
+ const inlineValue = equals === -1 ? undefined : token.slice(equals + 1);
112
+ if (flagNames.has(name)) {
113
+ if (inlineValue !== undefined)
114
+ throw new CliError(`Option --${name} does not take a value.`);
115
+ flags.add(name);
116
+ continue;
117
+ }
118
+ if (!valueNames.has(name))
119
+ throw new CliError(`Unknown option: --${name}`);
120
+ const value = inlineValue ?? args[++index];
121
+ if (value === undefined || value.startsWith('--'))
122
+ throw new CliError(`Option --${name} requires a value.`);
123
+ values.set(name, value);
124
+ }
125
+ return { values, flags, positionals };
126
+ };
127
+ const option = (parsed, name) => parsed.values.get(name);
128
+ const has = (parsed, name) => parsed.flags.has(name);
129
+ const parseGlobal = (args) => {
130
+ let index = 0;
131
+ let apiUrl;
132
+ let format;
133
+ let help = false;
134
+ while (index < args.length) {
135
+ const token = args[index];
136
+ if (!token.startsWith('--'))
137
+ break;
138
+ if (token === '--help' || token === '-h') {
139
+ help = true;
140
+ index += 1;
141
+ continue;
142
+ }
143
+ if (token === '--json') {
144
+ format = 'json';
145
+ index += 1;
146
+ continue;
147
+ }
148
+ if (token === '--api-url') {
149
+ apiUrl = args[index + 1];
150
+ if (!apiUrl || apiUrl.startsWith('--'))
151
+ throw new CliError('--api-url requires a value.');
152
+ index += 2;
153
+ continue;
154
+ }
155
+ if (token === '--format') {
156
+ const value = args[index + 1];
157
+ if (value !== 'human' && value !== 'json')
158
+ throw new CliError('--format must be human or json.');
159
+ format = value;
160
+ index += 2;
161
+ continue;
162
+ }
163
+ break;
164
+ }
165
+ return {
166
+ apiUrl,
167
+ format: format ?? 'human',
168
+ help,
169
+ command: args[index],
170
+ rest: args.slice(index + 1),
171
+ };
172
+ };
173
+ const requireUuid = (value, label) => {
174
+ if (!UUID_V4.test(value))
175
+ throw new CliError(`${label} must be a canonical lowercase UUID.`);
176
+ return value;
177
+ };
178
+ const requireDocument = (value) => {
179
+ if (!isRecord(value) ||
180
+ Object.keys(value).some((key) => !['title', 'description', 'source'].includes(key))) {
181
+ throw new CliError('Document must contain only title, description, and source.');
182
+ }
183
+ if (typeof value.title !== 'string' ||
184
+ typeof value.description !== 'string' ||
185
+ typeof value.source !== 'string') {
186
+ throw new CliError('Document title, description, and source must all be strings.');
187
+ }
188
+ return validateDocument({
189
+ title: value.title,
190
+ description: value.description,
191
+ source: value.source,
192
+ });
193
+ };
194
+ const validateDocument = (document) => {
195
+ if (!document.title || bytes(document.title) > TITLE_MAX_BYTES) {
196
+ throw new CliError('Title must be non-empty and at most 100 UTF-8 bytes.');
197
+ }
198
+ if (bytes(document.description) > DESCRIPTION_MAX_BYTES) {
199
+ throw new CliError('Description must be at most 500 UTF-8 bytes.');
200
+ }
201
+ if (bytes(document.source) > SOURCE_MAX_BYTES) {
202
+ throw new CliError('Source must be at most 131072 UTF-8 bytes.');
203
+ }
204
+ return document;
205
+ };
206
+ const readText = async (filePath) => {
207
+ if (filePath !== '-')
208
+ return readFileSync(filePath, 'utf8');
209
+ const chunks = [];
210
+ for await (const chunk of process.stdin)
211
+ chunks.push(Buffer.isBuffer(chunk) ? chunk : Buffer.from(chunk));
212
+ return Buffer.concat(chunks).toString('utf8');
213
+ };
214
+ const readSecretPrompt = async () => {
215
+ if (!process.stdin.isTTY || !process.stdout.isTTY || !process.stdin.setRawMode) {
216
+ throw new CliError('Interactive API-key input requires a TTY; use --api-key-stdin for piped input.');
217
+ }
218
+ const wasRaw = process.stdin.isRaw;
219
+ let value = '';
220
+ process.stdout.write('API key: ');
221
+ process.stdin.setRawMode(true);
222
+ process.stdin.resume();
223
+ process.stdin.setEncoding('utf8');
224
+ try {
225
+ await new Promise((resolve, reject) => {
226
+ const onData = (chunk) => {
227
+ for (const character of chunk) {
228
+ if (character === '\u0003') {
229
+ reject(new CliError('API-key input cancelled.'));
230
+ return;
231
+ }
232
+ if (character === '\r' || character === '\n') {
233
+ resolve();
234
+ return;
235
+ }
236
+ if (character === '\u007f' || character === '\b') {
237
+ value = value.slice(0, -1);
238
+ continue;
239
+ }
240
+ value += character;
241
+ }
242
+ };
243
+ process.stdin.on('data', onData);
244
+ process.stdin.once('error', reject);
245
+ });
246
+ }
247
+ finally {
248
+ process.stdin.removeAllListeners('data');
249
+ process.stdin.setRawMode(wasRaw ?? false);
250
+ process.stdin.pause();
251
+ process.stdout.write('\n');
252
+ }
253
+ return value;
254
+ };
255
+ const shellQuote = (value) => `'${value.replaceAll("'", "'\\''")}'`;
256
+ const writeCredentialFile = (apiKey, apiUrl) => {
257
+ const directory = join(homedir(), '.config', 'shaders-app');
258
+ mkdirSync(directory, { recursive: true, mode: 0o700 });
259
+ chmodSync(directory, 0o700);
260
+ const lines = [`export SHADER_API_KEY=${shellQuote(apiKey)}`];
261
+ if (apiUrl && apiUrl.toString() !== `${DEFAULT_API_URL}/`) {
262
+ lines.push(`export SHADER_API_URL=${shellQuote(apiUrl.origin)}`);
263
+ }
264
+ const temporaryPath = `${DEFAULT_ENV_FILE}.${process.pid}.tmp`;
265
+ writeFileSync(temporaryPath, `${lines.join('\n')}\n`, {
266
+ encoding: 'utf8',
267
+ mode: 0o600,
268
+ flag: 'wx',
269
+ });
270
+ chmodSync(temporaryPath, 0o600);
271
+ renameSync(temporaryPath, DEFAULT_ENV_FILE);
272
+ chmodSync(DEFAULT_ENV_FILE, 0o600);
273
+ };
274
+ const parseJsonFile = (filePath) => {
275
+ try {
276
+ return JSON.parse(readFileSync(filePath, 'utf8'));
277
+ }
278
+ catch {
279
+ throw new CliError(`Unable to parse JSON document file: ${filePath}`);
280
+ }
281
+ };
282
+ const shareUrl = (config, shaderId) => new URL(`/s/${shaderId}`, config.apiUrl).toString();
283
+ const responseBody = async (response) => {
284
+ const text = await response.text();
285
+ if (!text)
286
+ return undefined;
287
+ try {
288
+ return JSON.parse(text);
289
+ }
290
+ catch {
291
+ return undefined;
292
+ }
293
+ };
294
+ const errorMessage = (body) => {
295
+ if (!isRecord(body) || !isRecord(body.error) || typeof body.error.message !== 'string')
296
+ return undefined;
297
+ return body.error.message;
298
+ };
299
+ const request = async (config, path, init = {}) => {
300
+ const controller = new AbortController();
301
+ const timeout = setTimeout(() => controller.abort(), config.timeoutMs);
302
+ try {
303
+ const response = await fetch(new URL(path, config.apiUrl), {
304
+ ...init,
305
+ signal: controller.signal,
306
+ headers: {
307
+ Accept: 'application/json',
308
+ Authorization: `Bearer ${config.apiToken}`,
309
+ ...(init.body === undefined ? {} : { 'Content-Type': 'application/json' }),
310
+ ...init.headers,
311
+ },
312
+ });
313
+ const body = await responseBody(response);
314
+ if (!response.ok) {
315
+ throw new CliError(errorMessage(body) ?? `The shader service returned HTTP ${response.status}.`);
316
+ }
317
+ return body;
318
+ }
319
+ catch (error) {
320
+ if (error instanceof CliError)
321
+ throw error;
322
+ if (error instanceof Error && error.name === 'AbortError')
323
+ throw new CliError('The request timed out.');
324
+ throw new CliError(error instanceof Error ? error.message : 'The shader service is unavailable.');
325
+ }
326
+ finally {
327
+ clearTimeout(timeout);
328
+ }
329
+ };
330
+ const asSnapshot = (value) => {
331
+ if (!isRecord(value) ||
332
+ typeof value.id !== 'string' ||
333
+ typeof value.revision !== 'number' ||
334
+ typeof value.title !== 'string' ||
335
+ typeof value.description !== 'string' ||
336
+ typeof value.source !== 'string') {
337
+ throw new CliError('The shader service returned an invalid snapshot.');
338
+ }
339
+ return value;
340
+ };
341
+ const asListPage = (value) => {
342
+ if (!isRecord(value) ||
343
+ !Array.isArray(value.shaders) ||
344
+ !(value.nextCursor === null || typeof value.nextCursor === 'string')) {
345
+ throw new CliError('The shader service returned an invalid shader list.');
346
+ }
347
+ return value;
348
+ };
349
+ const asCreateResult = (value) => {
350
+ if (!isRecord(value) || typeof value.deduplicated !== 'boolean') {
351
+ throw new CliError('The shader service returned an invalid create result.');
352
+ }
353
+ return { snapshot: asSnapshot(value.snapshot), deduplicated: value.deduplicated };
354
+ };
355
+ const asMutationResult = (value) => {
356
+ if (!isRecord(value) ||
357
+ typeof value.changed !== 'boolean' ||
358
+ typeof value.deduplicated !== 'boolean') {
359
+ throw new CliError('The shader service returned an invalid mutation result.');
360
+ }
361
+ return {
362
+ snapshot: asSnapshot(value.snapshot),
363
+ changed: value.changed,
364
+ deduplicated: value.deduplicated,
365
+ };
366
+ };
367
+ const jsonBody = (body) => ({ method: 'POST', body: JSON.stringify(body) });
368
+ const resultWithShareUrl = (config, result) => ({
369
+ ...result,
370
+ shareUrl: shareUrl(config, result.snapshot.id),
371
+ });
372
+ const printResult = (config, value, human) => {
373
+ if (config.format === 'json') {
374
+ console.log(JSON.stringify(value, null, '\t'));
375
+ return;
376
+ }
377
+ console.log(human);
378
+ };
379
+ const documentSummary = (document) => ({
380
+ title: document.title,
381
+ description: document.description,
382
+ sourceBytes: bytes(document.source),
383
+ });
384
+ const createCommand = async (config, args) => {
385
+ const parsed = parseOptions(args, new Set(['title', 'description', 'source-file', 'request-id', 'format']), new Set(['json', 'dry-run']));
386
+ const title = option(parsed, 'title');
387
+ if (!title)
388
+ throw new CliError('--title is required.');
389
+ if (parsed.positionals.length > 0)
390
+ throw new CliError(`Unexpected argument: ${parsed.positionals[0]}`);
391
+ const source = option(parsed, 'source-file')
392
+ ? await readText(option(parsed, 'source-file'))
393
+ : DEFAULT_SHADER_SOURCE;
394
+ const document = validateDocument({
395
+ title,
396
+ description: option(parsed, 'description') ?? '',
397
+ source,
398
+ });
399
+ const requestId = requireUuid(option(parsed, 'request-id') ?? crypto.randomUUID(), 'Request ID');
400
+ const dryRun = has(parsed, 'dry-run');
401
+ const result = {
402
+ command: 'create',
403
+ requestId,
404
+ document: documentSummary(document),
405
+ apiUrl: config.apiUrl.toString(),
406
+ };
407
+ if (dryRun) {
408
+ printResult(config, { ...result, dryRun: true }, `Would create ${JSON.stringify(documentSummary(document))} at ${config.apiUrl}`);
409
+ return;
410
+ }
411
+ const created = asCreateResult(await request(config, '/api/shaders', jsonBody({ requestId, ...document })));
412
+ const output = { command: 'create', requestId, ...resultWithShareUrl(config, created) };
413
+ printResult(config, output, `Created ${created.snapshot.id} (revision ${created.snapshot.revision}) at ${config.apiUrl}\n${shareUrl(config, created.snapshot.id)}`);
414
+ };
415
+ const listCommand = async (config, args) => {
416
+ const parsed = parseOptions(args, new Set(['limit', 'cursor', 'format']), new Set(['json', 'all']));
417
+ if (parsed.positionals.length > 0)
418
+ throw new CliError(`Unexpected argument: ${parsed.positionals[0]}`);
419
+ const rawLimit = option(parsed, 'limit');
420
+ const limit = rawLimit === undefined ? undefined : Number(rawLimit);
421
+ if (limit !== undefined && (!Number.isInteger(limit) || limit < 1 || limit > 100)) {
422
+ throw new CliError('--limit must be an integer from 1 through 100.');
423
+ }
424
+ let cursor = option(parsed, 'cursor');
425
+ const shaders = [];
426
+ let nextCursor = cursor ?? null;
427
+ while (true) {
428
+ const params = new URLSearchParams();
429
+ if (limit !== undefined)
430
+ params.set('limit', String(limit));
431
+ if (cursor)
432
+ params.set('cursor', cursor);
433
+ const page = asListPage(await request(config, `/api/shaders?${params}`));
434
+ shaders.push(...page.shaders);
435
+ nextCursor = page.nextCursor;
436
+ if (!has(parsed, 'all') || !nextCursor)
437
+ break;
438
+ cursor = nextCursor;
439
+ }
440
+ const output = has(parsed, 'all')
441
+ ? { command: 'list', shaders, nextCursor: null, complete: true }
442
+ : { command: 'list', shaders, nextCursor };
443
+ const human = shaders.length === 0
444
+ ? 'No shaders found.'
445
+ : shaders
446
+ .map((shader) => `${shader.id}\t${shader.title}\trevision ${shader.revision}`)
447
+ .join('\n');
448
+ printResult(config, output, human);
449
+ };
450
+ const getCommand = async (config, args) => {
451
+ const parsed = parseOptions(args, new Set(['format']), new Set(['json', 'source']));
452
+ const [shaderId] = parsed.positionals;
453
+ if (!shaderId)
454
+ throw new CliError('A shader ID is required.');
455
+ if (parsed.positionals.length > 1)
456
+ throw new CliError(`Unexpected argument: ${parsed.positionals[1]}`);
457
+ const snapshot = asSnapshot(await request(config, `/api/shaders/${encodeURIComponent(requireUuid(shaderId, 'Shader ID'))}`));
458
+ if (has(parsed, 'source')) {
459
+ process.stdout.write(snapshot.source);
460
+ return;
461
+ }
462
+ const output = { command: 'get', snapshot, shareUrl: shareUrl(config, snapshot.id) };
463
+ printResult(config, output, `${snapshot.title} (revision ${snapshot.revision})\n${shareUrl(config, snapshot.id)}`);
464
+ };
465
+ const editCommand = async (config, args) => {
466
+ const parsed = parseOptions(args, new Set(['title', 'description', 'source-file', 'document-file', 'mutation-id', 'format']), new Set(['json', 'dry-run']));
467
+ const [rawShaderId] = parsed.positionals;
468
+ if (!rawShaderId)
469
+ throw new CliError('A shader ID is required.');
470
+ if (parsed.positionals.length > 1)
471
+ throw new CliError(`Unexpected argument: ${parsed.positionals[1]}`);
472
+ const shaderId = requireUuid(rawShaderId, 'Shader ID');
473
+ const fieldNames = ['title', 'description', 'source-file'].filter((name) => option(parsed, name) !== undefined);
474
+ const documentFile = option(parsed, 'document-file');
475
+ if (documentFile && fieldNames.length > 0)
476
+ throw new CliError('--document-file cannot be combined with field options.');
477
+ if (!documentFile && fieldNames.length === 0)
478
+ throw new CliError('Provide an edit field or --document-file.');
479
+ const current = asSnapshot(await request(config, `/api/shaders/${encodeURIComponent(shaderId)}`));
480
+ let document;
481
+ if (documentFile) {
482
+ document = requireDocument(parseJsonFile(documentFile));
483
+ }
484
+ else {
485
+ document = {
486
+ title: option(parsed, 'title') ?? current.title,
487
+ description: option(parsed, 'description') ?? current.description,
488
+ source: option(parsed, 'source-file')
489
+ ? await readText(option(parsed, 'source-file'))
490
+ : current.source,
491
+ };
492
+ document = validateDocument(document);
493
+ }
494
+ const mutationId = requireUuid(option(parsed, 'mutation-id') ?? crypto.randomUUID(), 'Mutation ID');
495
+ const summary = {
496
+ command: 'edit',
497
+ shaderId,
498
+ mutationId,
499
+ baselineRevision: current.revision,
500
+ document: documentSummary(document),
501
+ apiUrl: config.apiUrl.toString(),
502
+ };
503
+ if (has(parsed, 'dry-run')) {
504
+ printResult(config, { ...summary, dryRun: true }, `Would edit ${shaderId} at ${config.apiUrl}`);
505
+ return;
506
+ }
507
+ const updated = asMutationResult(await request(config, `/api/shaders/${encodeURIComponent(shaderId)}`, {
508
+ method: 'PUT',
509
+ body: JSON.stringify({ mutationId, document }),
510
+ }));
511
+ const output = { ...summary, ...resultWithShareUrl(config, updated) };
512
+ printResult(config, output, `Updated ${shaderId} to revision ${updated.snapshot.revision} at ${config.apiUrl}\n${shareUrl(config, shaderId)}`);
513
+ };
514
+ const deleteCommand = async (config, args) => {
515
+ const parsed = parseOptions(args, new Set(['mutation-id', 'format']), new Set(['json', 'yes', 'dry-run']));
516
+ const [rawShaderId] = parsed.positionals;
517
+ if (!rawShaderId)
518
+ throw new CliError('A shader ID is required.');
519
+ if (parsed.positionals.length > 1)
520
+ throw new CliError(`Unexpected argument: ${parsed.positionals[1]}`);
521
+ const shaderId = requireUuid(rawShaderId, 'Shader ID');
522
+ if (!has(parsed, 'yes'))
523
+ throw new CliError('Deletion requires --yes.');
524
+ const mutationId = requireUuid(option(parsed, 'mutation-id') ?? crypto.randomUUID(), 'Mutation ID');
525
+ const output = { command: 'delete', shaderId, mutationId, shareUrl: shareUrl(config, shaderId) };
526
+ if (has(parsed, 'dry-run')) {
527
+ printResult(config, { ...output, dryRun: true }, `Would delete ${shaderId} at ${config.apiUrl}`);
528
+ return;
529
+ }
530
+ await request(config, `/api/shaders/${encodeURIComponent(shaderId)}`, {
531
+ method: 'DELETE',
532
+ body: JSON.stringify({ mutationId }),
533
+ });
534
+ printResult(config, output, `Deleted ${shaderId} at ${config.apiUrl}`);
535
+ };
536
+ const initCommand = async (args, globalApiUrl, fallbackFormat) => {
537
+ const parsed = parseOptions(args, new Set(['api-url', 'format']), new Set(['json', 'force', 'api-key-stdin']));
538
+ if (parsed.positionals.length > 0)
539
+ throw new CliError(`Unexpected argument: ${parsed.positionals[0]}`);
540
+ if (existsSync(DEFAULT_ENV_FILE) && !has(parsed, 'force')) {
541
+ throw new CliError(`Credential file already exists: ${DEFAULT_ENV_FILE}. Use --force to replace it.`);
542
+ }
543
+ const apiUrl = normalizeApiUrl(option(parsed, 'api-url') ?? globalApiUrl ?? DEFAULT_API_URL);
544
+ const rawApiKey = has(parsed, 'api-key-stdin') ? await readText('-') : await readSecretPrompt();
545
+ const apiKey = rawApiKey.trim();
546
+ if (!apiKey || /\s/.test(apiKey))
547
+ throw new CliError('API key must be non-empty and contain no whitespace.');
548
+ writeCredentialFile(apiKey, apiUrl);
549
+ const format = formatFromCommandArgs(args, fallbackFormat);
550
+ const output = { command: 'init', path: DEFAULT_ENV_FILE, apiUrl: apiUrl.toString() };
551
+ if (format === 'json') {
552
+ console.log(JSON.stringify(output, null, '\t'));
553
+ }
554
+ else {
555
+ console.log(`Wrote ${DEFAULT_ENV_FILE} for ${apiUrl}`);
556
+ }
557
+ };
558
+ const formatFromCommandArgs = (args, fallback) => {
559
+ if (args.includes('--json'))
560
+ return 'json';
561
+ for (let index = 0; index < args.length; index += 1) {
562
+ const token = args[index];
563
+ const value = token.startsWith('--format=')
564
+ ? token.slice('--format='.length)
565
+ : token === '--format'
566
+ ? args[index + 1]
567
+ : undefined;
568
+ if (value !== undefined) {
569
+ if (value !== 'human' && value !== 'json')
570
+ throw new CliError('--format must be human or json.');
571
+ return value;
572
+ }
573
+ }
574
+ return fallback;
575
+ };
576
+ const HELP = `Usage: shader [--api-url URL] [--format human|json] <command>
577
+
578
+ Production is the default target. Set SHADER_API_URL to use another API origin.
579
+ Credentials are read from SHADER_API_KEY or ~/.config/shaders-app/.env.shaders.
580
+
581
+ Commands:
582
+ init [--api-url URL] [--force] [--api-key-stdin]
583
+ create --title TITLE [--description TEXT] [--source-file PATH|-] [--dry-run]
584
+ list [--limit 1..100] [--cursor CURSOR] [--all]
585
+ get SHADER_ID [--source]
586
+ edit SHADER_ID [--source-file PATH|-] [--title TITLE] [--description TEXT]
587
+ [--document-file JSON] [--dry-run]
588
+ delete SHADER_ID --yes [--dry-run]
589
+
590
+ Use --json for stable machine-readable output. API tokens are never accepted as arguments.`;
591
+ const main = async () => {
592
+ const global = parseGlobal(process.argv.slice(2));
593
+ if (global.help || !global.command) {
594
+ console.log(HELP);
595
+ return;
596
+ }
597
+ const commandArgs = global.rest;
598
+ if (global.command === 'init') {
599
+ await initCommand(commandArgs, global.apiUrl, global.format);
600
+ return;
601
+ }
602
+ const config = loadConfig(global.format, global.apiUrl);
603
+ const effectiveConfig = { ...config, format: formatFromCommandArgs(commandArgs, global.format) };
604
+ switch (global.command) {
605
+ case 'create':
606
+ await createCommand(effectiveConfig, commandArgs);
607
+ return;
608
+ case 'list':
609
+ await listCommand(effectiveConfig, commandArgs);
610
+ return;
611
+ case 'get':
612
+ await getCommand(effectiveConfig, commandArgs);
613
+ return;
614
+ case 'edit':
615
+ await editCommand(effectiveConfig, commandArgs);
616
+ return;
617
+ case 'delete':
618
+ await deleteCommand(effectiveConfig, commandArgs);
619
+ return;
620
+ default:
621
+ throw new CliError(`Unknown command: ${global.command}\n\n${HELP}`, 2);
622
+ }
623
+ };
624
+ try {
625
+ await main();
626
+ }
627
+ catch (error) {
628
+ const message = error instanceof Error ? error.message : 'Unexpected CLI error.';
629
+ console.error(`shader: ${message}`);
630
+ process.exitCode = error instanceof CliError ? error.exitCode : 1;
631
+ }
632
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
package/package.json ADDED
@@ -0,0 +1,46 @@
1
+ {
2
+ "name": "@dudasaus/shaders-app-cli",
3
+ "version": "0.1.0",
4
+ "description": "Agent-friendly CLI for the Shader Web App",
5
+ "license": "MIT",
6
+ "repository": {
7
+ "type": "git",
8
+ "url": "git+https://github.com/dudasaus/shader-web-app.git",
9
+ "directory": "cli"
10
+ },
11
+ "homepage": "https://github.com/dudasaus/shader-web-app/tree/main/cli#readme",
12
+ "bugs": {
13
+ "url": "https://github.com/dudasaus/shader-web-app/issues"
14
+ },
15
+ "keywords": [
16
+ "cli",
17
+ "glsl",
18
+ "shader",
19
+ "webgl",
20
+ "agents"
21
+ ],
22
+ "type": "module",
23
+ "bin": {
24
+ "shader": "dist/index.js"
25
+ },
26
+ "files": [
27
+ "dist",
28
+ "README.md",
29
+ "LICENSE"
30
+ ],
31
+ "publishConfig": {
32
+ "access": "public"
33
+ },
34
+ "engines": {
35
+ "node": ">=22"
36
+ },
37
+ "scripts": {
38
+ "build": "tsc -p tsconfig.json",
39
+ "typecheck": "tsc -p tsconfig.json --noEmit",
40
+ "prepublishOnly": "npm run build"
41
+ },
42
+ "devDependencies": {
43
+ "@types/node": "^26.0.1",
44
+ "typescript": "^5.5.2"
45
+ }
46
+ }