tshex-cli 1.0.16 → 1.0.17

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.
Files changed (36) hide show
  1. package/build/main.js +11 -38
  2. package/package.json +1 -1
  3. package/readme.md +2 -14
  4. package/source/main.ts +11 -44
  5. package/templates/ctx/example-ports.ts +5 -0
  6. package/templates/lib/shared/application/databases.ts +70 -49
  7. package/templates/lib/shared/application/loggers.ts +6 -30
  8. package/templates/lib/shared/application/validations.ts +10 -0
  9. package/templates/ctx/index.ts +0 -0
  10. package/templates/react-project/core/context/adapters/api/.gitkeep +0 -0
  11. package/templates/react-project/core/context/adapters/hooks/.gitkeep +0 -0
  12. package/templates/react-project/core/context/adapters/schemas/.gitkeep +0 -0
  13. package/templates/react-project/core/context/application/.gitkeep +0 -0
  14. package/templates/react-project/core/context/domain/.gitkeep +0 -0
  15. package/templates/react-project/core/context/languages/.gitkeep +0 -0
  16. package/templates/react-project/core/shared/adapters/i18n/.gitkeep +0 -0
  17. package/templates/react-project/dom-client/context/Example.tsx +0 -11
  18. package/templates/react-project/dom-client/context/assets/.gitkeep +0 -0
  19. package/templates/react-project/dom-client/context/styles/.gitkeep +0 -0
  20. package/templates/react-project/dom-server/context/Example.tsx +0 -11
  21. package/templates/react-project/dom-server/context/assets/.gitkeep +0 -0
  22. package/templates/react-project/dom-server/context/styles/.gitkeep +0 -0
  23. package/templates/react-project/index.d.ts +0 -1
  24. package/templates/react-project/native/context/Example.tsx +0 -11
  25. package/templates/react-project/native/context/assets/.gitkeep +0 -0
  26. package/templates/react-project/native/context/styles/.gitkeep +0 -0
  27. package/templates/react-project/tests/core/.gitkeep +0 -0
  28. package/templates/react-project/tests/dom-client/.gitkeep +0 -0
  29. package/templates/react-project/tests/dom-server/.gitkeep +0 -0
  30. package/templates/react-project/tests/native/.gitkeep +0 -0
  31. /package/templates/{react-context → ctx-react}/adapters/api/.gitkeep +0 -0
  32. /package/templates/{react-context → ctx-react}/adapters/hooks/.gitkeep +0 -0
  33. /package/templates/{react-context → ctx-react}/adapters/schemas/.gitkeep +0 -0
  34. /package/templates/{react-context → ctx-react}/application/.gitkeep +0 -0
  35. /package/templates/{react-context → ctx-react}/domain/.gitkeep +0 -0
  36. /package/templates/{react-context → ctx-react}/languages/.gitkeep +0 -0
package/build/main.js CHANGED
@@ -31,35 +31,9 @@ function executeCreateContext(templatesDir, contextDir) {
31
31
  console.error(err);
32
32
  }
33
33
  }
34
- function copyDirectoryContents(sourceDir, destinationDir) {
35
- const entries = fs.readdirSync(sourceDir, { withFileTypes: true });
36
- for (const entry of entries) {
37
- const sourcePath = path.join(sourceDir, entry.name);
38
- const destinationPath = path.join(destinationDir, entry.name);
39
- if (fs.existsSync(destinationPath) === false) {
40
- fs.cpSync(sourcePath, destinationPath, {
41
- recursive: true,
42
- filter: (src) => src.endsWith('.gitkeep') === false
43
- });
44
- }
45
- }
46
- }
47
- function executeCreateReactProject(templatesDir, projectDir) {
48
- try {
49
- fs.cpSync(path.join(templatesDir, 'react-project'), projectDir, {
50
- recursive: true,
51
- filter: (src) => src.endsWith('.gitkeep') === false
52
- });
53
- copyDirectoryContents(path.join(templatesDir, 'lib', 'shared'), path.join(projectDir, 'core', 'shared'));
54
- console.log('React project created successfully');
55
- }
56
- catch (err) {
57
- console.error(err);
58
- }
59
- }
60
34
  function executeCreateReactContext(templatesDir, contextDir) {
61
35
  try {
62
- fs.cpSync(path.join(templatesDir, 'react-context'), contextDir, {
36
+ fs.cpSync(path.join(templatesDir, 'ctx-react'), contextDir, {
63
37
  recursive: true,
64
38
  filter: (src) => src.endsWith('.gitkeep') === false
65
39
  });
@@ -83,17 +57,17 @@ function main(program) {
83
57
  targetDir = path.join(targetDir, options.lib);
84
58
  executeCreateLib(templatesDir, targetDir);
85
59
  }
60
+ if (options.react === true && options.ctx === undefined) {
61
+ program.error('Option --react requires --ctx <name>');
62
+ }
86
63
  if (options.ctx !== undefined) {
87
64
  targetDir = path.join(targetDir, options.ctx);
88
- executeCreateContext(templatesDir, targetDir);
89
- }
90
- if (options.reactProject !== undefined) {
91
- targetDir = path.join(targetDir, options.reactProject);
92
- executeCreateReactProject(templatesDir, targetDir);
93
- }
94
- if (options.reactContext !== undefined) {
95
- targetDir = path.join(targetDir, options.reactContext);
96
- executeCreateReactContext(templatesDir, targetDir);
65
+ if (options.react === true) {
66
+ executeCreateReactContext(templatesDir, targetDir);
67
+ }
68
+ else {
69
+ executeCreateContext(templatesDir, targetDir);
70
+ }
97
71
  }
98
72
  }
99
73
  const packageJson = readPackageJson();
@@ -102,8 +76,7 @@ program
102
76
  .version(packageJson.version)
103
77
  .option('--lib <name>', "creates a new library with it's shared directory")
104
78
  .option('--ctx <name>', 'creates a new context')
79
+ .option('-R, --react', 'creates a React context with --ctx')
105
80
  .option('--dir <path>', 'sets the directory to create the new item')
106
- .option('--react-project <name>', 'creates a new React project')
107
- .option('--react-context <name>', 'creates a new React context')
108
81
  .parse(process.argv);
109
82
  main(program);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "tshex-cli",
3
- "version": "1.0.16",
3
+ "version": "1.0.17",
4
4
  "author": "https://github.com/virtualitems/",
5
5
  "description": "Typescript Hexagonal Architecture CLI",
6
6
  "type": "module",
package/readme.md CHANGED
@@ -24,7 +24,6 @@ There are four things you can generate:
24
24
 
25
25
  - A **library** (`--lib`): the shared foundation of a project. It contains the domain and application contracts (entities, value objects, services, etc.) that the rest of the code depends on.
26
26
  - A **context** (`--ctx`): a specific business area (e.g. `users`, `billing`, `orders`). It contains the `domain/`, `application/`, and `adapters/` folders where you implement that area's logic.
27
- - A **React project** (`--react-project`): a full React-oriented hexagonal structure with `core/`, `dom-client/`, `dom-server/`, and `native/` folders.
28
27
  - A **React context** (`--react-context`): a React-ready context scaffold.
29
28
 
30
29
  A typical project has one library and one or more contexts inside it.
@@ -52,20 +51,19 @@ tshex --help
52
51
  ## Usage
53
52
 
54
53
  ```bash
55
- tshex [--lib <name>] [--ctx <name>] [--react-project <name>] [--react-context <name>] [--dir <path>]
54
+ tshex [--lib <name>] [--ctx <name>] [--react-context <name>] [--dir <path>]
56
55
  ```
57
56
 
58
57
  | Option | Purpose |
59
58
  | -------------- | ------------------------------------------------------------------- |
60
59
  | `--lib <name>` | Generate a library called `<name>`, based on `templates/lib`. |
61
60
  | `--ctx <name>` | Generate a context called `<name>`, based on `templates/ctx`. |
62
- | `--react-project <name>` | Generate a React project called `<name>`, based on `templates/react-project` and `templates/lib/shared`. |
63
61
  | `--react-context <name>` | Generate a React context called `<name>`, based on `templates/react-context`. |
64
62
  | `--dir <path>` | Parent directory where the library/context will be created. Defaults to the current directory. |
65
63
  | `--help` | Show the command options. |
66
64
  | `--version` | Show the installed version. |
67
65
 
68
- `--lib`, `--ctx`, `--react-project`, and `--react-context` can be used together in a single command. Running `tshex` without any options just prints the help text — it does not generate anything.
66
+ `--lib`, `--ctx`, and `--react-context` can be used together in a single command. Running `tshex` without any options just prints the help text — it does not generate anything.
69
67
 
70
68
  ## Create a library
71
69
 
@@ -208,16 +206,6 @@ src/
208
206
  └── index.ts
209
207
  ```
210
208
 
211
- ## Create a React project
212
-
213
- Use this when you want the React-specific project scaffold with the shared `core/shared` contracts copied from the library template:
214
-
215
- ```bash
216
- tshex --react-project app
217
- ```
218
-
219
- This generates a `app/` folder in the current directory.
220
-
221
209
  ## Create a React context
222
210
 
223
211
  Use this when you want only the React context scaffold:
package/source/main.ts CHANGED
@@ -41,40 +41,9 @@ function executeCreateContext(templatesDir: string, contextDir: string) {
41
41
  }
42
42
  }
43
43
 
44
- function copyDirectoryContents(sourceDir: string, destinationDir: string) {
45
- const entries = fs.readdirSync(sourceDir, { withFileTypes: true })
46
-
47
- for (const entry of entries) {
48
- const sourcePath = path.join(sourceDir, entry.name)
49
- const destinationPath = path.join(destinationDir, entry.name)
50
-
51
- if (fs.existsSync(destinationPath) === false) {
52
- fs.cpSync(sourcePath, destinationPath, {
53
- recursive: true,
54
- filter: (src) => src.endsWith('.gitkeep') === false
55
- })
56
- }
57
- }
58
- }
59
-
60
- function executeCreateReactProject(templatesDir: string, projectDir: string) {
61
- try {
62
- fs.cpSync(path.join(templatesDir, 'react-project'), projectDir, {
63
- recursive: true,
64
- filter: (src) => src.endsWith('.gitkeep') === false
65
- })
66
-
67
- copyDirectoryContents(path.join(templatesDir, 'lib', 'shared'), path.join(projectDir, 'core', 'shared'))
68
-
69
- console.log('React project created successfully')
70
- } catch (err) {
71
- console.error(err)
72
- }
73
- }
74
-
75
44
  function executeCreateReactContext(templatesDir: string, contextDir: string) {
76
45
  try {
77
- fs.cpSync(path.join(templatesDir, 'react-context'), contextDir, {
46
+ fs.cpSync(path.join(templatesDir, 'ctx-react'), contextDir, {
78
47
  recursive: true,
79
48
  filter: (src) => src.endsWith('.gitkeep') === false
80
49
  })
@@ -104,19 +73,18 @@ function main(program: typeof import('commander').program) {
104
73
  executeCreateLib(templatesDir, targetDir)
105
74
  }
106
75
 
107
- if (options.ctx !== undefined) {
108
- targetDir = path.join(targetDir, options.ctx)
109
- executeCreateContext(templatesDir, targetDir)
76
+ if (options.react === true && options.ctx === undefined) {
77
+ program.error('Option --react requires --ctx <name>')
110
78
  }
111
79
 
112
- if (options.reactProject !== undefined) {
113
- targetDir = path.join(targetDir, options.reactProject)
114
- executeCreateReactProject(templatesDir, targetDir)
115
- }
80
+ if (options.ctx !== undefined) {
81
+ targetDir = path.join(targetDir, options.ctx)
116
82
 
117
- if (options.reactContext !== undefined) {
118
- targetDir = path.join(targetDir, options.reactContext)
119
- executeCreateReactContext(templatesDir, targetDir)
83
+ if (options.react === true) {
84
+ executeCreateReactContext(templatesDir, targetDir)
85
+ } else {
86
+ executeCreateContext(templatesDir, targetDir)
87
+ }
120
88
  }
121
89
  }
122
90
 
@@ -127,9 +95,8 @@ program
127
95
  .version(packageJson.version)
128
96
  .option('--lib <name>', "creates a new library with it's shared directory")
129
97
  .option('--ctx <name>', 'creates a new context')
98
+ .option('-R, --react', 'creates a React context with --ctx')
130
99
  .option('--dir <path>', 'sets the directory to create the new item')
131
- .option('--react-project <name>', 'creates a new React project')
132
- .option('--react-context <name>', 'creates a new React context')
133
100
  .parse(process.argv)
134
101
 
135
102
  main(program)
@@ -0,0 +1,5 @@
1
+ // Ports are exports from the context root level
2
+
3
+ export function example(): void {
4
+ // ...
5
+ }
@@ -1,81 +1,102 @@
1
- // Libraries
1
+ type Generic<T = unknown> = Record<string, T>
2
2
 
3
- // Same Layer
3
+ /**
4
+ * @description
5
+ */
6
+ export interface Filterable<S = Generic> {
7
+ filter(selector: S): Promise<Array<S>>
8
+ }
4
9
 
5
- // Lower Layers
10
+ /**
11
+ * @description
12
+ */
13
+ export interface Sortable<S = Generic> {
14
+ sort(selector: S): Promise<Array<S>>
15
+ }
6
16
 
7
- // Types
17
+ /**
18
+ * @description
19
+ */
20
+ export interface Creatable<D = Generic> {
21
+ create(data: D): Promise<unknown>
22
+ }
8
23
 
9
- // Constants
24
+ /**
25
+ * @description
26
+ */
27
+ export interface Updatable<S = Generic, D = Generic> {
28
+ update(selector: S, data: D): Promise<unknown>
29
+ }
10
30
 
11
31
  /**
12
32
  * @description
13
33
  */
14
- export abstract class DataManager {
15
- [property: string]: unknown
34
+ export interface Deletable<S = Generic> {
35
+ delete(selector: S): Promise<unknown>
36
+ }
16
37
 
17
- // Public Attributes
38
+ /**
39
+ * @description
40
+ */
41
+ export interface Aggregatable<S = Generic> {
42
+ aggregate(selector: S): Promise<S>
43
+ }
18
44
 
19
- // Protected Attributes
45
+ /**
46
+ * @description
47
+ */
48
+ export interface Relatable {
49
+ selectRelated(...args: unknown[]): unknown
20
50
 
21
- // Private Attributes
51
+ prefetchRelated(...args: unknown[]): unknown
52
+ }
22
53
 
23
- // Public Static Attributes
54
+ /**
55
+ * @description
56
+ */
57
+ export abstract class DataManager<T = Generic> {
58
+ [property: string]: unknown
24
59
 
25
- // Protected Static Attributes
60
+ public abstract all(): Promise<Array<T>>
26
61
 
27
- // Private Static Attributes
62
+ public abstract none(): Array<T>
63
+ } //:: class
28
64
 
29
- // Constructor, Getters, Setters
65
+ /**
66
+ * @description
67
+ */
68
+ export abstract class DatasetManager<T = Generic> extends DataManager<T> {
69
+ [property: string]: unknown
30
70
 
31
- // Public Methods
71
+ public abstract union(other: Array<T>): Promise<Array<T>>
32
72
 
33
- public abstract connect(...args: unknown[]): Promise<unknown>
73
+ public abstract intersection(other: Array<T>): Promise<Array<T>>
34
74
 
35
- public abstract disconnect(): Promise<unknown>
75
+ public abstract difference(other: Array<T>): Promise<Array<T>>
36
76
 
37
- // Protected Methods
77
+ public abstract symmetric_difference(other: Array<T>): Promise<Array<T>>
38
78
 
39
- // Private Methods
79
+ public abstract complement(other: Array<T>): Promise<Array<T>>
80
+ } //:: class
40
81
 
41
- // Public Static Methods
82
+ /**
83
+ * @description
84
+ */
85
+ export abstract class DriverManager<M extends DataManager = DataManager> {
86
+ [property: string]: unknown
42
87
 
43
- // Protected Static Methods
88
+ public abstract connect(...args: unknown[]): Promise<M>
44
89
 
45
- // Private Static Methods
90
+ public abstract disconnect(): Promise<unknown>
46
91
  } //:: class
47
92
 
48
93
  /**
49
94
  * @description Represents a data source.
50
95
  */
51
- export abstract class Repository<Manager extends DataManager> {
96
+ export abstract class Repository<M extends DriverManager = DriverManager> {
52
97
  [property: string]: unknown
53
98
 
54
- // Public Attributes
55
-
56
- // Protected Attributes
57
-
58
- // Private Attributes
59
-
60
- // Public Static Attributes
61
-
62
- // Protected Static Attributes
63
-
64
- // Private Static Attributes
65
-
66
- // Constructor, Getters, Setters
67
-
68
- public constructor(public readonly manager: Manager) {}
69
-
70
- // Public Methods
71
-
72
- // Protected Methods
73
-
74
- // Private Methods
75
-
76
- // Public Static Methods
77
-
78
- // Protected Static Methods
99
+ public constructor(public readonly manager: M) {}
79
100
 
80
- // Private Static Methods
101
+ protected abstract transform<T = Generic>(data: Generic): T
81
102
  } //:: class
@@ -1,12 +1,12 @@
1
- // Libraries
1
+ export const DEBUG = 10
2
2
 
3
- // Same Layer
3
+ export const INFO = 20
4
4
 
5
- // Lower Layers
5
+ export const WARNING = 30
6
6
 
7
- // Types
7
+ export const ERROR = 40
8
8
 
9
- // Constants
9
+ export const CRITICAL = 50
10
10
 
11
11
  /**
12
12
  * @description
@@ -14,22 +14,6 @@
14
14
  export abstract class Logger {
15
15
  [property: string]: unknown
16
16
 
17
- // public ATTRIBUTES
18
-
19
- // protected ATTRIBUTES
20
-
21
- // private ATTRIBUTES
22
-
23
- // public static ATTRIBUTES
24
-
25
- // protected static ATTRIBUTES
26
-
27
- // private static ATTRIBUTES
28
-
29
- // Constructor, Getters, Setters
30
-
31
- // public METHODS
32
-
33
17
  public abstract debug(data: unknown): void
34
18
 
35
19
  public abstract info(data: unknown): void
@@ -38,13 +22,5 @@ export abstract class Logger {
38
22
 
39
23
  public abstract error(data: unknown): void
40
24
 
41
- // protected METHODS
42
-
43
- // private METHODS
44
-
45
- // public static METHODS
46
-
47
- // protected static METHODS
48
-
49
- // private static METHODS
25
+ public abstract critical(data: unknown): void
50
26
  } //:: class
@@ -0,0 +1,10 @@
1
+ /**
2
+ * @description
3
+ */
4
+ export interface Validatable {
5
+ [property: string]: unknown
6
+
7
+ isValid(): boolean
8
+
9
+ validate(): unknown
10
+ }
File without changes
@@ -1,11 +0,0 @@
1
- type Props = {
2
- children?: React.ReactNode
3
- }
4
-
5
- /**
6
- * @description Example component that renders its children.
7
- */
8
- export default function Example(props: Props) {
9
- const { children } = props
10
- return children
11
- }
@@ -1,11 +0,0 @@
1
- type Props = {
2
- children?: React.ReactNode
3
- }
4
-
5
- /**
6
- * @description Example component that renders its children.
7
- */
8
- export default function Example(props: Props) {
9
- const { children } = props
10
- return children
11
- }
@@ -1 +0,0 @@
1
- type Generic<T=unknown> = Record<string, T>;
@@ -1,11 +0,0 @@
1
- type Props = {
2
- children?: React.ReactNode
3
- }
4
-
5
- /**
6
- * @description Example component that renders its children.
7
- */
8
- export default function Example(props: Props) {
9
- const { children } = props
10
- return children
11
- }
File without changes
File without changes
File without changes
File without changes