termcast 1.4.1 → 1.5.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/dist/build.d.ts.map +1 -1
- package/dist/build.js +8 -7
- package/dist/build.js.map +1 -1
- package/dist/cli.js +0 -40
- package/dist/cli.js.map +1 -1
- package/dist/components/bar-graph.d.ts +23 -8
- package/dist/components/bar-graph.d.ts.map +1 -1
- package/dist/components/bar-graph.js +84 -40
- package/dist/components/bar-graph.js.map +1 -1
- package/dist/components/dotted-line-graph.d.ts +86 -0
- package/dist/components/dotted-line-graph.d.ts.map +1 -0
- package/dist/components/dotted-line-graph.js +260 -0
- package/dist/components/dotted-line-graph.js.map +1 -0
- package/dist/components/extension-preferences.d.ts.map +1 -1
- package/dist/components/extension-preferences.js +1 -10
- package/dist/components/extension-preferences.js.map +1 -1
- package/dist/components/graph.d.ts.map +1 -1
- package/dist/components/graph.js +7 -1
- package/dist/components/graph.js.map +1 -1
- package/dist/components/histogram.d.ts +42 -0
- package/dist/components/histogram.d.ts.map +1 -0
- package/dist/components/histogram.js +115 -0
- package/dist/components/histogram.js.map +1 -0
- package/dist/components/horizontal-bar-graph.d.ts +47 -0
- package/dist/components/horizontal-bar-graph.d.ts.map +1 -0
- package/dist/components/horizontal-bar-graph.js +137 -0
- package/dist/components/horizontal-bar-graph.js.map +1 -0
- package/dist/components/list.d.ts +2 -0
- package/dist/components/list.d.ts.map +1 -1
- package/dist/components/list.js +10 -10
- package/dist/components/list.js.map +1 -1
- package/dist/examples/bar-graph-weekly.js +2 -2
- package/dist/examples/bar-graph-weekly.js.map +1 -1
- package/dist/examples/charts-showcase-barchart.d.ts +2 -0
- package/dist/examples/charts-showcase-barchart.d.ts.map +1 -0
- package/dist/examples/charts-showcase-barchart.js +10 -0
- package/dist/examples/charts-showcase-barchart.js.map +1 -0
- package/dist/examples/charts-showcase-bargraph.d.ts +2 -0
- package/dist/examples/charts-showcase-bargraph.d.ts.map +1 -0
- package/dist/examples/charts-showcase-bargraph.js +60 -0
- package/dist/examples/charts-showcase-bargraph.js.map +1 -0
- package/dist/examples/charts-showcase-candle.d.ts +2 -0
- package/dist/examples/charts-showcase-candle.d.ts.map +1 -0
- package/dist/examples/charts-showcase-candle.js +30 -0
- package/dist/examples/charts-showcase-candle.js.map +1 -0
- package/dist/examples/charts-showcase-graph.d.ts +2 -0
- package/dist/examples/charts-showcase-graph.d.ts.map +1 -0
- package/dist/examples/charts-showcase-graph.js +33 -0
- package/dist/examples/charts-showcase-graph.js.map +1 -0
- package/dist/examples/charts-showcase-heatmap.d.ts +2 -0
- package/dist/examples/charts-showcase-heatmap.d.ts.map +1 -0
- package/dist/examples/charts-showcase-heatmap.js +36 -0
- package/dist/examples/charts-showcase-heatmap.js.map +1 -0
- package/dist/examples/charts-showcase-mixed.d.ts +2 -0
- package/dist/examples/charts-showcase-mixed.d.ts.map +1 -0
- package/dist/examples/charts-showcase-mixed.js +30 -0
- package/dist/examples/charts-showcase-mixed.js.map +1 -0
- package/dist/examples/charts-showcase-progress.d.ts +2 -0
- package/dist/examples/charts-showcase-progress.d.ts.map +1 -0
- package/dist/examples/charts-showcase-progress.js +10 -0
- package/dist/examples/charts-showcase-progress.js.map +1 -0
- package/dist/examples/graph-multi-series.js +1 -1
- package/dist/examples/graph-multi-series.js.map +1 -1
- package/dist/examples/horizontal-bar-graph-weekly.d.ts +2 -0
- package/dist/examples/horizontal-bar-graph-weekly.d.ts.map +1 -0
- package/dist/examples/horizontal-bar-graph-weekly.js +67 -0
- package/dist/examples/horizontal-bar-graph-weekly.js.map +1 -0
- package/dist/examples/simple-dotted-line-graph.d.ts +2 -0
- package/dist/examples/simple-dotted-line-graph.d.ts.map +1 -0
- package/dist/examples/simple-dotted-line-graph.js +39 -0
- package/dist/examples/simple-dotted-line-graph.js.map +1 -0
- package/dist/examples/simple-histogram.d.ts +2 -0
- package/dist/examples/simple-histogram.d.ts.map +1 -0
- package/dist/examples/simple-histogram.js +47 -0
- package/dist/examples/simple-histogram.js.map +1 -0
- package/dist/index.d.ts +6 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +6 -0
- package/dist/index.js.map +1 -1
- package/dist/platform/node/sqlite.d.ts +6 -5
- package/dist/platform/node/sqlite.d.ts.map +1 -1
- package/dist/platform/node/sqlite.js +30 -14
- package/dist/platform/node/sqlite.js.map +1 -1
- package/dist/theme.d.ts.map +1 -1
- package/dist/theme.js +11 -9
- package/dist/theme.js.map +1 -1
- package/dist/utils/run-command.d.ts.map +1 -1
- package/dist/utils/run-command.js +8 -19
- package/dist/utils/run-command.js.map +1 -1
- package/dist/utils.d.ts +1 -19
- package/dist/utils.d.ts.map +1 -1
- package/dist/utils.js +1 -100
- package/dist/utils.js.map +1 -1
- package/package.json +6 -8
- package/src/build.tsx +11 -10
- package/src/cli.tsx +3 -40
- package/src/compile.vitest.tsx +3 -3
- package/src/components/bar-graph.tsx +217 -111
- package/src/components/dotted-line-graph.tsx +407 -0
- package/src/components/extension-preferences.tsx +2 -12
- package/src/components/graph.tsx +5 -1
- package/src/components/histogram.tsx +228 -0
- package/src/components/horizontal-bar-graph.tsx +279 -0
- package/src/components/list.tsx +20 -15
- package/src/examples/action-shortcut.vitest.tsx +17 -17
- package/src/examples/bar-graph-weekly.tsx +2 -2
- package/src/examples/bar-graph-weekly.vitest.tsx +63 -62
- package/src/examples/charts-showcase-bargraph.tsx +103 -0
- package/src/examples/detail-metadata-showcase.vitest.tsx +12 -12
- package/src/examples/form-basic.vitest.tsx +11 -11
- package/src/examples/form-dropdown.vitest.tsx +11 -11
- package/src/examples/form-scroll.vitest.tsx +1 -1
- package/src/examples/form-tagpicker.vitest.tsx +11 -11
- package/src/examples/github.vitest.tsx +22 -22
- package/src/examples/graph-bar-chart.vitest.tsx +8 -8
- package/src/examples/graph-multi-series.tsx +1 -1
- package/src/examples/graph-row.vitest.tsx +14 -14
- package/src/examples/graph-styles.vitest.tsx +77 -77
- package/src/examples/horizontal-bar-graph-weekly.tsx +138 -0
- package/src/examples/horizontal-bar-graph-weekly.vitest.tsx +164 -0
- package/src/examples/list-detail-metadata.vitest.tsx +4 -4
- package/src/examples/list-with-detail.vitest.tsx +46 -46
- package/src/examples/simple-candle-chart.vitest.tsx +8 -8
- package/src/examples/simple-dotted-line-graph.tsx +53 -0
- package/src/examples/simple-dotted-line-graph.vitest.tsx +62 -0
- package/src/examples/simple-grid.vitest.tsx +4 -4
- package/src/examples/simple-heatmap.vitest.tsx +9 -9
- package/src/examples/simple-histogram.tsx +90 -0
- package/src/examples/simple-navigation.vitest.tsx +4 -4
- package/src/examples/swift-extension.vitest.tsx +3 -3
- package/src/extensions/dev.vitest.tsx +8 -8
- package/src/index.tsx +21 -0
- package/src/platform/node/sqlite.ts +29 -13
- package/src/theme.tsx +11 -10
- package/src/utils/run-command.tsx +10 -19
- package/src/utils.tsx +0 -163
- package/src/examples/store.tsx +0 -4
- package/src/examples/store.vitest.tsx +0 -78
- package/src/extensions/home.tsx +0 -227
- package/src/extensions/store.tsx +0 -375
package/src/index.tsx
CHANGED
|
@@ -64,6 +64,13 @@ export type {
|
|
|
64
64
|
GraphVariant,
|
|
65
65
|
} from 'termcast/src/components/graph'
|
|
66
66
|
|
|
67
|
+
// Core UI Components - DottedLineGraph
|
|
68
|
+
export { DottedLineGraph } from 'termcast/src/components/dotted-line-graph'
|
|
69
|
+
export type {
|
|
70
|
+
DottedLineGraphProps,
|
|
71
|
+
DottedLineGraphSeriesProps,
|
|
72
|
+
} from 'termcast/src/components/dotted-line-graph'
|
|
73
|
+
|
|
67
74
|
// Core UI Components - Row
|
|
68
75
|
export { Row } from 'termcast/src/components/row'
|
|
69
76
|
export type { RowProps } from 'termcast/src/components/row'
|
|
@@ -86,6 +93,13 @@ export type {
|
|
|
86
93
|
BarGraphSeriesProps,
|
|
87
94
|
} from 'termcast/src/components/bar-graph'
|
|
88
95
|
|
|
96
|
+
// Core UI Components - HorizontalBarGraph
|
|
97
|
+
export { HorizontalBarGraph } from 'termcast/src/components/horizontal-bar-graph'
|
|
98
|
+
export type {
|
|
99
|
+
HorizontalBarGraphProps,
|
|
100
|
+
HorizontalBarGraphSeriesProps,
|
|
101
|
+
} from 'termcast/src/components/horizontal-bar-graph'
|
|
102
|
+
|
|
89
103
|
// Core UI Components - CandleChart
|
|
90
104
|
export { CandleChart } from 'termcast/src/components/candle-chart'
|
|
91
105
|
export type {
|
|
@@ -104,6 +118,13 @@ export type {
|
|
|
104
118
|
HeatmapCellChar,
|
|
105
119
|
} from 'termcast/src/components/heatmap'
|
|
106
120
|
|
|
121
|
+
// Core UI Components - Histogram
|
|
122
|
+
export { Histogram } from 'termcast/src/components/histogram'
|
|
123
|
+
export type {
|
|
124
|
+
HistogramProps,
|
|
125
|
+
HistogramItemProps,
|
|
126
|
+
} from 'termcast/src/components/histogram'
|
|
127
|
+
|
|
107
128
|
// Core UI Components - ProgressBar
|
|
108
129
|
export { ProgressBar } from 'termcast/src/components/progress-bar'
|
|
109
130
|
export type { ProgressBarProps } from 'termcast/src/components/progress-bar'
|
|
@@ -1,13 +1,14 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* SQLite Database for Node.js — uses
|
|
2
|
+
* SQLite Database for Node.js — uses the built-in node:sqlite module.
|
|
3
3
|
*
|
|
4
|
-
* Translates bun:sqlite constructor options ({ create, readwrite })
|
|
5
|
-
* to
|
|
6
|
-
*
|
|
7
|
-
*
|
|
4
|
+
* Translates bun:sqlite constructor options ({ create, readwrite, readonly })
|
|
5
|
+
* to node:sqlite DatabaseSync options ({ readOnly }).
|
|
6
|
+
* Adds a transaction() polyfill since node:sqlite lacks a built-in one.
|
|
7
|
+
*
|
|
8
|
+
* Requires Node.js >= 22.13.0 (node:sqlite without --experimental-sqlite flag).
|
|
8
9
|
*/
|
|
9
10
|
|
|
10
|
-
import
|
|
11
|
+
import { DatabaseSync } from 'node:sqlite'
|
|
11
12
|
|
|
12
13
|
interface DatabaseOptions {
|
|
13
14
|
create?: boolean
|
|
@@ -16,16 +17,31 @@ interface DatabaseOptions {
|
|
|
16
17
|
}
|
|
17
18
|
|
|
18
19
|
function NodeDatabase(path: string, options?: DatabaseOptions) {
|
|
19
|
-
const
|
|
20
|
+
const readOnly = options?.readonly === true || options?.readwrite === false
|
|
20
21
|
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
|
|
22
|
+
const db = new DatabaseSync(path, {
|
|
23
|
+
readOnly,
|
|
24
|
+
})
|
|
25
|
+
|
|
26
|
+
// node:sqlite's DatabaseSync lacks a transaction() helper.
|
|
27
|
+
// Polyfill it to match better-sqlite3 / bun:sqlite behavior:
|
|
28
|
+
// transaction(fn) returns a new function that wraps fn in BEGIN/COMMIT/ROLLBACK.
|
|
29
|
+
const dbAny = db as any
|
|
30
|
+
dbAny.transaction = <T>(fn: () => T): (() => T) => {
|
|
31
|
+
return () => {
|
|
32
|
+
db.exec('BEGIN')
|
|
33
|
+
try {
|
|
34
|
+
const result = fn()
|
|
35
|
+
db.exec('COMMIT')
|
|
36
|
+
return result
|
|
37
|
+
} catch (e) {
|
|
38
|
+
db.exec('ROLLBACK')
|
|
39
|
+
throw e
|
|
40
|
+
}
|
|
41
|
+
}
|
|
26
42
|
}
|
|
27
43
|
|
|
28
|
-
return
|
|
44
|
+
return db
|
|
29
45
|
}
|
|
30
46
|
|
|
31
47
|
export const Database: new (path: string, options?: DatabaseOptions) => DatabaseInstance = NodeDatabase as any
|
package/src/theme.tsx
CHANGED
|
@@ -2,6 +2,7 @@ import { SyntaxStyle } from '@opentui/core'
|
|
|
2
2
|
import { getResolvedTheme, getSyntaxTheme, type ResolvedTheme, defaultThemeName, themeNames } from './themes'
|
|
3
3
|
import { useStore } from './state'
|
|
4
4
|
import { Cache } from './apis/cache'
|
|
5
|
+
import { Color } from './colors'
|
|
5
6
|
|
|
6
7
|
// Global cache for theme persistence (no namespace = global storage).
|
|
7
8
|
// Tracks extensionPath so the cache is recreated if the path changes.
|
|
@@ -83,17 +84,18 @@ export function getInteractiveHoverBackground(theme: ResolvedTheme): string {
|
|
|
83
84
|
return theme.primary
|
|
84
85
|
}
|
|
85
86
|
|
|
86
|
-
// Shared color palette for
|
|
87
|
-
//
|
|
87
|
+
// Shared color palette for chart components.
|
|
88
|
+
// Based on the original Histogram showcase colors, which read better than a
|
|
89
|
+
// strictly semantic theme order for categorical data.
|
|
88
90
|
export function getThemePalette(theme: ResolvedTheme): string[] {
|
|
89
91
|
return [
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
92
|
+
Color.Orange,
|
|
93
|
+
Color.SecondaryText,
|
|
94
|
+
'#00CCCC',
|
|
95
|
+
Color.Purple,
|
|
96
|
+
Color.Yellow,
|
|
97
|
+
Color.Green,
|
|
98
|
+
Color.Blue,
|
|
97
99
|
]
|
|
98
100
|
}
|
|
99
101
|
|
|
@@ -104,4 +106,3 @@ export const markdownSyntaxStyle = new Proxy({} as SyntaxStyle, {
|
|
|
104
106
|
return getMarkdownSyntaxStyle()[prop as keyof SyntaxStyle]
|
|
105
107
|
},
|
|
106
108
|
})
|
|
107
|
-
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import React from 'react'
|
|
2
|
-
import { goke } from 'goke'
|
|
3
2
|
import { useStore } from 'termcast/src/state'
|
|
4
3
|
import { showToast, Toast } from 'termcast/src/apis/toast'
|
|
5
4
|
import { LocalStorage } from 'termcast/src/apis/localstorage'
|
|
@@ -31,17 +30,11 @@ export interface ParsedExtensionArgs {
|
|
|
31
30
|
export function parseExtensionArgs({
|
|
32
31
|
skipArgv = 0,
|
|
33
32
|
}: { skipArgv?: number } = {}): ParsedExtensionArgs {
|
|
34
|
-
|
|
35
|
-
const argv = [
|
|
36
|
-
process.argv[0],
|
|
37
|
-
process.argv[1],
|
|
38
|
-
...process.argv.slice(2 + skipArgv),
|
|
39
|
-
]
|
|
40
|
-
const parsed = goke().parse(argv, { run: false })
|
|
33
|
+
const args = process.argv.slice(2 + skipArgv)
|
|
41
34
|
return {
|
|
42
|
-
commandName:
|
|
43
|
-
showHelp:
|
|
44
|
-
showVersion:
|
|
35
|
+
commandName: args.find((arg) => !arg.startsWith('-')),
|
|
36
|
+
showHelp: args.includes('--help') || args.includes('-h'),
|
|
37
|
+
showVersion: args.includes('--version') || args.includes('-v'),
|
|
45
38
|
}
|
|
46
39
|
}
|
|
47
40
|
|
|
@@ -137,7 +130,7 @@ export async function runCommand(options: RunCommandOptions): Promise<void> {
|
|
|
137
130
|
: undefined
|
|
138
131
|
}
|
|
139
132
|
onSubmit={() => {
|
|
140
|
-
runCommand({ ...options, push: replace || push })
|
|
133
|
+
void runCommand({ ...options, push: replace || push })
|
|
141
134
|
}}
|
|
142
135
|
/>,
|
|
143
136
|
)
|
|
@@ -157,7 +150,7 @@ export async function runCommand(options: RunCommandOptions): Promise<void> {
|
|
|
157
150
|
commandTitle={command.title}
|
|
158
151
|
onSubmit={(args) => {
|
|
159
152
|
useStore.setState({ currentCommandArguments: args })
|
|
160
|
-
runCommand({ ...options, push: replace || push })
|
|
153
|
+
void runCommand({ ...options, push: replace || push })
|
|
161
154
|
}}
|
|
162
155
|
/>,
|
|
163
156
|
)
|
|
@@ -290,12 +283,10 @@ async function checkRequiredPreferences({
|
|
|
290
283
|
const savedCommandPrefs = await LocalStorage.getItem(commandPrefsKey)
|
|
291
284
|
const savedExtensionPrefs = await LocalStorage.getItem(extensionPrefsKey)
|
|
292
285
|
|
|
293
|
-
const parsedCommandPrefs =
|
|
294
|
-
? JSON.parse(savedCommandPrefs
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
? JSON.parse(savedExtensionPrefs as string)
|
|
298
|
-
: {}
|
|
286
|
+
const parsedCommandPrefs =
|
|
287
|
+
typeof savedCommandPrefs === 'string' ? JSON.parse(savedCommandPrefs) : {}
|
|
288
|
+
const parsedExtensionPrefs =
|
|
289
|
+
typeof savedExtensionPrefs === 'string' ? JSON.parse(savedExtensionPrefs) : {}
|
|
299
290
|
|
|
300
291
|
// Check if all required command preferences are set
|
|
301
292
|
for (const pref of commandPrefs) {
|
package/src/utils.tsx
CHANGED
|
@@ -13,10 +13,6 @@ import {
|
|
|
13
13
|
readFileSync,
|
|
14
14
|
ensureDir,
|
|
15
15
|
execCommand,
|
|
16
|
-
readdirSync,
|
|
17
|
-
rmSync,
|
|
18
|
-
mkdirSync,
|
|
19
|
-
cpSync,
|
|
20
16
|
} from '#platform/runtime'
|
|
21
17
|
import {
|
|
22
18
|
parsePackageJson,
|
|
@@ -317,90 +313,11 @@ export function captureException(exception: unknown): void {
|
|
|
317
313
|
console.error('[captureException] Exception captured:', exception)
|
|
318
314
|
}
|
|
319
315
|
|
|
320
|
-
export function getExtensionPath(extensionName: string): string {
|
|
321
|
-
const storeDir = getStoreDirectory()
|
|
322
|
-
return joinPath(storeDir, extensionName)
|
|
323
|
-
}
|
|
324
|
-
|
|
325
|
-
export function getExtensionPackageJsonPath(extensionName: string): string {
|
|
326
|
-
return joinPath(getExtensionPath(extensionName), 'package.json')
|
|
327
|
-
}
|
|
328
|
-
|
|
329
|
-
export function getExtensionPackageJson(
|
|
330
|
-
extensionName: string,
|
|
331
|
-
): RaycastPackageJson | null {
|
|
332
|
-
const packageJsonPath = getExtensionPackageJsonPath(extensionName)
|
|
333
|
-
|
|
334
|
-
if (!fileExists(packageJsonPath)) {
|
|
335
|
-
return null
|
|
336
|
-
}
|
|
337
|
-
|
|
338
|
-
try {
|
|
339
|
-
return parsePackageJson({ packageJsonPath })
|
|
340
|
-
} catch (error) {
|
|
341
|
-
console.error(`Failed to parse package.json for ${extensionName}:`, error)
|
|
342
|
-
return null
|
|
343
|
-
}
|
|
344
|
-
}
|
|
345
|
-
|
|
346
316
|
export interface ExtensionPreferencesInfo {
|
|
347
317
|
hasPreferences: boolean
|
|
348
318
|
hasRequiredPreferences: boolean
|
|
349
319
|
}
|
|
350
320
|
|
|
351
|
-
export function checkExtensionPreferences(
|
|
352
|
-
extensionName: string,
|
|
353
|
-
): ExtensionPreferencesInfo {
|
|
354
|
-
const packageJson = getExtensionPackageJson(extensionName)
|
|
355
|
-
|
|
356
|
-
if (!packageJson) {
|
|
357
|
-
return { hasPreferences: false, hasRequiredPreferences: false }
|
|
358
|
-
}
|
|
359
|
-
|
|
360
|
-
// Check for extension-wide preferences
|
|
361
|
-
const hasExtensionPreferences =
|
|
362
|
-
packageJson.preferences && packageJson.preferences.length > 0
|
|
363
|
-
|
|
364
|
-
// Check if any command has preferences
|
|
365
|
-
const commandsWithPreferences = (packageJson.commands || []).filter(
|
|
366
|
-
(cmd) => cmd.preferences && cmd.preferences.length > 0,
|
|
367
|
-
)
|
|
368
|
-
|
|
369
|
-
const hasPreferences =
|
|
370
|
-
hasExtensionPreferences || commandsWithPreferences.length > 0
|
|
371
|
-
|
|
372
|
-
// Check for required extension-wide preferences
|
|
373
|
-
const requiredExtensionPrefs = (packageJson.preferences || []).filter(
|
|
374
|
-
(pref) => pref.required,
|
|
375
|
-
)
|
|
376
|
-
|
|
377
|
-
// Check if any command has required preferences
|
|
378
|
-
const commandsWithRequiredPrefs = (packageJson.commands || []).filter(
|
|
379
|
-
(cmd) => {
|
|
380
|
-
const requiredPrefs = (cmd.preferences || []).filter(
|
|
381
|
-
(pref) => pref.required,
|
|
382
|
-
)
|
|
383
|
-
return requiredPrefs.length > 0
|
|
384
|
-
},
|
|
385
|
-
)
|
|
386
|
-
|
|
387
|
-
const hasRequiredPreferences =
|
|
388
|
-
requiredExtensionPrefs.length > 0 || commandsWithRequiredPrefs.length > 0
|
|
389
|
-
|
|
390
|
-
return { hasPreferences, hasRequiredPreferences }
|
|
391
|
-
}
|
|
392
|
-
|
|
393
|
-
// Store management types
|
|
394
|
-
interface BundledCommand extends CommandWithFile {
|
|
395
|
-
bundledPath: string
|
|
396
|
-
}
|
|
397
|
-
|
|
398
|
-
interface StoredExtension {
|
|
399
|
-
name: string
|
|
400
|
-
packageJsonPath: string
|
|
401
|
-
commands: BundledCommand[]
|
|
402
|
-
}
|
|
403
|
-
|
|
404
321
|
export function resolveCommandPath({
|
|
405
322
|
commandName,
|
|
406
323
|
dir,
|
|
@@ -425,87 +342,7 @@ export function resolveCommandPath({
|
|
|
425
342
|
return ''
|
|
426
343
|
}
|
|
427
344
|
|
|
428
|
-
export function getStoreDirectory(): string {
|
|
429
|
-
const homeDir = homedir()
|
|
430
|
-
const storeDir = joinPath(homeDir, '.termcast', 'store')
|
|
431
|
-
|
|
432
|
-
// Ensure store directory exists
|
|
433
|
-
ensureDir(storeDir)
|
|
434
|
-
|
|
435
|
-
return storeDir
|
|
436
|
-
}
|
|
437
|
-
|
|
438
|
-
export function installExtension({
|
|
439
|
-
extensionName,
|
|
440
|
-
extensionSourcePath,
|
|
441
|
-
}: {
|
|
442
|
-
extensionName: string
|
|
443
|
-
extensionSourcePath: string
|
|
444
|
-
}): void {
|
|
445
|
-
const storeDir = getStoreDirectory()
|
|
446
|
-
const extensionDir = joinPath(storeDir, extensionName)
|
|
447
|
-
|
|
448
|
-
if (fileExists(extensionDir)) {
|
|
449
|
-
rmSync(extensionDir)
|
|
450
|
-
}
|
|
451
|
-
|
|
452
|
-
mkdirSync(extensionDir)
|
|
453
|
-
cpSync(extensionSourcePath, extensionDir)
|
|
454
|
-
|
|
455
|
-
logger.log(`Extension '${extensionName}' installed to ${extensionDir}`)
|
|
456
|
-
}
|
|
457
|
-
|
|
458
|
-
export function getStoredExtensions(): StoredExtension[] {
|
|
459
|
-
const storeDir = getStoreDirectory()
|
|
460
|
-
const extensions: StoredExtension[] = []
|
|
461
345
|
|
|
462
|
-
if (!fileExists(storeDir)) {
|
|
463
|
-
return extensions
|
|
464
|
-
}
|
|
465
|
-
|
|
466
|
-
const entries = readdirSync(storeDir)
|
|
467
|
-
|
|
468
|
-
for (const entry of entries) {
|
|
469
|
-
if (!entry.isDirectory()) continue
|
|
470
|
-
|
|
471
|
-
const extensionDir = joinPath(storeDir, entry.name)
|
|
472
|
-
const packageJsonPath = joinPath(extensionDir, 'package.json')
|
|
473
|
-
|
|
474
|
-
if (!fileExists(packageJsonPath)) {
|
|
475
|
-
logger.log(`Skipping ${entry.name}: no package.json found`)
|
|
476
|
-
continue
|
|
477
|
-
}
|
|
478
|
-
|
|
479
|
-
try {
|
|
480
|
-
const commandsData = getCommandsWithFiles({ packageJsonPath })
|
|
481
|
-
|
|
482
|
-
// Map commands to bundled commands using the resolver
|
|
483
|
-
const bundledCommands: BundledCommand[] = commandsData.commands.map(
|
|
484
|
-
(command) => {
|
|
485
|
-
const bundledPath = resolveCommandPath({
|
|
486
|
-
commandName: command.name,
|
|
487
|
-
dir: extensionDir,
|
|
488
|
-
})
|
|
489
|
-
|
|
490
|
-
return {
|
|
491
|
-
...command,
|
|
492
|
-
bundledPath,
|
|
493
|
-
}
|
|
494
|
-
},
|
|
495
|
-
)
|
|
496
|
-
|
|
497
|
-
extensions.push({
|
|
498
|
-
name: entry.name,
|
|
499
|
-
packageJsonPath,
|
|
500
|
-
commands: bundledCommands,
|
|
501
|
-
})
|
|
502
|
-
} catch (error: any) {
|
|
503
|
-
logger.error(`Failed to load extension ${entry.name}:`, error.message)
|
|
504
|
-
}
|
|
505
|
-
}
|
|
506
|
-
|
|
507
|
-
return extensions
|
|
508
|
-
}
|
|
509
346
|
|
|
510
347
|
export type ParseExecOutputHandler<T = any> = (args: { stdout: string }) => T
|
|
511
348
|
|
package/src/examples/store.tsx
DELETED
|
@@ -1,78 +0,0 @@
|
|
|
1
|
-
import { test, expect, afterEach, beforeEach } from 'vitest'
|
|
2
|
-
import { launchTerminal, Session } from 'tuistory/src'
|
|
3
|
-
|
|
4
|
-
let session: Session
|
|
5
|
-
|
|
6
|
-
beforeEach(async () => {
|
|
7
|
-
session = await launchTerminal({
|
|
8
|
-
command: 'bun',
|
|
9
|
-
args: ['src/examples/store.tsx'],
|
|
10
|
-
cols: 80,
|
|
11
|
-
rows: 30,
|
|
12
|
-
})
|
|
13
|
-
})
|
|
14
|
-
|
|
15
|
-
afterEach(() => {
|
|
16
|
-
session?.close()
|
|
17
|
-
})
|
|
18
|
-
|
|
19
|
-
test('Store extension - searching for spiceblow shows Database', async () => {
|
|
20
|
-
// Wait for store interface to load
|
|
21
|
-
const initialOutput = await session.text({
|
|
22
|
-
waitFor: (text) => {
|
|
23
|
-
// Wait until we see the store title
|
|
24
|
-
return text.includes('Store - Install Extensions')
|
|
25
|
-
},
|
|
26
|
-
timeout: 15000,
|
|
27
|
-
})
|
|
28
|
-
|
|
29
|
-
// Verify the store interface loads
|
|
30
|
-
expect(initialOutput).toContain('Store - Install Extensions')
|
|
31
|
-
|
|
32
|
-
// Type "spiceblow" in the search bar
|
|
33
|
-
await session.type('spiceblow')
|
|
34
|
-
|
|
35
|
-
// Get the output after search, waiting for Database to appear
|
|
36
|
-
// This will automatically wait for the API request to complete and results to show
|
|
37
|
-
const afterSearchOutput = await session.text({
|
|
38
|
-
waitFor: (text) => {
|
|
39
|
-
return text.includes('Search, update, insert')
|
|
40
|
-
},
|
|
41
|
-
timeout: 15000,
|
|
42
|
-
})
|
|
43
|
-
|
|
44
|
-
// Store the snapshot after searching for spiceblow
|
|
45
|
-
expect(afterSearchOutput).toMatchInlineSnapshot(`
|
|
46
|
-
"
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
Store - Install Extensions ───────────────────────────────────────────────
|
|
50
|
-
|
|
51
|
-
> spiceblow
|
|
52
|
-
|
|
53
|
-
›Spiceblow - Sql Database Management Search, update, insert and delete rows
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
↵ view details ↑↓ navigate ^k actions :vim powered by termcast.app
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
"
|
|
77
|
-
`)
|
|
78
|
-
}, 30000)
|