@feathersjs/generators 5.0.0-pre.35

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 (169) hide show
  1. package/CHANGELOG.md +10 -0
  2. package/LICENSE +22 -0
  3. package/README.md +23 -0
  4. package/lib/app/index.d.ts +29 -0
  5. package/lib/app/index.js +146 -0
  6. package/lib/app/index.js.map +1 -0
  7. package/lib/app/index.ts +228 -0
  8. package/lib/app/static/.gitignore +121 -0
  9. package/lib/app/templates/app.test.tpl.d.ts +2 -0
  10. package/lib/app/templates/app.test.tpl.js +49 -0
  11. package/lib/app/templates/app.test.tpl.js.map +1 -0
  12. package/lib/app/templates/app.test.tpl.ts +50 -0
  13. package/lib/app/templates/app.tpl.d.ts +2 -0
  14. package/lib/app/templates/app.tpl.js +123 -0
  15. package/lib/app/templates/app.tpl.js.map +1 -0
  16. package/lib/app/templates/app.tpl.ts +138 -0
  17. package/lib/app/templates/channels.tpl.d.ts +2 -0
  18. package/lib/app/templates/channels.tpl.js +50 -0
  19. package/lib/app/templates/channels.tpl.js.map +1 -0
  20. package/lib/app/templates/channels.tpl.ts +56 -0
  21. package/lib/app/templates/client.test.tpl.d.ts +2 -0
  22. package/lib/app/templates/client.test.tpl.js +27 -0
  23. package/lib/app/templates/client.test.tpl.js.map +1 -0
  24. package/lib/app/templates/client.test.tpl.ts +26 -0
  25. package/lib/app/templates/client.tpl.d.ts +2 -0
  26. package/lib/app/templates/client.tpl.js +38 -0
  27. package/lib/app/templates/client.tpl.js.map +1 -0
  28. package/lib/app/templates/client.tpl.ts +45 -0
  29. package/lib/app/templates/configuration.tpl.d.ts +2 -0
  30. package/lib/app/templates/configuration.tpl.js +71 -0
  31. package/lib/app/templates/configuration.tpl.js.map +1 -0
  32. package/lib/app/templates/configuration.tpl.ts +82 -0
  33. package/lib/app/templates/declarations.tpl.d.ts +2 -0
  34. package/lib/app/templates/declarations.tpl.js +28 -0
  35. package/lib/app/templates/declarations.tpl.js.map +1 -0
  36. package/lib/app/templates/declarations.tpl.ts +37 -0
  37. package/lib/app/templates/index.html.tpl.d.ts +2 -0
  38. package/lib/app/templates/index.html.tpl.js +45 -0
  39. package/lib/app/templates/index.html.tpl.js.map +1 -0
  40. package/lib/app/templates/index.html.tpl.ts +44 -0
  41. package/lib/app/templates/index.tpl.d.ts +2 -0
  42. package/lib/app/templates/index.tpl.js +22 -0
  43. package/lib/app/templates/index.tpl.js.map +1 -0
  44. package/lib/app/templates/index.tpl.ts +26 -0
  45. package/lib/app/templates/logger.tpl.d.ts +3 -0
  46. package/lib/app/templates/logger.tpl.js +45 -0
  47. package/lib/app/templates/logger.tpl.js.map +1 -0
  48. package/lib/app/templates/logger.tpl.ts +56 -0
  49. package/lib/app/templates/package.json.tpl.d.ts +2 -0
  50. package/lib/app/templates/package.json.tpl.js +58 -0
  51. package/lib/app/templates/package.json.tpl.js.map +1 -0
  52. package/lib/app/templates/package.json.tpl.ts +71 -0
  53. package/lib/app/templates/prettierrc.tpl.d.ts +2 -0
  54. package/lib/app/templates/prettierrc.tpl.js +11 -0
  55. package/lib/app/templates/prettierrc.tpl.js.map +1 -0
  56. package/lib/app/templates/prettierrc.tpl.ts +14 -0
  57. package/lib/app/templates/readme.md.tpl.d.ts +2 -0
  58. package/lib/app/templates/readme.md.tpl.js +54 -0
  59. package/lib/app/templates/readme.md.tpl.js.map +1 -0
  60. package/lib/app/templates/readme.md.tpl.ts +57 -0
  61. package/lib/app/templates/services.tpl.d.ts +2 -0
  62. package/lib/app/templates/services.tpl.js +15 -0
  63. package/lib/app/templates/services.tpl.js.map +1 -0
  64. package/lib/app/templates/services.tpl.ts +20 -0
  65. package/lib/app/templates/tsconfig.json.tpl.d.ts +2 -0
  66. package/lib/app/templates/tsconfig.json.tpl.js +22 -0
  67. package/lib/app/templates/tsconfig.json.tpl.js.map +1 -0
  68. package/lib/app/templates/tsconfig.json.tpl.ts +28 -0
  69. package/lib/app/templates/validators.tpl.d.ts +2 -0
  70. package/lib/app/templates/validators.tpl.js +36 -0
  71. package/lib/app/templates/validators.tpl.js.map +1 -0
  72. package/lib/app/templates/validators.tpl.ts +40 -0
  73. package/lib/authentication/index.d.ts +73 -0
  74. package/lib/authentication/index.js +107 -0
  75. package/lib/authentication/index.js.map +1 -0
  76. package/lib/authentication/index.ts +126 -0
  77. package/lib/authentication/templates/authentication.tpl.d.ts +2 -0
  78. package/lib/authentication/templates/authentication.tpl.js +40 -0
  79. package/lib/authentication/templates/authentication.tpl.js.map +1 -0
  80. package/lib/authentication/templates/authentication.tpl.ts +51 -0
  81. package/lib/authentication/templates/client.test.tpl.d.ts +2 -0
  82. package/lib/authentication/templates/client.test.tpl.js +62 -0
  83. package/lib/authentication/templates/client.test.tpl.js.map +1 -0
  84. package/lib/authentication/templates/client.test.tpl.ts +74 -0
  85. package/lib/authentication/templates/config.tpl.d.ts +2 -0
  86. package/lib/authentication/templates/config.tpl.js +50 -0
  87. package/lib/authentication/templates/config.tpl.js.map +1 -0
  88. package/lib/authentication/templates/config.tpl.ts +57 -0
  89. package/lib/authentication/templates/declarations.tpl.d.ts +2 -0
  90. package/lib/authentication/templates/declarations.tpl.js +19 -0
  91. package/lib/authentication/templates/declarations.tpl.js.map +1 -0
  92. package/lib/authentication/templates/declarations.tpl.ts +34 -0
  93. package/lib/authentication/templates/knex.tpl.d.ts +2 -0
  94. package/lib/authentication/templates/knex.tpl.js +45 -0
  95. package/lib/authentication/templates/knex.tpl.js.map +1 -0
  96. package/lib/authentication/templates/knex.tpl.ts +62 -0
  97. package/lib/authentication/templates/schema.json.tpl.d.ts +2 -0
  98. package/lib/authentication/templates/schema.json.tpl.js +103 -0
  99. package/lib/authentication/templates/schema.json.tpl.js.map +1 -0
  100. package/lib/authentication/templates/schema.json.tpl.ts +124 -0
  101. package/lib/authentication/templates/schema.typebox.tpl.d.ts +3 -0
  102. package/lib/authentication/templates/schema.typebox.tpl.js +86 -0
  103. package/lib/authentication/templates/schema.typebox.tpl.js.map +1 -0
  104. package/lib/authentication/templates/schema.typebox.tpl.ts +108 -0
  105. package/lib/commons.d.ts +150 -0
  106. package/lib/commons.js +198 -0
  107. package/lib/commons.js.map +1 -0
  108. package/lib/commons.ts +284 -0
  109. package/lib/connection/index.d.ts +55 -0
  110. package/lib/connection/index.js +88 -0
  111. package/lib/connection/index.js.map +1 -0
  112. package/lib/connection/index.ts +123 -0
  113. package/lib/connection/templates/knex.tpl.d.ts +2 -0
  114. package/lib/connection/templates/knex.tpl.js +48 -0
  115. package/lib/connection/templates/knex.tpl.js.map +1 -0
  116. package/lib/connection/templates/knex.tpl.ts +67 -0
  117. package/lib/connection/templates/mongodb.tpl.d.ts +2 -0
  118. package/lib/connection/templates/mongodb.tpl.js +34 -0
  119. package/lib/connection/templates/mongodb.tpl.js.map +1 -0
  120. package/lib/connection/templates/mongodb.tpl.ts +40 -0
  121. package/lib/hook/index.d.ts +22 -0
  122. package/lib/hook/index.js +43 -0
  123. package/lib/hook/index.js.map +1 -0
  124. package/lib/hook/index.ts +47 -0
  125. package/lib/hook/templates/hook.tpl.d.ts +2 -0
  126. package/lib/hook/templates/hook.tpl.js +22 -0
  127. package/lib/hook/templates/hook.tpl.js.map +1 -0
  128. package/lib/hook/templates/hook.tpl.ts +33 -0
  129. package/lib/index.d.ts +7 -0
  130. package/lib/index.js +37 -0
  131. package/lib/index.js.map +1 -0
  132. package/lib/index.ts +8 -0
  133. package/lib/service/index.d.ts +64 -0
  134. package/lib/service/index.js +116 -0
  135. package/lib/service/index.js.map +1 -0
  136. package/lib/service/index.ts +191 -0
  137. package/lib/service/templates/client.tpl.d.ts +2 -0
  138. package/lib/service/templates/client.tpl.js +30 -0
  139. package/lib/service/templates/client.tpl.js.map +1 -0
  140. package/lib/service/templates/client.tpl.ts +56 -0
  141. package/lib/service/templates/schema.json.tpl.d.ts +2 -0
  142. package/lib/service/templates/schema.json.tpl.js +83 -0
  143. package/lib/service/templates/schema.json.tpl.js.map +1 -0
  144. package/lib/service/templates/schema.json.tpl.ts +98 -0
  145. package/lib/service/templates/schema.typebox.tpl.d.ts +2 -0
  146. package/lib/service/templates/schema.typebox.tpl.js +61 -0
  147. package/lib/service/templates/schema.typebox.tpl.js.map +1 -0
  148. package/lib/service/templates/schema.typebox.tpl.ts +76 -0
  149. package/lib/service/templates/service.tpl.d.ts +3 -0
  150. package/lib/service/templates/service.tpl.js +112 -0
  151. package/lib/service/templates/service.tpl.js.map +1 -0
  152. package/lib/service/templates/service.tpl.ts +152 -0
  153. package/lib/service/templates/test.tpl.d.ts +2 -0
  154. package/lib/service/templates/test.tpl.js +25 -0
  155. package/lib/service/templates/test.tpl.js.map +1 -0
  156. package/lib/service/templates/test.tpl.ts +33 -0
  157. package/lib/service/type/custom.tpl.d.ts +3 -0
  158. package/lib/service/type/custom.tpl.js +98 -0
  159. package/lib/service/type/custom.tpl.js.map +1 -0
  160. package/lib/service/type/custom.tpl.ts +109 -0
  161. package/lib/service/type/knex.tpl.d.ts +3 -0
  162. package/lib/service/type/knex.tpl.js +71 -0
  163. package/lib/service/type/knex.tpl.js.map +1 -0
  164. package/lib/service/type/knex.tpl.ts +92 -0
  165. package/lib/service/type/mongodb.tpl.d.ts +3 -0
  166. package/lib/service/type/mongodb.tpl.js +50 -0
  167. package/lib/service/type/mongodb.tpl.js.map +1 -0
  168. package/lib/service/type/mongodb.tpl.ts +62 -0
  169. package/package.json +89 -0
@@ -0,0 +1,124 @@
1
+ import { generator, toFile, when } from '@feathershq/pinion'
2
+ import { fileExists, renderSource } from '../../commons'
3
+ import { AuthenticationGeneratorContext, localTemplate } from '../index'
4
+
5
+ const template = ({
6
+ cwd,
7
+ lib,
8
+ camelName,
9
+ upperName,
10
+ authStrategies,
11
+ type,
12
+ relative
13
+ }: AuthenticationGeneratorContext) => /* ts */ `// For more information about this file see https://dove.feathersjs.com/guides/cli/service.schemas.html
14
+ import { resolve, querySyntax, getValidator } from '@feathersjs/schema'
15
+ import type { FromSchema } from '@feathersjs/schema'
16
+ ${localTemplate(authStrategies, `import { passwordHash } from '@feathersjs/authentication-local'`)}
17
+
18
+ import type { HookContext } from '${relative}/declarations'
19
+ import { dataValidator, queryValidator } from '${relative}/${
20
+ fileExists(cwd, lib, 'schemas') ? 'schemas/' : '' // This is for legacy backwards compatibility
21
+ }validators'
22
+
23
+ // Main data model schema
24
+ export const ${camelName}Schema = {
25
+ $id: '${upperName}',
26
+ type: 'object',
27
+ additionalProperties: false,
28
+ required: [ '${type === 'mongodb' ? '_id' : 'id'}'${localTemplate(authStrategies, ", 'email'")} ],
29
+ properties: {
30
+ ${type === 'mongodb' ? '_id' : 'id'}: {
31
+ type: '${type === 'mongodb' ? 'string' : 'number'}'
32
+ },
33
+ ${authStrategies
34
+ .map((name) =>
35
+ name === 'local'
36
+ ? ` email: { type: 'string' },
37
+ password: { type: 'string' }`
38
+ : ` ${name}Id: { type: 'string' }`
39
+ )
40
+ .join(',\n')}
41
+ }
42
+ } as const
43
+ export type ${upperName} = FromSchema<typeof ${camelName}Schema>
44
+ export const ${camelName}Resolver = resolve<${upperName}, HookContext>({})
45
+
46
+ export const ${camelName}ExternalResolver = resolve<${upperName}, HookContext>({
47
+ ${localTemplate(
48
+ authStrategies,
49
+ `// The password should never be visible externally
50
+ password: async () => undefined`
51
+ )}
52
+ })
53
+
54
+ // Schema for creating new users
55
+ export const ${camelName}DataSchema = {
56
+ $id: '${upperName}Data',
57
+ type: 'object',
58
+ additionalProperties: false,
59
+ required: [ ],
60
+ properties: {
61
+ ...${camelName}Schema.properties
62
+ }
63
+ } as const
64
+ export type ${upperName}Data = FromSchema<typeof ${camelName}DataSchema>
65
+ export const ${camelName}DataValidator = getValidator(${camelName}DataSchema, dataValidator)
66
+ export const ${camelName}DataResolver = resolve<${upperName}Data, HookContext>({
67
+ ${localTemplate(authStrategies, `password: passwordHash({ strategy: 'local' })`)}
68
+ })
69
+
70
+ // Schema for updating existing users
71
+ export const ${camelName}DataSchema = {
72
+ $id: '${upperName}Patch',
73
+ type: 'object',
74
+ additionalProperties: false,
75
+ required: [],
76
+ properties: {
77
+ ...${camelName}Schema.properties
78
+ }
79
+ } as const
80
+ export type ${upperName}Patch = FromSchema<typeof ${camelName}PatchSchema>
81
+ export const ${camelName}PatchValidator = getValidator(${camelName}PatchSchema, dataValidator)
82
+ export const ${camelName}PatchResolver = resolve<${upperName}Patch, HookContext>({
83
+ ${localTemplate(authStrategies, `password: passwordHash({ strategy: 'local' })`)}
84
+ })
85
+
86
+ // Schema for allowed query properties
87
+ export const ${camelName}QuerySchema = {
88
+ $id: '${upperName}Query',
89
+ type: 'object',
90
+ additionalProperties: false,
91
+ properties: {
92
+ ...querySyntax(${camelName}Schema.properties)
93
+ }
94
+ } as const
95
+ export type ${upperName}Query = FromSchema<typeof ${camelName}QuerySchema>
96
+ export const ${camelName}QueryValidator = getValidator(${camelName}QuerySchema, queryValidator)
97
+ export const ${camelName}QueryResolver = resolve<${upperName}Query, HookContext>({
98
+ // If there is a user (e.g. with authentication), they are only allowed to see their own data
99
+ ${type === 'mongodb' ? '_id' : 'id'}: async (value, user, context) => {
100
+ if (context.params.user) {
101
+ return context.params.user.${type === 'mongodb' ? '_id' : 'id'}
102
+ }
103
+
104
+ return value
105
+ }
106
+ })
107
+ `
108
+
109
+ export const generate = (ctx: AuthenticationGeneratorContext) =>
110
+ generator(ctx).then(
111
+ when<AuthenticationGeneratorContext>(
112
+ ({ schema }) => schema === 'json',
113
+ renderSource(
114
+ template,
115
+ toFile(({ lib, folder, fileName }: AuthenticationGeneratorContext) => [
116
+ lib,
117
+ 'services',
118
+ ...folder,
119
+ `${fileName}.schema`
120
+ ]),
121
+ { force: true }
122
+ )
123
+ )
124
+ )
@@ -0,0 +1,3 @@
1
+ import { AuthenticationGeneratorContext } from '../index';
2
+ export declare const template: ({ cwd, lib, camelName, upperName, authStrategies, type, relative }: AuthenticationGeneratorContext) => string;
3
+ export declare const generate: (ctx: AuthenticationGeneratorContext) => Promise<AuthenticationGeneratorContext>;
@@ -0,0 +1,86 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.generate = exports.template = void 0;
4
+ const pinion_1 = require("@feathershq/pinion");
5
+ const commons_1 = require("../../commons");
6
+ const index_1 = require("../index");
7
+ const template = ({ cwd, lib, camelName, upperName, authStrategies, type, relative }) => /* ts */ `// For more information about this file see https://dove.feathersjs.com/guides/cli/service.schemas.html
8
+ import { resolve } from '@feathersjs/schema'
9
+ import { Type, getDataValidator, getValidator, querySyntax } from '@feathersjs/typebox'
10
+ import type { Static } from '@feathersjs/typebox'
11
+ ${(0, index_1.localTemplate)(authStrategies, `import { passwordHash } from '@feathersjs/authentication-local'`)}
12
+
13
+ import type { HookContext } from '${relative}/declarations'
14
+ import { dataValidator, queryValidator } from '${relative}/${(0, commons_1.fileExists)(cwd, lib, 'schemas') ? 'schemas/' : '' // This is for legacy backwards compatibility
15
+ }validators'
16
+
17
+ // Main data model schema
18
+ export const ${camelName}Schema = Type.Object({
19
+ ${type === 'mongodb' ? '_id: Type.String()' : 'id: Type.Number()'},
20
+ ${authStrategies
21
+ .map((name) => name === 'local'
22
+ ? ` email: Type.String(),
23
+ password: Type.Optional(Type.String())`
24
+ : ` ${name}Id: Type.Optional(Type.String())`)
25
+ .join(',\n')}
26
+ },{ $id: '${upperName}', additionalProperties: false })
27
+ export type ${upperName} = Static<typeof ${camelName}Schema>
28
+ export const ${camelName}Resolver = resolve<${upperName}, HookContext>({})
29
+
30
+ export const ${camelName}ExternalResolver = resolve<${upperName}, HookContext>({
31
+ ${(0, index_1.localTemplate)(authStrategies, `// The password should never be visible externally
32
+ password: async () => undefined`)}
33
+ })
34
+
35
+ // Schema for creating new users
36
+ export const ${camelName}DataSchema = Type.Pick(${camelName}Schema, [
37
+ ${authStrategies.map((name) => (name === 'local' ? `'email', 'password'` : `'${name}Id'`)).join(', ')}
38
+ ],
39
+ { $id: '${upperName}Data', additionalProperties: false }
40
+ )
41
+ export type ${upperName}Data = Static<typeof ${camelName}DataSchema>
42
+ export const ${camelName}DataValidator = getDataValidator(${camelName}DataSchema, dataValidator)
43
+ export const ${camelName}DataResolver = resolve<${upperName}, HookContext>({
44
+ ${(0, index_1.localTemplate)(authStrategies, `password: passwordHash({ strategy: 'local' })`)}
45
+ })
46
+
47
+ // Schema for updating existing users
48
+ export const ${camelName}PatchSchema = Type.Partial(${camelName}Schema, {
49
+ $id: '${upperName}Patch'
50
+ })
51
+ export type ${upperName}Patch = Static<typeof ${camelName}PatchSchema>
52
+ export const ${camelName}PatchValidator = getDataValidator(${camelName}PatchSchema, dataValidator)
53
+ export const ${camelName}PatchResolver = resolve<${upperName}, HookContext>({
54
+ ${(0, index_1.localTemplate)(authStrategies, `password: passwordHash({ strategy: 'local' })`)}
55
+ })
56
+
57
+ // Schema for allowed query properties
58
+ export const ${camelName}QueryProperties = Type.Pick(${camelName}Schema, ['${type === 'mongodb' ? '_id' : 'id'}', ${authStrategies.map((name) => (name === 'local' ? `'email'` : `'${name}Id'`)).join(', ')}
59
+ ])
60
+ export const ${camelName}QuerySchema = Type.Intersect([
61
+ querySyntax(${camelName}QueryProperties),
62
+ // Add additional query properties here
63
+ Type.Object({}, { additionalProperties: false })
64
+ ], { additionalProperties: false })
65
+ export type ${upperName}Query = Static<typeof ${camelName}QuerySchema>
66
+ export const ${camelName}QueryValidator = getValidator(${camelName}QuerySchema, queryValidator)
67
+ export const ${camelName}QueryResolver = resolve<${upperName}Query, HookContext>({
68
+ // If there is a user (e.g. with authentication), they are only allowed to see their own data
69
+ ${type === 'mongodb' ? '_id' : 'id'}: async (value, user, context) => {
70
+ if (context.params.user) {
71
+ return context.params.user.${type === 'mongodb' ? '_id' : 'id'}
72
+ }
73
+
74
+ return value
75
+ }
76
+ })
77
+ `;
78
+ exports.template = template;
79
+ const generate = (ctx) => (0, pinion_1.generator)(ctx).then((0, pinion_1.when)(({ schema }) => schema === 'typebox', (0, commons_1.renderSource)(exports.template, (0, pinion_1.toFile)(({ lib, folder, fileName }) => [
80
+ lib,
81
+ 'services',
82
+ ...folder,
83
+ `${fileName}.schema`
84
+ ]), { force: true })));
85
+ exports.generate = generate;
86
+ //# sourceMappingURL=schema.typebox.tpl.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"schema.typebox.tpl.js","sourceRoot":"","sources":["../../../src/authentication/templates/schema.typebox.tpl.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,108 @@
1
+ import { generator, toFile, when } from '@feathershq/pinion'
2
+ import { fileExists, renderSource } from '../../commons'
3
+ import { AuthenticationGeneratorContext, localTemplate } from '../index'
4
+
5
+ export const template = ({
6
+ cwd,
7
+ lib,
8
+ camelName,
9
+ upperName,
10
+ authStrategies,
11
+ type,
12
+ relative
13
+ }: AuthenticationGeneratorContext) => /* ts */ `// For more information about this file see https://dove.feathersjs.com/guides/cli/service.schemas.html
14
+ import { resolve } from '@feathersjs/schema'
15
+ import { Type, getDataValidator, getValidator, querySyntax } from '@feathersjs/typebox'
16
+ import type { Static } from '@feathersjs/typebox'
17
+ ${localTemplate(authStrategies, `import { passwordHash } from '@feathersjs/authentication-local'`)}
18
+
19
+ import type { HookContext } from '${relative}/declarations'
20
+ import { dataValidator, queryValidator } from '${relative}/${
21
+ fileExists(cwd, lib, 'schemas') ? 'schemas/' : '' // This is for legacy backwards compatibility
22
+ }validators'
23
+
24
+ // Main data model schema
25
+ export const ${camelName}Schema = Type.Object({
26
+ ${type === 'mongodb' ? '_id: Type.String()' : 'id: Type.Number()'},
27
+ ${authStrategies
28
+ .map((name) =>
29
+ name === 'local'
30
+ ? ` email: Type.String(),
31
+ password: Type.Optional(Type.String())`
32
+ : ` ${name}Id: Type.Optional(Type.String())`
33
+ )
34
+ .join(',\n')}
35
+ },{ $id: '${upperName}', additionalProperties: false })
36
+ export type ${upperName} = Static<typeof ${camelName}Schema>
37
+ export const ${camelName}Resolver = resolve<${upperName}, HookContext>({})
38
+
39
+ export const ${camelName}ExternalResolver = resolve<${upperName}, HookContext>({
40
+ ${localTemplate(
41
+ authStrategies,
42
+ `// The password should never be visible externally
43
+ password: async () => undefined`
44
+ )}
45
+ })
46
+
47
+ // Schema for creating new users
48
+ export const ${camelName}DataSchema = Type.Pick(${camelName}Schema, [
49
+ ${authStrategies.map((name) => (name === 'local' ? `'email', 'password'` : `'${name}Id'`)).join(', ')}
50
+ ],
51
+ { $id: '${upperName}Data', additionalProperties: false }
52
+ )
53
+ export type ${upperName}Data = Static<typeof ${camelName}DataSchema>
54
+ export const ${camelName}DataValidator = getDataValidator(${camelName}DataSchema, dataValidator)
55
+ export const ${camelName}DataResolver = resolve<${upperName}, HookContext>({
56
+ ${localTemplate(authStrategies, `password: passwordHash({ strategy: 'local' })`)}
57
+ })
58
+
59
+ // Schema for updating existing users
60
+ export const ${camelName}PatchSchema = Type.Partial(${camelName}Schema, {
61
+ $id: '${upperName}Patch'
62
+ })
63
+ export type ${upperName}Patch = Static<typeof ${camelName}PatchSchema>
64
+ export const ${camelName}PatchValidator = getDataValidator(${camelName}PatchSchema, dataValidator)
65
+ export const ${camelName}PatchResolver = resolve<${upperName}, HookContext>({
66
+ ${localTemplate(authStrategies, `password: passwordHash({ strategy: 'local' })`)}
67
+ })
68
+
69
+ // Schema for allowed query properties
70
+ export const ${camelName}QueryProperties = Type.Pick(${camelName}Schema, ['${
71
+ type === 'mongodb' ? '_id' : 'id'
72
+ }', ${authStrategies.map((name) => (name === 'local' ? `'email'` : `'${name}Id'`)).join(', ')}
73
+ ])
74
+ export const ${camelName}QuerySchema = Type.Intersect([
75
+ querySyntax(${camelName}QueryProperties),
76
+ // Add additional query properties here
77
+ Type.Object({}, { additionalProperties: false })
78
+ ], { additionalProperties: false })
79
+ export type ${upperName}Query = Static<typeof ${camelName}QuerySchema>
80
+ export const ${camelName}QueryValidator = getValidator(${camelName}QuerySchema, queryValidator)
81
+ export const ${camelName}QueryResolver = resolve<${upperName}Query, HookContext>({
82
+ // If there is a user (e.g. with authentication), they are only allowed to see their own data
83
+ ${type === 'mongodb' ? '_id' : 'id'}: async (value, user, context) => {
84
+ if (context.params.user) {
85
+ return context.params.user.${type === 'mongodb' ? '_id' : 'id'}
86
+ }
87
+
88
+ return value
89
+ }
90
+ })
91
+ `
92
+
93
+ export const generate = (ctx: AuthenticationGeneratorContext) =>
94
+ generator(ctx).then(
95
+ when<AuthenticationGeneratorContext>(
96
+ ({ schema }) => schema === 'typebox',
97
+ renderSource(
98
+ template,
99
+ toFile(({ lib, folder, fileName }: AuthenticationGeneratorContext) => [
100
+ lib,
101
+ 'services',
102
+ ...folder,
103
+ `${fileName}.schema`
104
+ ]),
105
+ { force: true }
106
+ )
107
+ )
108
+ )
@@ -0,0 +1,150 @@
1
+ import { PackageJson } from 'type-fest';
2
+ import { Callable, PinionContext, Location } from '@feathershq/pinion';
3
+ import * as ts from 'typescript';
4
+ import { Options as PrettierOptions } from 'prettier';
5
+ export declare const version: any;
6
+ export type DependencyVersions = {
7
+ [key: string]: string;
8
+ };
9
+ /**
10
+ * The database types supported by this generator
11
+ */
12
+ export type DatabaseType = 'mongodb' | 'mysql' | 'postgresql' | 'sqlite' | 'mssql';
13
+ /**
14
+ * Returns the name of the Feathers database adapter for a supported database type
15
+ *
16
+ * @param database The type of the database
17
+ * @returns The name of the adapter
18
+ */
19
+ export declare const getDatabaseAdapter: (database: DatabaseType) => "mongodb" | "knex";
20
+ export type FeathersAppInfo = {
21
+ /**
22
+ * The application language
23
+ */
24
+ language: 'ts' | 'js';
25
+ /**
26
+ * The main database
27
+ */
28
+ database: DatabaseType;
29
+ /**
30
+ * The package manager used
31
+ */
32
+ packager: 'yarn' | 'npm';
33
+ /**
34
+ * A list of all chosen transports
35
+ */
36
+ transports: ('rest' | 'websockets')[];
37
+ /**
38
+ * The HTTP framework used
39
+ */
40
+ framework: 'koa' | 'express';
41
+ /**
42
+ * The main schema definition format
43
+ */
44
+ schema: 'typebox' | 'json';
45
+ };
46
+ export interface AppPackageJson extends PackageJson {
47
+ feathers?: FeathersAppInfo;
48
+ }
49
+ export interface FeathersBaseContext extends PinionContext {
50
+ /**
51
+ * Information about the Feathers application (like chosen language, database etc.)
52
+ * usually taken from `package.json`
53
+ */
54
+ feathers: FeathersAppInfo;
55
+ /**
56
+ * The package.json file
57
+ */
58
+ pkg: AppPackageJson;
59
+ /**
60
+ * The folder where source files are put
61
+ */
62
+ lib: string;
63
+ /**
64
+ * The folder where test files are put
65
+ */
66
+ test: string;
67
+ /**
68
+ * The language the app is generated in
69
+ */
70
+ language: 'js' | 'ts';
71
+ /**
72
+ * A list dependencies that should be installed with a certain version.
73
+ * Used for installing development dependencies during testing.
74
+ */
75
+ dependencyVersions?: DependencyVersions;
76
+ }
77
+ /**
78
+ * Returns dependencies with the versions from the context attached (if available)
79
+ *
80
+ * @param dependencies The dependencies to install
81
+ * @param versions The dependency version list
82
+ * @returns A list of dependencies with their versions
83
+ */
84
+ export declare const addVersions: (dependencies: string[], versions: DependencyVersions) => string[];
85
+ /**
86
+ * Loads the application package.json and populates information like the library and test directory
87
+ * and Feathers app specific information.
88
+ *
89
+ * @returns The updated context
90
+ */
91
+ export declare const initializeBaseContext: () => <C extends FeathersBaseContext>(ctx: C) => Promise<Awaited<C> & {
92
+ lib: string;
93
+ test: string;
94
+ language: "ts" | "js";
95
+ feathers: FeathersAppInfo;
96
+ }>;
97
+ /**
98
+ * Checks if the current context contains a valid generated application. This is necesary for most
99
+ * generators (besides the app generator).
100
+ *
101
+ * @param ctx The context to check against
102
+ * @returns Throws an error or returns the original context
103
+ */
104
+ export declare const checkPreconditions: () => <T extends FeathersBaseContext>(ctx: T) => Promise<T>;
105
+ /**
106
+ * Returns the transpiled and prettified JavaScript for a TypeScript source code
107
+ *
108
+ * @param typescript The TypeScript source code
109
+ * @param options TypeScript transpilation options
110
+ * @returns The formatted JavaScript source code
111
+ */
112
+ export declare const getJavaScript: (typescript: string, options?: ts.TranspileOptions) => string;
113
+ /**
114
+ * The default configuration for prettifying files
115
+ */
116
+ export declare const PRETTIERRC: PrettierOptions;
117
+ export declare const prettify: <C extends PinionContext & {
118
+ language: 'js' | 'ts';
119
+ }>(target: Callable<string, C>, options?: PrettierOptions) => (ctx: C) => Promise<C>;
120
+ /**
121
+ * Render a source file template for the language set in the context.
122
+ *
123
+ * @param templates The JavaScript and TypeScript template to render
124
+ * @param target The target filename without extension (will be added based on language)
125
+ * @returns The updated context
126
+ */
127
+ export declare const renderSource: <C extends PinionContext & {
128
+ language: 'js' | 'ts';
129
+ }>(template: Callable<string, C>, target: Callable<string, C>, options?: {
130
+ force: boolean;
131
+ }) => (ctx: C) => Promise<C>;
132
+ /**
133
+ * Inject a source template as the language set in the context.
134
+ *
135
+ * @param template The source template to render
136
+ * @param location The location to inject the code to. Must use the target language.
137
+ * @param target The target file name
138
+ * @param transpile Set to `false` if the code should not be transpiled to JavaScript
139
+ * @returns
140
+ */
141
+ export declare const injectSource: <C extends PinionContext & {
142
+ language: 'js' | 'ts';
143
+ }>(template: Callable<string, C>, location: Location<C>, target: Callable<string, C>, transpile?: boolean) => (ctx: C) => Promise<C>;
144
+ /**
145
+ * Synchronously checks if a file exits
146
+ * @param context The base context
147
+ * @param filenames The filenames to check
148
+ * @returns Wether the file exists or not
149
+ */
150
+ export declare const fileExists: (...filenames: string[]) => boolean;
package/lib/commons.js ADDED
@@ -0,0 +1,198 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || function (mod) {
19
+ if (mod && mod.__esModule) return mod;
20
+ var result = {};
21
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
+ __setModuleDefault(result, mod);
23
+ return result;
24
+ };
25
+ var __importDefault = (this && this.__importDefault) || function (mod) {
26
+ return (mod && mod.__esModule) ? mod : { "default": mod };
27
+ };
28
+ Object.defineProperty(exports, "__esModule", { value: true });
29
+ exports.fileExists = exports.injectSource = exports.renderSource = exports.prettify = exports.PRETTIERRC = exports.getJavaScript = exports.checkPreconditions = exports.initializeBaseContext = exports.addVersions = exports.getDatabaseAdapter = exports.version = void 0;
30
+ const fs_1 = __importDefault(require("fs"));
31
+ const path_1 = require("path");
32
+ const promises_1 = require("fs/promises");
33
+ const pinion_1 = require("@feathershq/pinion");
34
+ const ts = __importStar(require("typescript"));
35
+ const prettier_1 = __importDefault(require("prettier"));
36
+ const path_2 = __importDefault(require("path"));
37
+ exports.version = JSON.parse(fs_1.default.readFileSync((0, path_1.join)(__dirname, '..', 'package.json')).toString()).version;
38
+ /**
39
+ * Returns the name of the Feathers database adapter for a supported database type
40
+ *
41
+ * @param database The type of the database
42
+ * @returns The name of the adapter
43
+ */
44
+ const getDatabaseAdapter = (database) => (database === 'mongodb' ? 'mongodb' : 'knex');
45
+ exports.getDatabaseAdapter = getDatabaseAdapter;
46
+ /**
47
+ * Returns dependencies with the versions from the context attached (if available)
48
+ *
49
+ * @param dependencies The dependencies to install
50
+ * @param versions The dependency version list
51
+ * @returns A list of dependencies with their versions
52
+ */
53
+ const addVersions = (dependencies, versions) => dependencies.map((dep) => `${dep}@${versions[dep] ? versions[dep] : 'latest'}`);
54
+ exports.addVersions = addVersions;
55
+ /**
56
+ * Loads the application package.json and populates information like the library and test directory
57
+ * and Feathers app specific information.
58
+ *
59
+ * @returns The updated context
60
+ */
61
+ const initializeBaseContext = () => (ctx) => Promise.resolve(ctx)
62
+ .then((0, pinion_1.loadJSON)((0, pinion_1.fromFile)('package.json'), (pkg) => ({ pkg }), {}))
63
+ .then((0, pinion_1.loadJSON)(path_2.default.join(__dirname, '..', 'package.json'), (pkg) => ({
64
+ dependencyVersions: {
65
+ ...pkg.devDependencies,
66
+ ...ctx.dependencyVersions,
67
+ '@feathersjs/cli': exports.version
68
+ }
69
+ })))
70
+ .then((ctx) => {
71
+ var _a, _b, _c, _d, _e, _f, _g;
72
+ return ({
73
+ ...ctx,
74
+ lib: ((_b = (_a = ctx.pkg) === null || _a === void 0 ? void 0 : _a.directories) === null || _b === void 0 ? void 0 : _b.lib) || 'src',
75
+ test: ((_d = (_c = ctx.pkg) === null || _c === void 0 ? void 0 : _c.directories) === null || _d === void 0 ? void 0 : _d.test) || 'test',
76
+ language: ctx.language || ((_f = (_e = ctx.pkg) === null || _e === void 0 ? void 0 : _e.feathers) === null || _f === void 0 ? void 0 : _f.language),
77
+ feathers: (_g = ctx.pkg) === null || _g === void 0 ? void 0 : _g.feathers
78
+ });
79
+ });
80
+ exports.initializeBaseContext = initializeBaseContext;
81
+ /**
82
+ * Checks if the current context contains a valid generated application. This is necesary for most
83
+ * generators (besides the app generator).
84
+ *
85
+ * @param ctx The context to check against
86
+ * @returns Throws an error or returns the original context
87
+ */
88
+ const checkPreconditions = () => async (ctx) => {
89
+ if (!ctx.feathers) {
90
+ throw new Error(`Can not run generator since the current folder does not appear to be a Feathers application.
91
+ Either your package.json is missing or it does not have \`feathers\` property.
92
+ `);
93
+ }
94
+ return ctx;
95
+ };
96
+ exports.checkPreconditions = checkPreconditions;
97
+ const importRegex = /from '(\..*)'/g;
98
+ const escapeNewLines = (code) => code.replace(/\n\n/g, '\n/* :newline: */');
99
+ const restoreNewLines = (code) => code.replace(/\/\* :newline: \*\//g, '\n');
100
+ const fixLocalImports = (code) => code.replace(importRegex, "from '$1.js'");
101
+ /**
102
+ * Returns the transpiled and prettified JavaScript for a TypeScript source code
103
+ *
104
+ * @param typescript The TypeScript source code
105
+ * @param options TypeScript transpilation options
106
+ * @returns The formatted JavaScript source code
107
+ */
108
+ const getJavaScript = (typescript, options = {}) => {
109
+ const source = escapeNewLines(typescript);
110
+ const transpiled = ts.transpileModule(source, {
111
+ ...options,
112
+ compilerOptions: {
113
+ module: ts.ModuleKind.ESNext,
114
+ target: ts.ScriptTarget.ES2020,
115
+ preserveValueImports: true,
116
+ ...options.compilerOptions
117
+ }
118
+ });
119
+ return fixLocalImports(restoreNewLines(transpiled.outputText));
120
+ };
121
+ exports.getJavaScript = getJavaScript;
122
+ const getFileName = async (target, ctx) => `${await (0, pinion_1.getCallable)(target, ctx)}.${ctx.language}`;
123
+ /**
124
+ * The default configuration for prettifying files
125
+ */
126
+ exports.PRETTIERRC = {
127
+ tabWidth: 2,
128
+ useTabs: false,
129
+ printWidth: 110,
130
+ semi: false,
131
+ trailingComma: 'none',
132
+ singleQuote: true
133
+ };
134
+ /*
135
+ * Format a source file using Prettier. Will use the local configuration, the settings set in
136
+ * `options` or a default configuration
137
+ *
138
+ * @param target The file to prettify
139
+ * @param options The Prettier options
140
+ * @returns The updated context
141
+ */
142
+ const prettify = (target, options = exports.PRETTIERRC) => async (ctx) => {
143
+ const fileName = await getFileName(target, ctx);
144
+ const config = (await prettier_1.default.resolveConfig(ctx.cwd)) || options;
145
+ const content = (await (0, promises_1.readFile)(fileName)).toString();
146
+ try {
147
+ await (0, promises_1.writeFile)(fileName, await prettier_1.default.format(content, {
148
+ parser: ctx.language === 'ts' ? 'typescript' : 'babel',
149
+ ...config
150
+ }));
151
+ }
152
+ catch (error) {
153
+ throw new Error(`Error prettifying ${fileName}: ${error.message}`);
154
+ }
155
+ return ctx;
156
+ };
157
+ exports.prettify = prettify;
158
+ /**
159
+ * Render a source file template for the language set in the context.
160
+ *
161
+ * @param templates The JavaScript and TypeScript template to render
162
+ * @param target The target filename without extension (will be added based on language)
163
+ * @returns The updated context
164
+ */
165
+ const renderSource = (template, target, options) => async (ctx) => {
166
+ const { language } = ctx;
167
+ const fileName = await getFileName(target, ctx);
168
+ const content = language === 'js' ? (0, exports.getJavaScript)(await (0, pinion_1.getCallable)(template, ctx)) : template;
169
+ const renderer = (0, pinion_1.renderTemplate)(content, fileName, options);
170
+ return renderer(ctx).then((0, exports.prettify)(target));
171
+ };
172
+ exports.renderSource = renderSource;
173
+ /**
174
+ * Inject a source template as the language set in the context.
175
+ *
176
+ * @param template The source template to render
177
+ * @param location The location to inject the code to. Must use the target language.
178
+ * @param target The target file name
179
+ * @param transpile Set to `false` if the code should not be transpiled to JavaScript
180
+ * @returns
181
+ */
182
+ const injectSource = (template, location, target, transpile = true) => async (ctx) => {
183
+ const { language } = ctx;
184
+ const source = language === 'js' && transpile ? (0, exports.getJavaScript)(await (0, pinion_1.getCallable)(template, ctx)) : template;
185
+ const fileName = await getFileName(target, ctx);
186
+ const injector = (0, pinion_1.inject)(source, location, fileName);
187
+ return injector(ctx).then((0, exports.prettify)(target));
188
+ };
189
+ exports.injectSource = injectSource;
190
+ /**
191
+ * Synchronously checks if a file exits
192
+ * @param context The base context
193
+ * @param filenames The filenames to check
194
+ * @returns Wether the file exists or not
195
+ */
196
+ const fileExists = (...filenames) => fs_1.default.existsSync((0, path_1.join)(...filenames));
197
+ exports.fileExists = fileExists;
198
+ //# sourceMappingURL=commons.js.map