@eide/uniformgen 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/README.md +356 -0
- package/dist/auth/credentials.d.ts +58 -0
- package/dist/auth/credentials.d.ts.map +1 -0
- package/dist/auth/credentials.js +107 -0
- package/dist/cli.d.ts +3 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +563 -0
- package/dist/commands/init.d.ts +11 -0
- package/dist/commands/init.d.ts.map +1 -0
- package/dist/commands/init.js +113 -0
- package/dist/commands/login.d.ts +9 -0
- package/dist/commands/login.d.ts.map +1 -0
- package/dist/commands/login.js +158 -0
- package/dist/commands/logout.d.ts +5 -0
- package/dist/commands/logout.d.ts.map +1 -0
- package/dist/commands/logout.js +13 -0
- package/dist/commands/push.d.ts +13 -0
- package/dist/commands/push.d.ts.map +1 -0
- package/dist/commands/push.js +328 -0
- package/dist/commands/scaffold.d.ts +19 -0
- package/dist/commands/scaffold.d.ts.map +1 -0
- package/dist/commands/scaffold.js +366 -0
- package/dist/commands/seed.d.ts +20 -0
- package/dist/commands/seed.d.ts.map +1 -0
- package/dist/commands/seed.js +380 -0
- package/dist/commands/select-project.d.ts +10 -0
- package/dist/commands/select-project.d.ts.map +1 -0
- package/dist/commands/select-project.js +277 -0
- package/dist/commands/setup.d.ts +5 -0
- package/dist/commands/setup.d.ts.map +1 -0
- package/dist/commands/setup.js +51 -0
- package/dist/commands/sync.d.ts +13 -0
- package/dist/commands/sync.d.ts.map +1 -0
- package/dist/commands/sync.js +318 -0
- package/dist/commands/whoami.d.ts +5 -0
- package/dist/commands/whoami.d.ts.map +1 -0
- package/dist/commands/whoami.js +31 -0
- package/dist/config/load-config.d.ts +6 -0
- package/dist/config/load-config.d.ts.map +1 -0
- package/dist/config/load-config.js +103 -0
- package/dist/config/settings.d.ts +20 -0
- package/dist/config/settings.d.ts.map +1 -0
- package/dist/config/settings.js +64 -0
- package/dist/config/types.d.ts +152 -0
- package/dist/config/types.d.ts.map +1 -0
- package/dist/config/types.js +94 -0
- package/dist/fetcher/fetch-schemas.d.ts +140 -0
- package/dist/fetcher/fetch-schemas.d.ts.map +1 -0
- package/dist/fetcher/fetch-schemas.js +223 -0
- package/dist/fetcher/fetch-workflows.d.ts +53 -0
- package/dist/fetcher/fetch-workflows.d.ts.map +1 -0
- package/dist/fetcher/fetch-workflows.js +164 -0
- package/dist/generated/hooks/customer-detail.d.ts +74 -0
- package/dist/generated/hooks/customer-detail.d.ts.map +1 -0
- package/dist/generated/hooks/customer-detail.js +113 -0
- package/dist/generated/hooks/design-system.d.ts +74 -0
- package/dist/generated/hooks/design-system.d.ts.map +1 -0
- package/dist/generated/hooks/design-system.js +109 -0
- package/dist/generated/hooks/index.d.ts +16 -0
- package/dist/generated/hooks/index.d.ts.map +1 -0
- package/dist/generated/hooks/index.js +14 -0
- package/dist/generated/hooks/shopify-collection.d.ts +74 -0
- package/dist/generated/hooks/shopify-collection.d.ts.map +1 -0
- package/dist/generated/hooks/shopify-collection.js +113 -0
- package/dist/generated/hooks/shopify-market.d.ts +74 -0
- package/dist/generated/hooks/shopify-market.d.ts.map +1 -0
- package/dist/generated/hooks/shopify-market.js +109 -0
- package/dist/generated/hooks/shopify-product.d.ts +74 -0
- package/dist/generated/hooks/shopify-product.d.ts.map +1 -0
- package/dist/generated/hooks/shopify-product.js +113 -0
- package/dist/generated/hooks/shopify-variant.d.ts +74 -0
- package/dist/generated/hooks/shopify-variant.d.ts.map +1 -0
- package/dist/generated/hooks/shopify-variant.js +113 -0
- package/dist/generated/hooks/template.d.ts +74 -0
- package/dist/generated/hooks/template.d.ts.map +1 -0
- package/dist/generated/hooks/template.js +107 -0
- package/dist/generated/types/config.d.ts +88 -0
- package/dist/generated/types/config.d.ts.map +1 -0
- package/dist/generated/types/config.js +14 -0
- package/dist/generated/types/data-models/index.d.ts +7 -0
- package/dist/generated/types/data-models/index.d.ts.map +1 -0
- package/dist/generated/types/data-models/index.js +6 -0
- package/dist/generated/types/data-models/test.d.ts +29 -0
- package/dist/generated/types/data-models/test.d.ts.map +1 -0
- package/dist/generated/types/data-models/test.js +1 -0
- package/dist/generated/types/data-models/watch.d.ts +26 -0
- package/dist/generated/types/data-models/watch.d.ts.map +1 -0
- package/dist/generated/types/data-models/watch.js +1 -0
- package/dist/generated/types/field-types.d.ts +255 -0
- package/dist/generated/types/field-types.d.ts.map +1 -0
- package/dist/generated/types/field-types.js +35 -0
- package/dist/generated/types/hooks.d.ts +106 -0
- package/dist/generated/types/hooks.d.ts.map +1 -0
- package/dist/generated/types/hooks.js +9 -0
- package/dist/generated/types/index.d.ts +10 -0
- package/dist/generated/types/index.d.ts.map +1 -0
- package/dist/generated/types/index.js +9 -0
- package/dist/generated/types/models/button-variant.d.ts +16 -0
- package/dist/generated/types/models/button-variant.d.ts.map +1 -0
- package/dist/generated/types/models/button-variant.js +1 -0
- package/dist/generated/types/models/color-palette.d.ts +27 -0
- package/dist/generated/types/models/color-palette.d.ts.map +1 -0
- package/dist/generated/types/models/color-palette.js +1 -0
- package/dist/generated/types/models/color-with-scale.d.ts +15 -0
- package/dist/generated/types/models/color-with-scale.d.ts.map +1 -0
- package/dist/generated/types/models/color-with-scale.js +1 -0
- package/dist/generated/types/models/context.d.ts +53 -0
- package/dist/generated/types/models/context.d.ts.map +1 -0
- package/dist/generated/types/models/context.js +51 -0
- package/dist/generated/types/models/customer-detail.d.ts +32 -0
- package/dist/generated/types/models/customer-detail.d.ts.map +1 -0
- package/dist/generated/types/models/customer-detail.js +26 -0
- package/dist/generated/types/models/design-system-badges.d.ts +16 -0
- package/dist/generated/types/models/design-system-badges.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-badges.js +1 -0
- package/dist/generated/types/models/design-system-buttons.d.ts +17 -0
- package/dist/generated/types/models/design-system-buttons.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-buttons.js +1 -0
- package/dist/generated/types/models/design-system-cards.d.ts +16 -0
- package/dist/generated/types/models/design-system-cards.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-cards.js +1 -0
- package/dist/generated/types/models/design-system-colors.d.ts +12 -0
- package/dist/generated/types/models/design-system-colors.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-colors.js +1 -0
- package/dist/generated/types/models/design-system-dark-mode.d.ts +13 -0
- package/dist/generated/types/models/design-system-dark-mode.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-dark-mode.js +1 -0
- package/dist/generated/types/models/design-system-focus-ring.d.ts +14 -0
- package/dist/generated/types/models/design-system-focus-ring.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-focus-ring.js +1 -0
- package/dist/generated/types/models/design-system-grid.d.ts +18 -0
- package/dist/generated/types/models/design-system-grid.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-grid.js +1 -0
- package/dist/generated/types/models/design-system-inputs.d.ts +26 -0
- package/dist/generated/types/models/design-system-inputs.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-inputs.js +1 -0
- package/dist/generated/types/models/design-system-links.d.ts +16 -0
- package/dist/generated/types/models/design-system-links.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-links.js +1 -0
- package/dist/generated/types/models/design-system-shadows.d.ts +20 -0
- package/dist/generated/types/models/design-system-shadows.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-shadows.js +1 -0
- package/dist/generated/types/models/design-system-spacing.d.ts +13 -0
- package/dist/generated/types/models/design-system-spacing.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-spacing.js +1 -0
- package/dist/generated/types/models/design-system-transitions.d.ts +15 -0
- package/dist/generated/types/models/design-system-transitions.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-transitions.js +1 -0
- package/dist/generated/types/models/design-system-typography.d.ts +21 -0
- package/dist/generated/types/models/design-system-typography.d.ts.map +1 -0
- package/dist/generated/types/models/design-system-typography.js +1 -0
- package/dist/generated/types/models/design-system.d.ts +138 -0
- package/dist/generated/types/models/design-system.d.ts.map +1 -0
- package/dist/generated/types/models/design-system.js +64 -0
- package/dist/generated/types/models/experiment.d.ts +57 -0
- package/dist/generated/types/models/experiment.d.ts.map +1 -0
- package/dist/generated/types/models/experiment.js +55 -0
- package/dist/generated/types/models/font-file.d.ts +16 -0
- package/dist/generated/types/models/font-file.d.ts.map +1 -0
- package/dist/generated/types/models/font-file.js +1 -0
- package/dist/generated/types/models/index.d.ts +38 -0
- package/dist/generated/types/models/index.d.ts.map +1 -0
- package/dist/generated/types/models/index.js +12 -0
- package/dist/generated/types/models/integration.d.ts +32 -0
- package/dist/generated/types/models/integration.d.ts.map +1 -0
- package/dist/generated/types/models/integration.js +26 -0
- package/dist/generated/types/models/route-tree.d.ts +43 -0
- package/dist/generated/types/models/route-tree.d.ts.map +1 -0
- package/dist/generated/types/models/route-tree.js +39 -0
- package/dist/generated/types/models/segment.d.ts +57 -0
- package/dist/generated/types/models/segment.d.ts.map +1 -0
- package/dist/generated/types/models/segment.js +55 -0
- package/dist/generated/types/models/shopify-collection.d.ts +32 -0
- package/dist/generated/types/models/shopify-collection.d.ts.map +1 -0
- package/dist/generated/types/models/shopify-collection.js +26 -0
- package/dist/generated/types/models/shopify-market.d.ts +32 -0
- package/dist/generated/types/models/shopify-market.d.ts.map +1 -0
- package/dist/generated/types/models/shopify-market.js +26 -0
- package/dist/generated/types/models/shopify-product.d.ts +32 -0
- package/dist/generated/types/models/shopify-product.d.ts.map +1 -0
- package/dist/generated/types/models/shopify-product.js +26 -0
- package/dist/generated/types/models/shopify-variant.d.ts +32 -0
- package/dist/generated/types/models/shopify-variant.d.ts.map +1 -0
- package/dist/generated/types/models/shopify-variant.js +26 -0
- package/dist/generated/types/models/template.d.ts +53 -0
- package/dist/generated/types/models/template.d.ts.map +1 -0
- package/dist/generated/types/models/template.js +40 -0
- package/dist/generated/types/models/typography-variant.d.ts +15 -0
- package/dist/generated/types/models/typography-variant.d.ts.map +1 -0
- package/dist/generated/types/models/typography-variant.js +1 -0
- package/dist/generated/types/scalars.d.ts +56 -0
- package/dist/generated/types/scalars.d.ts.map +1 -0
- package/dist/generated/types/scalars.js +6 -0
- package/dist/generators/admin/index.d.ts +32 -0
- package/dist/generators/admin/index.d.ts.map +1 -0
- package/dist/generators/admin/index.js +219 -0
- package/dist/generators/admin/mutations.d.ts +23 -0
- package/dist/generators/admin/mutations.d.ts.map +1 -0
- package/dist/generators/admin/mutations.js +424 -0
- package/dist/generators/admin/queries.d.ts +20 -0
- package/dist/generators/admin/queries.d.ts.map +1 -0
- package/dist/generators/admin/queries.js +476 -0
- package/dist/generators/admin/types.d.ts +28 -0
- package/dist/generators/admin/types.d.ts.map +1 -0
- package/dist/generators/admin/types.js +254 -0
- package/dist/generators/cms/index.d.ts +29 -0
- package/dist/generators/cms/index.d.ts.map +1 -0
- package/dist/generators/cms/index.js +126 -0
- package/dist/generators/cms/route.d.ts +27 -0
- package/dist/generators/cms/route.d.ts.map +1 -0
- package/dist/generators/cms/route.js +409 -0
- package/dist/generators/cms/types.d.ts +15 -0
- package/dist/generators/cms/types.d.ts.map +1 -0
- package/dist/generators/cms/types.js +137 -0
- package/dist/generators/contexts/index.d.ts +25 -0
- package/dist/generators/contexts/index.d.ts.map +1 -0
- package/dist/generators/contexts/index.js +591 -0
- package/dist/generators/documents/data-models.d.ts +6 -0
- package/dist/generators/documents/data-models.d.ts.map +1 -0
- package/dist/generators/documents/data-models.js +61 -0
- package/dist/generators/documents/entity-models.d.ts +7 -0
- package/dist/generators/documents/entity-models.d.ts.map +1 -0
- package/dist/generators/documents/entity-models.js +87 -0
- package/dist/generators/documents/workflows.d.ts +11 -0
- package/dist/generators/documents/workflows.d.ts.map +1 -0
- package/dist/generators/documents/workflows.js +101 -0
- package/dist/generators/filters/index.d.ts +16 -0
- package/dist/generators/filters/index.d.ts.map +1 -0
- package/dist/generators/filters/index.js +384 -0
- package/dist/generators/hooks/agnostic.d.ts +16 -0
- package/dist/generators/hooks/agnostic.d.ts.map +1 -0
- package/dist/generators/hooks/agnostic.js +248 -0
- package/dist/generators/hooks/index.d.ts +9 -0
- package/dist/generators/hooks/index.d.ts.map +1 -0
- package/dist/generators/hooks/index.js +8 -0
- package/dist/generators/hooks/react.d.ts +16 -0
- package/dist/generators/hooks/react.d.ts.map +1 -0
- package/dist/generators/hooks/react.js +394 -0
- package/dist/generators/hooks/remix.d.ts +16 -0
- package/dist/generators/hooks/remix.d.ts.map +1 -0
- package/dist/generators/hooks/remix.js +349 -0
- package/dist/generators/hooks/workflows.d.ts +23 -0
- package/dist/generators/hooks/workflows.d.ts.map +1 -0
- package/dist/generators/hooks/workflows.js +312 -0
- package/dist/generators/resolve/index.d.ts +13 -0
- package/dist/generators/resolve/index.d.ts.map +1 -0
- package/dist/generators/resolve/index.js +13 -0
- package/dist/generators/resolve/platform.d.ts +29 -0
- package/dist/generators/resolve/platform.d.ts.map +1 -0
- package/dist/generators/resolve/platform.js +479 -0
- package/dist/generators/types/config.d.ts +7 -0
- package/dist/generators/types/config.d.ts.map +1 -0
- package/dist/generators/types/config.js +113 -0
- package/dist/generators/types/data-models.d.ts +10 -0
- package/dist/generators/types/data-models.d.ts.map +1 -0
- package/dist/generators/types/data-models.js +100 -0
- package/dist/generators/types/entity-models.d.ts +13 -0
- package/dist/generators/types/entity-models.d.ts.map +1 -0
- package/dist/generators/types/entity-models.js +241 -0
- package/dist/generators/types/field-types.d.ts +9 -0
- package/dist/generators/types/field-types.d.ts.map +1 -0
- package/dist/generators/types/field-types.js +651 -0
- package/dist/generators/types/hooks.d.ts +7 -0
- package/dist/generators/types/hooks.d.ts.map +1 -0
- package/dist/generators/types/hooks.js +132 -0
- package/dist/generators/types/scalars.d.ts +6 -0
- package/dist/generators/types/scalars.d.ts.map +1 -0
- package/dist/generators/types/scalars.js +68 -0
- package/dist/generators/types/user-details.d.ts +6 -0
- package/dist/generators/types/user-details.d.ts.map +1 -0
- package/dist/generators/types/user-details.js +60 -0
- package/dist/generators/types/workflows.d.ts +15 -0
- package/dist/generators/types/workflows.d.ts.map +1 -0
- package/dist/generators/types/workflows.js +163 -0
- package/dist/graphql/generated/gql.d.ts +47 -0
- package/dist/graphql/generated/gql.d.ts.map +1 -0
- package/dist/graphql/generated/gql.js +10 -0
- package/dist/graphql/generated/graphql.d.ts +8455 -0
- package/dist/graphql/generated/graphql.d.ts.map +1 -0
- package/dist/graphql/generated/graphql.js +573 -0
- package/dist/graphql/generated/index.d.ts +2 -0
- package/dist/graphql/generated/index.d.ts.map +1 -0
- package/dist/graphql/generated/index.js +1 -0
- package/dist/index.d.ts +13 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +9 -0
- package/dist/schema/define-entity-model.d.ts +122 -0
- package/dist/schema/define-entity-model.d.ts.map +1 -0
- package/dist/schema/define-entity-model.js +59 -0
- package/dist/schema/schema-loader.d.ts +10 -0
- package/dist/schema/schema-loader.d.ts.map +1 -0
- package/dist/schema/schema-loader.js +91 -0
- package/dist/utils/field-mapping.d.ts +83 -0
- package/dist/utils/field-mapping.d.ts.map +1 -0
- package/dist/utils/field-mapping.js +334 -0
- package/dist/writer/write-files.d.ts +12 -0
- package/dist/writer/write-files.d.ts.map +1 -0
- package/dist/writer/write-files.js +35 -0
- package/package.json +70 -0
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import inquirer from 'inquirer';
|
|
2
|
+
import chalk from 'chalk';
|
|
3
|
+
import { getSettings, updateSettings } from '../config/settings.js';
|
|
4
|
+
const FRAMEWORK_CHOICES = [
|
|
5
|
+
{
|
|
6
|
+
name: 'React (Apollo Client)',
|
|
7
|
+
value: 'react',
|
|
8
|
+
description: 'Generate useQuery/useMutation hooks with Apollo Client',
|
|
9
|
+
},
|
|
10
|
+
{
|
|
11
|
+
name: 'Remix (Hydrogen/Storefront)',
|
|
12
|
+
value: 'remix',
|
|
13
|
+
description: 'Generate loader/action helpers for Remix and Hydrogen',
|
|
14
|
+
},
|
|
15
|
+
{
|
|
16
|
+
name: 'Agnostic (typed helpers only)',
|
|
17
|
+
value: 'agnostic',
|
|
18
|
+
description: 'Generate framework-agnostic typed parser functions',
|
|
19
|
+
},
|
|
20
|
+
];
|
|
21
|
+
/**
|
|
22
|
+
* Setup command - configure UniformGen preferences
|
|
23
|
+
*/
|
|
24
|
+
export async function setup() {
|
|
25
|
+
const currentSettings = await getSettings();
|
|
26
|
+
console.log(chalk.bold('\nUniformGen Setup\n'));
|
|
27
|
+
console.log('Configure your code generation preferences.\n');
|
|
28
|
+
// Framework selection
|
|
29
|
+
const { framework } = await inquirer.prompt([
|
|
30
|
+
{
|
|
31
|
+
type: 'list',
|
|
32
|
+
name: 'framework',
|
|
33
|
+
message: 'Select your target framework:',
|
|
34
|
+
default: currentSettings.framework,
|
|
35
|
+
choices: FRAMEWORK_CHOICES.map((choice) => ({
|
|
36
|
+
name: `${choice.name}\n ${chalk.gray(choice.description)}`,
|
|
37
|
+
value: choice.value,
|
|
38
|
+
short: choice.name,
|
|
39
|
+
})),
|
|
40
|
+
},
|
|
41
|
+
]);
|
|
42
|
+
// Save settings
|
|
43
|
+
await updateSettings({ framework });
|
|
44
|
+
console.log('');
|
|
45
|
+
console.log(chalk.green('✓ Settings saved!'));
|
|
46
|
+
console.log('');
|
|
47
|
+
console.log(chalk.gray('Your preferences:'));
|
|
48
|
+
console.log(chalk.gray(` Framework: ${framework}`));
|
|
49
|
+
console.log('');
|
|
50
|
+
console.log(chalk.cyan('Run `uniformgen pull` to generate typed hooks for your models.'));
|
|
51
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
interface SyncOptions {
|
|
2
|
+
apiUrl: string;
|
|
3
|
+
schemasDir: string;
|
|
4
|
+
pattern?: string;
|
|
5
|
+
publish?: boolean;
|
|
6
|
+
config?: string;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Sync command - push local schemas then pull generated types
|
|
10
|
+
*/
|
|
11
|
+
export declare function sync(options: SyncOptions): Promise<void>;
|
|
12
|
+
export {};
|
|
13
|
+
//# sourceMappingURL=sync.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../src/commands/sync.ts"],"names":[],"mappings":"AAgEA,UAAU,WAAW;IACnB,MAAM,EAAE,MAAM,CAAC;IACf,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED;;GAEG;AACH,wBAAsB,IAAI,CAAC,OAAO,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,CAyX9D"}
|
|
@@ -0,0 +1,318 @@
|
|
|
1
|
+
import chalk from 'chalk';
|
|
2
|
+
import { push } from './push.js';
|
|
3
|
+
import { loadConfig } from '../config/load-config.js';
|
|
4
|
+
import { getSettings } from '../config/settings.js';
|
|
5
|
+
import { fetchEntityModels } from '../fetcher/fetch-schemas.js';
|
|
6
|
+
import { fetchWorkflows } from '../fetcher/fetch-workflows.js';
|
|
7
|
+
import { generateEntityModelTypes, generateEntityModelsIndex, } from '../generators/types/entity-models.js';
|
|
8
|
+
import { generateFieldTypesFile } from '../generators/types/field-types.js';
|
|
9
|
+
import { generateHooksFile } from '../generators/types/hooks.js';
|
|
10
|
+
import { generateConfigFile } from '../generators/types/config.js';
|
|
11
|
+
import { generateEntityModelDocuments } from '../generators/documents/entity-models.js';
|
|
12
|
+
import { generateAgnosticHooks, generateAgnosticHooksIndex, generateReactHooks, generateReactHooksIndex, generateRemixHooks, generateRemixHooksIndex, } from '../generators/hooks/index.js';
|
|
13
|
+
// Phase 13: Admin layer generators
|
|
14
|
+
import { generateAdminHooksReact, generateAdminHooksRemix, generateAdminHooksIndexReact, generateAdminHooksIndexRemix, } from '../generators/admin/index.js';
|
|
15
|
+
// Phase 13: Platform resolve generators
|
|
16
|
+
import { generatePlatformResolveReact, generatePlatformResolveRemix, generatePlatformResolveIndexReact, generatePlatformResolveIndexRemix, } from '../generators/resolve/index.js';
|
|
17
|
+
// Phase 13: CMS layer generators
|
|
18
|
+
import { getRoutableModels, generateCmsTypes, generateResolveRouteReact as generateCmsRouteReact, generateResolveRouteRemix as generateCmsRouteRemix, generateCmsIndexReact, generateCmsIndexRemix, } from '../generators/cms/index.js';
|
|
19
|
+
import { generateModelFilters, generateFiltersIndex, } from '../generators/filters/index.js';
|
|
20
|
+
// Workflow generators
|
|
21
|
+
import { generateWorkflowTypes, generateWorkflowTypesIndex, } from '../generators/types/workflows.js';
|
|
22
|
+
import { generateWorkflowReactHooks, generateWorkflowRemixHooks, generateWorkflowReactHooksIndex, generateWorkflowRemixHooksIndex, } from '../generators/hooks/workflows.js';
|
|
23
|
+
import { generateWorkflowDocuments } from '../generators/documents/workflows.js';
|
|
24
|
+
import { writeFiles } from '../writer/write-files.js';
|
|
25
|
+
import { join } from 'path';
|
|
26
|
+
/**
|
|
27
|
+
* Sync command - push local schemas then pull generated types
|
|
28
|
+
*/
|
|
29
|
+
export async function sync(options) {
|
|
30
|
+
console.log(chalk.bold('Phase 1: Push local schemas\n'));
|
|
31
|
+
console.log('─'.repeat(40));
|
|
32
|
+
// Push schemas
|
|
33
|
+
await push({
|
|
34
|
+
apiUrl: options.apiUrl,
|
|
35
|
+
schemasDir: options.schemasDir,
|
|
36
|
+
pattern: options.pattern,
|
|
37
|
+
dryRun: false,
|
|
38
|
+
publish: options.publish,
|
|
39
|
+
});
|
|
40
|
+
console.log('\n' + chalk.bold('Phase 2: Pull generated types\n'));
|
|
41
|
+
console.log('─'.repeat(40));
|
|
42
|
+
// Load config for pull
|
|
43
|
+
const config = await loadConfig(options.config, process.cwd());
|
|
44
|
+
if (options.apiUrl)
|
|
45
|
+
config.apiUrl = options.apiUrl;
|
|
46
|
+
// Fetch updated entity models
|
|
47
|
+
console.log('Fetching updated entity models...');
|
|
48
|
+
const entityModels = await fetchEntityModels(config.apiUrl, config.accessToken, config.tenantId, config.projectId, { includeInline: true });
|
|
49
|
+
const recordModels = entityModels.filter((m) => m.modes.records);
|
|
50
|
+
const inlineOnlyModels = entityModels.filter((m) => m.modes.inline && !m.modes.records);
|
|
51
|
+
console.log(`Fetched ${entityModels.length} entity models (${recordModels.length} with records, ${inlineOnlyModels.length} inline-only)\n`);
|
|
52
|
+
// Generate files
|
|
53
|
+
const files = [];
|
|
54
|
+
// Generate base type files
|
|
55
|
+
console.log('Generating type definitions...');
|
|
56
|
+
files.push({
|
|
57
|
+
path: join(config.output.types, 'field-types.ts'),
|
|
58
|
+
content: generateFieldTypesFile(),
|
|
59
|
+
});
|
|
60
|
+
files.push({
|
|
61
|
+
path: join(config.output.types, 'hooks.ts'),
|
|
62
|
+
content: generateHooksFile(),
|
|
63
|
+
});
|
|
64
|
+
files.push({
|
|
65
|
+
path: join(config.output.types, 'config.ts'),
|
|
66
|
+
content: generateConfigFile(),
|
|
67
|
+
});
|
|
68
|
+
// Generate entity model types
|
|
69
|
+
if (entityModels.length > 0) {
|
|
70
|
+
const modelsDir = join(config.output.types, 'models');
|
|
71
|
+
for (const model of entityModels) {
|
|
72
|
+
files.push({
|
|
73
|
+
path: join(modelsDir, `${model.key}.ts`),
|
|
74
|
+
content: generateEntityModelTypes(model, entityModels),
|
|
75
|
+
});
|
|
76
|
+
}
|
|
77
|
+
files.push({
|
|
78
|
+
path: join(modelsDir, 'index.ts'),
|
|
79
|
+
content: generateEntityModelsIndex(entityModels),
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
// Generate GraphQL documents for public API models
|
|
83
|
+
const publicApiModels = recordModels.filter((m) => m.modes.publicApi);
|
|
84
|
+
if (publicApiModels.length > 0) {
|
|
85
|
+
console.log(`Generating GraphQL documents for ${publicApiModels.length} public API models...`);
|
|
86
|
+
for (const model of publicApiModels) {
|
|
87
|
+
files.push({
|
|
88
|
+
path: join(config.output.documents, `${model.key}.graphql`),
|
|
89
|
+
content: generateEntityModelDocuments(model),
|
|
90
|
+
});
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
// Generate typed hooks based on framework setting
|
|
94
|
+
const settings = await getSettings();
|
|
95
|
+
const framework = config.framework || settings.framework || 'agnostic';
|
|
96
|
+
const hooksDir = config.output.hooks;
|
|
97
|
+
if (publicApiModels.length > 0) {
|
|
98
|
+
console.log(`Generating ${framework} hooks for ${publicApiModels.length} models...`);
|
|
99
|
+
let generateHook;
|
|
100
|
+
let generateIndex;
|
|
101
|
+
switch (framework) {
|
|
102
|
+
case 'react':
|
|
103
|
+
generateHook = generateReactHooks;
|
|
104
|
+
generateIndex = generateReactHooksIndex;
|
|
105
|
+
break;
|
|
106
|
+
case 'remix':
|
|
107
|
+
generateHook = generateRemixHooks;
|
|
108
|
+
generateIndex = generateRemixHooksIndex;
|
|
109
|
+
break;
|
|
110
|
+
default:
|
|
111
|
+
generateHook = generateAgnosticHooks;
|
|
112
|
+
generateIndex = generateAgnosticHooksIndex;
|
|
113
|
+
}
|
|
114
|
+
for (const model of publicApiModels) {
|
|
115
|
+
const hookContent = generateHook(model, entityModels);
|
|
116
|
+
if (hookContent) {
|
|
117
|
+
files.push({
|
|
118
|
+
path: join(hooksDir, `${model.key}.ts`),
|
|
119
|
+
content: hookContent,
|
|
120
|
+
});
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
files.push({
|
|
124
|
+
path: join(hooksDir, 'index.ts'),
|
|
125
|
+
content: generateIndex(publicApiModels),
|
|
126
|
+
});
|
|
127
|
+
}
|
|
128
|
+
// ========================================================================
|
|
129
|
+
// Phase 13: Generate layered API structure
|
|
130
|
+
// ========================================================================
|
|
131
|
+
// Phase 13: Generate admin hooks (CRUD, versioning)
|
|
132
|
+
if (publicApiModels.length > 0 && framework !== 'agnostic') {
|
|
133
|
+
console.log(`Generating ${framework} admin hooks for ${publicApiModels.length} models...`);
|
|
134
|
+
const adminDir = join(hooksDir, 'admin');
|
|
135
|
+
const generateAdmin = framework === 'react' ? generateAdminHooksReact : generateAdminHooksRemix;
|
|
136
|
+
const generateAdminIndex = framework === 'react' ? generateAdminHooksIndexReact : generateAdminHooksIndexRemix;
|
|
137
|
+
for (const model of publicApiModels) {
|
|
138
|
+
const adminContent = generateAdmin(model, entityModels);
|
|
139
|
+
if (adminContent) {
|
|
140
|
+
files.push({
|
|
141
|
+
path: join(adminDir, `${model.key}.ts`),
|
|
142
|
+
content: adminContent,
|
|
143
|
+
});
|
|
144
|
+
}
|
|
145
|
+
}
|
|
146
|
+
files.push({
|
|
147
|
+
path: join(adminDir, 'index.ts'),
|
|
148
|
+
content: generateAdminIndex(publicApiModels),
|
|
149
|
+
});
|
|
150
|
+
}
|
|
151
|
+
// Phase 13: Generate platform resolve hooks (clean, no CMS features)
|
|
152
|
+
if (publicApiModels.length > 0 && framework !== 'agnostic') {
|
|
153
|
+
console.log(`Generating ${framework} platform resolve hooks for ${publicApiModels.length} models...`);
|
|
154
|
+
const platformResolveDir = join(hooksDir, 'resolve');
|
|
155
|
+
const generatePlatformResolve = framework === 'react' ? generatePlatformResolveReact : generatePlatformResolveRemix;
|
|
156
|
+
const generatePlatformIndex = framework === 'react' ? generatePlatformResolveIndexReact : generatePlatformResolveIndexRemix;
|
|
157
|
+
for (const model of publicApiModels) {
|
|
158
|
+
const resolveContent = generatePlatformResolve(model, entityModels);
|
|
159
|
+
if (resolveContent) {
|
|
160
|
+
files.push({
|
|
161
|
+
path: join(platformResolveDir, `${model.key}.ts`),
|
|
162
|
+
content: resolveContent,
|
|
163
|
+
});
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
files.push({
|
|
167
|
+
path: join(platformResolveDir, 'index.ts'),
|
|
168
|
+
content: generatePlatformIndex(publicApiModels),
|
|
169
|
+
});
|
|
170
|
+
}
|
|
171
|
+
// Phase 13: Generate CMS hooks (only if cms.enabled models exist)
|
|
172
|
+
const routableModels = getRoutableModels(entityModels);
|
|
173
|
+
if (routableModels.length > 0 && framework !== 'agnostic') {
|
|
174
|
+
console.log(`Generating ${framework} CMS hooks for ${routableModels.length} routable models...`);
|
|
175
|
+
const cmsDir = join(hooksDir, 'cms');
|
|
176
|
+
const generateCmsRoute = framework === 'react' ? generateCmsRouteReact : generateCmsRouteRemix;
|
|
177
|
+
const generateCmsIndex = framework === 'react' ? generateCmsIndexReact : generateCmsIndexRemix;
|
|
178
|
+
// Generate CMS types
|
|
179
|
+
files.push({
|
|
180
|
+
path: join(cmsDir, 'types.ts'),
|
|
181
|
+
content: generateCmsTypes(),
|
|
182
|
+
});
|
|
183
|
+
// Generate resolveRoute hook/function
|
|
184
|
+
files.push({
|
|
185
|
+
path: join(cmsDir, 'route.ts'),
|
|
186
|
+
content: generateCmsRoute(routableModels),
|
|
187
|
+
});
|
|
188
|
+
// Generate CMS index
|
|
189
|
+
files.push({
|
|
190
|
+
path: join(cmsDir, 'index.ts'),
|
|
191
|
+
content: generateCmsIndex(entityModels),
|
|
192
|
+
});
|
|
193
|
+
}
|
|
194
|
+
// Generate typed filters
|
|
195
|
+
if (publicApiModels.length > 0) {
|
|
196
|
+
console.log(`Generating typed filters for ${publicApiModels.length} models...`);
|
|
197
|
+
const filtersDir = join(config.output.types, '..', 'filters');
|
|
198
|
+
for (const model of publicApiModels) {
|
|
199
|
+
const filterContent = generateModelFilters(model, entityModels);
|
|
200
|
+
if (filterContent) {
|
|
201
|
+
files.push({
|
|
202
|
+
path: join(filtersDir, `${model.key}.ts`),
|
|
203
|
+
content: filterContent,
|
|
204
|
+
});
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
files.push({
|
|
208
|
+
path: join(filtersDir, 'index.ts'),
|
|
209
|
+
content: generateFiltersIndex(publicApiModels),
|
|
210
|
+
});
|
|
211
|
+
}
|
|
212
|
+
// ========================================================================
|
|
213
|
+
// Workflow Codegen: Generate typed workflow code
|
|
214
|
+
// ========================================================================
|
|
215
|
+
// Fetch workflows with API touchpoint
|
|
216
|
+
console.log('Fetching API workflows...');
|
|
217
|
+
let workflows = [];
|
|
218
|
+
try {
|
|
219
|
+
workflows = await fetchWorkflows(config.apiUrl, config.accessToken, config.tenantId, config.projectId);
|
|
220
|
+
console.log(`Fetched ${workflows.length} workflows with API touchpoint\n`);
|
|
221
|
+
}
|
|
222
|
+
catch (error) {
|
|
223
|
+
// Workflows may not exist yet - continue without them
|
|
224
|
+
console.log(chalk.yellow('Could not fetch workflows (this is OK if no workflows exist)\n'));
|
|
225
|
+
}
|
|
226
|
+
if (workflows.length > 0) {
|
|
227
|
+
// Generate workflow types
|
|
228
|
+
console.log(`Generating workflow types for ${workflows.length} workflows...`);
|
|
229
|
+
const workflowTypesDir = join(config.output.types, 'workflows');
|
|
230
|
+
for (const workflow of workflows) {
|
|
231
|
+
files.push({
|
|
232
|
+
path: join(workflowTypesDir, `${workflow.key}.ts`),
|
|
233
|
+
content: generateWorkflowTypes(workflow),
|
|
234
|
+
});
|
|
235
|
+
}
|
|
236
|
+
files.push({
|
|
237
|
+
path: join(workflowTypesDir, 'index.ts'),
|
|
238
|
+
content: generateWorkflowTypesIndex(workflows),
|
|
239
|
+
});
|
|
240
|
+
// Generate workflow GraphQL documents
|
|
241
|
+
console.log('Generating workflow GraphQL documents...');
|
|
242
|
+
files.push({
|
|
243
|
+
path: join(config.output.documents, 'workflows.ts'),
|
|
244
|
+
content: generateWorkflowDocuments(),
|
|
245
|
+
});
|
|
246
|
+
// Generate workflow hooks based on framework
|
|
247
|
+
if (framework !== 'agnostic') {
|
|
248
|
+
console.log(`Generating ${framework} workflow hooks for ${workflows.length} workflows...`);
|
|
249
|
+
const workflowHooksDir = join(hooksDir, 'workflows');
|
|
250
|
+
const generateWorkflowHook = framework === 'react'
|
|
251
|
+
? generateWorkflowReactHooks
|
|
252
|
+
: generateWorkflowRemixHooks;
|
|
253
|
+
const generateWorkflowIndex = framework === 'react'
|
|
254
|
+
? generateWorkflowReactHooksIndex
|
|
255
|
+
: generateWorkflowRemixHooksIndex;
|
|
256
|
+
for (const workflow of workflows) {
|
|
257
|
+
files.push({
|
|
258
|
+
path: join(workflowHooksDir, `${workflow.key}.ts`),
|
|
259
|
+
content: generateWorkflowHook(workflow),
|
|
260
|
+
});
|
|
261
|
+
}
|
|
262
|
+
files.push({
|
|
263
|
+
path: join(workflowHooksDir, 'index.ts'),
|
|
264
|
+
content: generateWorkflowIndex(workflows),
|
|
265
|
+
});
|
|
266
|
+
}
|
|
267
|
+
}
|
|
268
|
+
// Generate main index
|
|
269
|
+
files.push({
|
|
270
|
+
path: join(config.output.types, 'index.ts'),
|
|
271
|
+
content: `/**
|
|
272
|
+
* Generated types for EIDE project
|
|
273
|
+
*
|
|
274
|
+
* @generated by UniformGen - DO NOT EDIT MANUALLY
|
|
275
|
+
*/
|
|
276
|
+
|
|
277
|
+
export * from './field-types.js';
|
|
278
|
+
export * from './hooks.js';
|
|
279
|
+
export * from './config.js';
|
|
280
|
+
${entityModels.length > 0 ? "export * from './models/index.js';" : ''}
|
|
281
|
+
${workflows.length > 0 ? "export * from './workflows/index.js';" : ''}
|
|
282
|
+
`,
|
|
283
|
+
});
|
|
284
|
+
// Write files
|
|
285
|
+
console.log(`Writing ${files.length} files...`);
|
|
286
|
+
await writeFiles(files, config.prettier);
|
|
287
|
+
console.log(chalk.green(`\n✓ Sync complete!`));
|
|
288
|
+
console.log(chalk.gray(` Types: ${config.output.types}`));
|
|
289
|
+
console.log(chalk.gray(` Documents: ${config.output.documents}`));
|
|
290
|
+
console.log(chalk.gray(` Hooks: ${config.output.hooks}`));
|
|
291
|
+
console.log('');
|
|
292
|
+
console.log(chalk.cyan('Generated:'));
|
|
293
|
+
console.log(chalk.gray(` • field-types.ts - Field type definitions and value types`));
|
|
294
|
+
console.log(chalk.gray(` • hooks.ts - Lifecycle hook type definitions`));
|
|
295
|
+
console.log(chalk.gray(` • config.ts - EntityModelConfig base type`));
|
|
296
|
+
console.log(chalk.gray(` • ${entityModels.length} model files (${recordModels.length} configs + ${inlineOnlyModels.length} inline types)`));
|
|
297
|
+
if (publicApiModels.length > 0) {
|
|
298
|
+
console.log(chalk.gray(` • ${publicApiModels.length} GraphQL document files`));
|
|
299
|
+
console.log(chalk.gray(` • ${publicApiModels.length} ${framework} hook files`));
|
|
300
|
+
console.log(chalk.gray(` • ${publicApiModels.length} typed filter files`));
|
|
301
|
+
}
|
|
302
|
+
// Phase 13 output
|
|
303
|
+
if (publicApiModels.length > 0 && framework !== 'agnostic') {
|
|
304
|
+
console.log(chalk.gray(` • hooks/admin/ - ${publicApiModels.length} admin CRUD hooks`));
|
|
305
|
+
console.log(chalk.gray(` • hooks/resolve/ - ${publicApiModels.length} platform resolve hooks`));
|
|
306
|
+
}
|
|
307
|
+
if (routableModels.length > 0 && framework !== 'agnostic') {
|
|
308
|
+
console.log(chalk.gray(` • hooks/cms/ - CMS route resolution (${routableModels.length} routable models)`));
|
|
309
|
+
}
|
|
310
|
+
// Workflow output
|
|
311
|
+
if (workflows.length > 0) {
|
|
312
|
+
console.log(chalk.gray(` • types/workflows/ - ${workflows.length} workflow type definitions`));
|
|
313
|
+
console.log(chalk.gray(` • documents/workflows.ts - Workflow GraphQL documents`));
|
|
314
|
+
if (framework !== 'agnostic') {
|
|
315
|
+
console.log(chalk.gray(` • hooks/workflows/ - ${workflows.length} ${framework} workflow hooks`));
|
|
316
|
+
}
|
|
317
|
+
}
|
|
318
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"whoami.d.ts","sourceRoot":"","sources":["../../src/commands/whoami.ts"],"names":[],"mappings":"AAEA;;GAEG;AACH,wBAAsB,MAAM,IAAI,OAAO,CAAC,IAAI,CAAC,CA6B5C"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
import { getCredentials, isTokenExpired } from '../auth/credentials.js';
|
|
2
|
+
/**
|
|
3
|
+
* Whoami command - show current authentication status
|
|
4
|
+
*/
|
|
5
|
+
export async function whoami() {
|
|
6
|
+
const credentials = await getCredentials();
|
|
7
|
+
if (!credentials) {
|
|
8
|
+
console.log('Not logged in.');
|
|
9
|
+
console.log('\nRun `uniformgen login` to authenticate.');
|
|
10
|
+
process.exit(1);
|
|
11
|
+
}
|
|
12
|
+
const expired = isTokenExpired(credentials);
|
|
13
|
+
console.log('Authentication Status');
|
|
14
|
+
console.log('─'.repeat(40));
|
|
15
|
+
console.log(`User: ${credentials.user.name} <${credentials.user.email}>`);
|
|
16
|
+
console.log(`User ID: ${credentials.user.id}`);
|
|
17
|
+
console.log(`Token: ${expired ? '⚠ Expired' : '✓ Valid'}`);
|
|
18
|
+
if (credentials.selectedProject) {
|
|
19
|
+
console.log('');
|
|
20
|
+
console.log('Selected Project');
|
|
21
|
+
console.log('─'.repeat(40));
|
|
22
|
+
console.log(`Name: ${credentials.selectedProject.name}`);
|
|
23
|
+
console.log(`ID: ${credentials.selectedProject.id}`);
|
|
24
|
+
console.log(`Tenant ID: ${credentials.selectedProject.tenantId}`);
|
|
25
|
+
}
|
|
26
|
+
else {
|
|
27
|
+
console.log('');
|
|
28
|
+
console.log('No project selected.');
|
|
29
|
+
console.log('Run `uniformgen select-project` to choose a project.');
|
|
30
|
+
}
|
|
31
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"load-config.d.ts","sourceRoot":"","sources":["../../src/config/load-config.ts"],"names":[],"mappings":"AAGA,OAAO,EAA+B,KAAK,gBAAgB,EAAE,MAAM,YAAY,CAAC;AAehF;;GAEG;AACH,wBAAsB,UAAU,CAC9B,UAAU,CAAC,EAAE,MAAM,EACnB,GAAG,GAAE,MAAsB,GAC1B,OAAO,CAAC,gBAAgB,CAAC,CAuG3B"}
|
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
import { pathToFileURL } from 'url';
|
|
2
|
+
import { existsSync } from 'fs';
|
|
3
|
+
import { resolve, join } from 'path';
|
|
4
|
+
import { ConfigSchema, defaultConfig } from './types.js';
|
|
5
|
+
import { getCredentials } from '../auth/credentials.js';
|
|
6
|
+
/**
|
|
7
|
+
* Possible config file names
|
|
8
|
+
*/
|
|
9
|
+
const CONFIG_FILES = [
|
|
10
|
+
'.uniformrc.ts',
|
|
11
|
+
'.uniformrc.js',
|
|
12
|
+
'.uniformrc.mjs',
|
|
13
|
+
'uniformgen.config.ts',
|
|
14
|
+
'uniformgen.config.js',
|
|
15
|
+
'uniformgen.config.mjs',
|
|
16
|
+
];
|
|
17
|
+
/**
|
|
18
|
+
* Load configuration from file or use defaults
|
|
19
|
+
*/
|
|
20
|
+
export async function loadConfig(configPath, cwd = process.cwd()) {
|
|
21
|
+
let configFile = null;
|
|
22
|
+
// If explicit config path provided, use it
|
|
23
|
+
if (configPath) {
|
|
24
|
+
const absolutePath = resolve(cwd, configPath);
|
|
25
|
+
if (!existsSync(absolutePath)) {
|
|
26
|
+
throw new Error(`Config file not found: ${absolutePath}`);
|
|
27
|
+
}
|
|
28
|
+
configFile = absolutePath;
|
|
29
|
+
}
|
|
30
|
+
else {
|
|
31
|
+
// Search for config file in current directory
|
|
32
|
+
for (const fileName of CONFIG_FILES) {
|
|
33
|
+
const filePath = join(cwd, fileName);
|
|
34
|
+
if (existsSync(filePath)) {
|
|
35
|
+
configFile = filePath;
|
|
36
|
+
break;
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
let userConfig = {};
|
|
41
|
+
// Load config file if found
|
|
42
|
+
if (configFile) {
|
|
43
|
+
try {
|
|
44
|
+
const configUrl = pathToFileURL(configFile).href;
|
|
45
|
+
const configModule = await import(configUrl);
|
|
46
|
+
userConfig = configModule.default || configModule;
|
|
47
|
+
}
|
|
48
|
+
catch (error) {
|
|
49
|
+
throw new Error(`Failed to load config file: ${configFile}\n${error instanceof Error ? error.message : String(error)}`);
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
// Get API URL from environment variable if not in config
|
|
53
|
+
const apiUrl = userConfig.apiUrl ||
|
|
54
|
+
process.env.UNIFORMGEN_API_URL ||
|
|
55
|
+
process.env.FOIR_API_URL ||
|
|
56
|
+
defaultConfig.apiUrl;
|
|
57
|
+
// Get credentials from CLI login
|
|
58
|
+
const credentials = await getCredentials();
|
|
59
|
+
// Try to get access token from multiple sources in order of preference:
|
|
60
|
+
// 1. Explicit access token in config/env
|
|
61
|
+
// 2. CLI credentials from login
|
|
62
|
+
const accessToken = userConfig.accessToken ||
|
|
63
|
+
process.env.UNIFORMGEN_ACCESS_TOKEN ||
|
|
64
|
+
process.env.FOIR_ACCESS_TOKEN ||
|
|
65
|
+
credentials?.accessToken;
|
|
66
|
+
// Require an access token
|
|
67
|
+
if (!accessToken) {
|
|
68
|
+
throw new Error('Authentication required. Run `uniformgen login` and `uniformgen select-project` to authenticate via CLI.');
|
|
69
|
+
}
|
|
70
|
+
// Require a selected project
|
|
71
|
+
if (!credentials?.selectedProject) {
|
|
72
|
+
throw new Error('No project selected. Run `uniformgen select-project` to choose a project.');
|
|
73
|
+
}
|
|
74
|
+
// Get tenant and project IDs from selected project
|
|
75
|
+
const tenantId = credentials.selectedProject.tenantId;
|
|
76
|
+
const projectId = credentials.selectedProject.id;
|
|
77
|
+
// Project key is optional (kept for backwards compatibility)
|
|
78
|
+
const projectKey = userConfig.projectKey ||
|
|
79
|
+
process.env.UNIFORMGEN_PROJECT_KEY ||
|
|
80
|
+
process.env.EIDE_PROJECT_KEY ||
|
|
81
|
+
credentials?.selectedProject?.apiKey;
|
|
82
|
+
// Merge with defaults
|
|
83
|
+
const mergedConfig = {
|
|
84
|
+
...defaultConfig,
|
|
85
|
+
...userConfig,
|
|
86
|
+
accessToken,
|
|
87
|
+
tenantId,
|
|
88
|
+
projectId,
|
|
89
|
+
projectKey,
|
|
90
|
+
apiUrl,
|
|
91
|
+
output: {
|
|
92
|
+
...defaultConfig.output,
|
|
93
|
+
...userConfig.output,
|
|
94
|
+
},
|
|
95
|
+
};
|
|
96
|
+
// Validate config
|
|
97
|
+
try {
|
|
98
|
+
return ConfigSchema.parse(mergedConfig);
|
|
99
|
+
}
|
|
100
|
+
catch (error) {
|
|
101
|
+
throw new Error(`Invalid configuration:\n${error instanceof Error ? error.message : String(error)}`);
|
|
102
|
+
}
|
|
103
|
+
}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Local settings structure (stored per-machine, not per-project)
|
|
3
|
+
*/
|
|
4
|
+
export interface LocalSettings {
|
|
5
|
+
/** Target framework for generated hooks */
|
|
6
|
+
framework: 'agnostic' | 'react' | 'remix';
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Read local settings
|
|
10
|
+
*/
|
|
11
|
+
export declare function getSettings(): Promise<LocalSettings>;
|
|
12
|
+
/**
|
|
13
|
+
* Write settings to file
|
|
14
|
+
*/
|
|
15
|
+
export declare function writeSettings(settings: LocalSettings): Promise<void>;
|
|
16
|
+
/**
|
|
17
|
+
* Update settings with new values
|
|
18
|
+
*/
|
|
19
|
+
export declare function updateSettings(updates: Partial<LocalSettings>): Promise<void>;
|
|
20
|
+
//# sourceMappingURL=settings.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"settings.d.ts","sourceRoot":"","sources":["../../src/config/settings.ts"],"names":[],"mappings":"AAIA;;GAEG;AACH,MAAM,WAAW,aAAa;IAC5B,2CAA2C;IAC3C,SAAS,EAAE,UAAU,GAAG,OAAO,GAAG,OAAO,CAAC;CAC3C;AAkCD;;GAEG;AACH,wBAAsB,WAAW,IAAI,OAAO,CAAC,aAAa,CAAC,CAU1D;AAED;;GAEG;AACH,wBAAsB,aAAa,CAAC,QAAQ,EAAE,aAAa,GAAG,OAAO,CAAC,IAAI,CAAC,CAM1E;AAED;;GAEG;AACH,wBAAsB,cAAc,CAClC,OAAO,EAAE,OAAO,CAAC,aAAa,CAAC,GAC9B,OAAO,CAAC,IAAI,CAAC,CAGf"}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import { promises as fs } from 'fs';
|
|
2
|
+
import { join } from 'path';
|
|
3
|
+
import { homedir } from 'os';
|
|
4
|
+
const DEFAULT_SETTINGS = {
|
|
5
|
+
framework: 'agnostic',
|
|
6
|
+
};
|
|
7
|
+
/**
|
|
8
|
+
* Get the settings directory path
|
|
9
|
+
*/
|
|
10
|
+
function getSettingsDir() {
|
|
11
|
+
return join(homedir(), '.uniformgen');
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* Get the settings file path
|
|
15
|
+
*/
|
|
16
|
+
function getSettingsPath() {
|
|
17
|
+
return join(getSettingsDir(), 'settings.json');
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Ensure the settings directory exists
|
|
21
|
+
*/
|
|
22
|
+
async function ensureSettingsDir() {
|
|
23
|
+
const dir = getSettingsDir();
|
|
24
|
+
try {
|
|
25
|
+
await fs.mkdir(dir, { recursive: true, mode: 0o700 });
|
|
26
|
+
}
|
|
27
|
+
catch (error) {
|
|
28
|
+
if (error.code !== 'EEXIST') {
|
|
29
|
+
throw error;
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* Read local settings
|
|
35
|
+
*/
|
|
36
|
+
export async function getSettings() {
|
|
37
|
+
try {
|
|
38
|
+
const content = await fs.readFile(getSettingsPath(), 'utf-8');
|
|
39
|
+
return { ...DEFAULT_SETTINGS, ...JSON.parse(content) };
|
|
40
|
+
}
|
|
41
|
+
catch (error) {
|
|
42
|
+
if (error.code === 'ENOENT') {
|
|
43
|
+
return DEFAULT_SETTINGS;
|
|
44
|
+
}
|
|
45
|
+
throw error;
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Write settings to file
|
|
50
|
+
*/
|
|
51
|
+
export async function writeSettings(settings) {
|
|
52
|
+
await ensureSettingsDir();
|
|
53
|
+
const path = getSettingsPath();
|
|
54
|
+
await fs.writeFile(path, JSON.stringify(settings, null, 2), {
|
|
55
|
+
mode: 0o600,
|
|
56
|
+
});
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Update settings with new values
|
|
60
|
+
*/
|
|
61
|
+
export async function updateSettings(updates) {
|
|
62
|
+
const existing = await getSettings();
|
|
63
|
+
await writeSettings({ ...existing, ...updates });
|
|
64
|
+
}
|