@anu8151/adonisjs-blueprint 0.2.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.
Files changed (90) hide show
  1. package/LICENSE.md +9 -0
  2. package/README.md +131 -0
  3. package/build/configure.d.ts +2 -0
  4. package/build/configure.js +7 -0
  5. package/build/index.d.ts +16 -0
  6. package/build/index.js +9 -0
  7. package/build/init-TjAcOVVP.js +64 -0
  8. package/build/main-1fZp_M_R.js +8 -0
  9. package/build/parser-DJB5DEck.js +5832 -0
  10. package/build/src/commands/build.d.ts +14 -0
  11. package/build/src/commands/build.js +177 -0
  12. package/build/src/commands/erase.d.ts +6 -0
  13. package/build/src/commands/erase.js +23 -0
  14. package/build/src/commands/init.d.ts +6 -0
  15. package/build/src/commands/main.d.ts +1 -0
  16. package/build/src/commands/main.js +10 -0
  17. package/build/src/commands/stubs.d.ts +6 -0
  18. package/build/src/commands/stubs.js +16 -0
  19. package/build/src/commands/trace.d.ts +6 -0
  20. package/build/src/commands/trace.js +60 -0
  21. package/build/src/generators/base_generator.d.ts +12 -0
  22. package/build/src/generators/base_generator.js +31 -0
  23. package/build/src/generators/channel_generator.d.ts +4 -0
  24. package/build/src/generators/channel_generator.js +25 -0
  25. package/build/src/generators/class_generator.d.ts +4 -0
  26. package/build/src/generators/class_generator.js +11 -0
  27. package/build/src/generators/controller_generator.d.ts +5 -0
  28. package/build/src/generators/controller_generator.js +355 -0
  29. package/build/src/generators/enum_generator.d.ts +4 -0
  30. package/build/src/generators/enum_generator.js +17 -0
  31. package/build/src/generators/event_generator.d.ts +4 -0
  32. package/build/src/generators/event_generator.js +10 -0
  33. package/build/src/generators/factory_generator.d.ts +4 -0
  34. package/build/src/generators/factory_generator.js +50 -0
  35. package/build/src/generators/job_generator.d.ts +4 -0
  36. package/build/src/generators/job_generator.js +10 -0
  37. package/build/src/generators/mail_generator.d.ts +4 -0
  38. package/build/src/generators/mail_generator.js +10 -0
  39. package/build/src/generators/middleware_generator.d.ts +4 -0
  40. package/build/src/generators/middleware_generator.js +10 -0
  41. package/build/src/generators/migration_generator.d.ts +5 -0
  42. package/build/src/generators/migration_generator.js +46 -0
  43. package/build/src/generators/model_generator.d.ts +4 -0
  44. package/build/src/generators/model_generator.js +57 -0
  45. package/build/src/generators/notification_generator.d.ts +4 -0
  46. package/build/src/generators/notification_generator.js +10 -0
  47. package/build/src/generators/openapi_generator.d.ts +8 -0
  48. package/build/src/generators/openapi_generator.js +200 -0
  49. package/build/src/generators/policy_generator.d.ts +4 -0
  50. package/build/src/generators/policy_generator.js +29 -0
  51. package/build/src/generators/route_generator.d.ts +4 -0
  52. package/build/src/generators/route_generator.js +34 -0
  53. package/build/src/generators/seeder_generator.d.ts +4 -0
  54. package/build/src/generators/seeder_generator.js +16 -0
  55. package/build/src/generators/service_generator.d.ts +4 -0
  56. package/build/src/generators/service_generator.js +14 -0
  57. package/build/src/generators/test_generator.d.ts +5 -0
  58. package/build/src/generators/test_generator.js +38 -0
  59. package/build/src/generators/validator_generator.d.ts +4 -0
  60. package/build/src/generators/validator_generator.js +70 -0
  61. package/build/src/generators/view_generator.d.ts +4 -0
  62. package/build/src/generators/view_generator.js +23 -0
  63. package/build/src/parser.d.ts +7 -0
  64. package/build/src/parser.js +2 -0
  65. package/build/src/statements/index.d.ts +1 -0
  66. package/build/src/statements_registry.d.ts +47 -0
  67. package/build/src/types.d.ts +50 -0
  68. package/build/statements_registry-DzyxAiKP.js +19 -0
  69. package/build/stubs/config.stub +32 -0
  70. package/build/stubs/main.d.ts +5 -0
  71. package/build/stubs/make/controller/main.stub +47 -0
  72. package/build/stubs/make/enum/main.stub +10 -0
  73. package/build/stubs/make/event/main.stub +12 -0
  74. package/build/stubs/make/factory/main.stub +25 -0
  75. package/build/stubs/make/job/main.stub +12 -0
  76. package/build/stubs/make/mail/main.stub +23 -0
  77. package/build/stubs/make/middleware/main.stub +16 -0
  78. package/build/stubs/make/migration/main.stub +25 -0
  79. package/build/stubs/make/model/main.stub +19 -0
  80. package/build/stubs/make/notification/main.stub +28 -0
  81. package/build/stubs/make/policy/main.stub +17 -0
  82. package/build/stubs/make/seeder/main.stub +21 -0
  83. package/build/stubs/make/service/main.stub +8 -0
  84. package/build/stubs/make/test/controller.stub +23 -0
  85. package/build/stubs/make/validator/main.stub +22 -0
  86. package/build/stubs/make/view/edge.stub +65 -0
  87. package/build/stubs/make/view/react.stub +57 -0
  88. package/build/stubs/make/view/svelte.stub +67 -0
  89. package/build/stubs/make/view/vue.stub +74 -0
  90. package/package.json +151 -0
@@ -0,0 +1,200 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ import { writeFileSync } from "node:fs";
3
+ import string from "@adonisjs/core/helpers/string";
4
+ //#region src/generators/openapi_generator.ts
5
+ var OpenAPIGenerator = class extends BaseGenerator {
6
+ async generate(_name, blueprint) {
7
+ if (!blueprint.controllers) return;
8
+ const openapi = {
9
+ openapi: "3.0.0",
10
+ info: {
11
+ title: blueprint.settings?.api ? "AdonisJS API Documentation" : "AdonisJS Application API",
12
+ version: "1.0.0"
13
+ },
14
+ paths: {},
15
+ components: {
16
+ schemas: {},
17
+ securitySchemes: { bearerAuth: {
18
+ type: "http",
19
+ scheme: "bearer",
20
+ bearerFormat: "JWT"
21
+ } }
22
+ }
23
+ };
24
+ if (blueprint.models) for (const [modelName, modelDef] of Object.entries(blueprint.models)) {
25
+ const schema = {
26
+ type: "object",
27
+ properties: {},
28
+ required: []
29
+ };
30
+ if (modelDef.attributes) for (const [attrName, attrType] of Object.entries(modelDef.attributes)) {
31
+ const typeStr = typeof attrType === "string" ? attrType : attrType.type || "string";
32
+ schema.properties[attrName] = { type: this.mapToOpenAPIType(typeStr) };
33
+ if (typeof attrType === "string" && !attrType.includes("optional") && !attrType.includes("nullable")) schema.required.push(attrName);
34
+ }
35
+ if (schema.required.length === 0) delete schema.required;
36
+ openapi.components.schemas[modelName] = schema;
37
+ }
38
+ for (const [controllerName, controllerDef] of Object.entries(blueprint.controllers)) {
39
+ const resourceName = string.snakeCase(controllerName);
40
+ const normalizedDefinition = this.normalizeDefinition(controllerDef, blueprint.settings?.api, controllerName);
41
+ const modelName = string.pascalCase(string.singular(controllerName));
42
+ for (const [actionName, actionDef] of Object.entries(normalizedDefinition)) {
43
+ if (actionName === "resource" || actionName === "middleware" || actionName === "stub") continue;
44
+ const { path, method } = this.inferRoute(resourceName, actionName);
45
+ if (!path || !method) continue;
46
+ if (!openapi.paths[path]) openapi.paths[path] = {};
47
+ const operation = {
48
+ tags: [controllerName],
49
+ summary: `${actionName} action for ${controllerName}`,
50
+ responses: { "200": { description: "Successful response" } }
51
+ };
52
+ if (path.includes("{id}")) operation.parameters = [{
53
+ name: "id",
54
+ in: "path",
55
+ required: true,
56
+ schema: { type: "string" }
57
+ }];
58
+ if (actionDef.auth) operation.security = [{ bearerAuth: [] }];
59
+ if (actionDef.validate) {
60
+ const validateFields = actionDef.validate === "all" ? Object.keys(blueprint.models?.[modelName]?.attributes || {}) : actionDef.validate.split(",").map((f) => f.trim());
61
+ operation.requestBody = { content: { "application/json": { schema: {
62
+ type: "object",
63
+ properties: {}
64
+ } } } };
65
+ for (const field of validateFields) {
66
+ const attrType = blueprint.models?.[modelName]?.attributes?.[field];
67
+ const typeStr = typeof attrType === "string" ? attrType : attrType?.type || "string";
68
+ operation.requestBody.content["application/json"].schema.properties[field] = { type: this.mapToOpenAPIType(typeStr) };
69
+ }
70
+ } else if (actionName === "store" || actionName === "update") operation.requestBody = { content: { "application/json": { schema: { $ref: `#/components/schemas/${modelName}` } } } };
71
+ if (actionDef.query === "all" || actionDef.query?.startsWith("paginate")) {
72
+ operation.responses["200"].content = { "application/json": { schema: {
73
+ type: "array",
74
+ items: { $ref: `#/components/schemas/${modelName}` }
75
+ } } };
76
+ if (actionDef.query.startsWith("paginate")) {
77
+ if (!operation.parameters) operation.parameters = [];
78
+ operation.parameters.push({
79
+ name: "page",
80
+ in: "query",
81
+ schema: {
82
+ type: "integer",
83
+ default: 1
84
+ }
85
+ }, {
86
+ name: "limit",
87
+ in: "query",
88
+ schema: {
89
+ type: "integer",
90
+ default: 20
91
+ }
92
+ });
93
+ }
94
+ } else if (actionDef.query === "find") operation.responses["200"].content = { "application/json": { schema: { $ref: `#/components/schemas/${modelName}` } } };
95
+ openapi.paths[path][method] = operation;
96
+ }
97
+ }
98
+ const outputPath = this.app.makePath("openapi.json");
99
+ writeFileSync(outputPath, JSON.stringify(openapi, null, 2));
100
+ this.logger.action(`create ${outputPath}`).succeeded();
101
+ if (this.manifest) this.manifest.push(outputPath);
102
+ }
103
+ mapToOpenAPIType(type) {
104
+ switch (type.split(":")[0]) {
105
+ case "integer":
106
+ case "number": return "number";
107
+ case "boolean": return "boolean";
108
+ case "datetime":
109
+ case "timestamp":
110
+ case "date": return "string";
111
+ default: return "string";
112
+ }
113
+ }
114
+ normalizeDefinition(definition, isApi, controllerName) {
115
+ if (definition.resource) {
116
+ const pluralName = string.plural(string.camelCase(controllerName || ""));
117
+ return isApi ? {
118
+ index: {
119
+ query: "all",
120
+ render: "json"
121
+ },
122
+ store: {
123
+ validate: "all",
124
+ save: true,
125
+ render: "json"
126
+ },
127
+ show: {
128
+ query: "find",
129
+ render: "json"
130
+ },
131
+ update: {
132
+ validate: "all",
133
+ save: true,
134
+ render: "json"
135
+ },
136
+ destroy: {
137
+ delete: true,
138
+ render: "json"
139
+ }
140
+ } : {
141
+ index: { render: `${pluralName}/index` },
142
+ create: { render: `${pluralName}/create` },
143
+ store: {
144
+ validate: "all",
145
+ save: true,
146
+ redirect: `${pluralName}.index`
147
+ },
148
+ show: { render: `${pluralName}/show` },
149
+ edit: { render: `${pluralName}/edit` },
150
+ update: {
151
+ validate: "all",
152
+ save: true,
153
+ redirect: `${pluralName}.index`
154
+ },
155
+ destroy: {
156
+ delete: true,
157
+ redirect: `${pluralName}.index`
158
+ }
159
+ };
160
+ }
161
+ return definition;
162
+ }
163
+ inferRoute(resourceName, actionName) {
164
+ return {
165
+ index: {
166
+ path: `/${resourceName}`,
167
+ method: "get"
168
+ },
169
+ create: {
170
+ path: `/${resourceName}/create`,
171
+ method: "get"
172
+ },
173
+ store: {
174
+ path: `/${resourceName}`,
175
+ method: "post"
176
+ },
177
+ show: {
178
+ path: `/${resourceName}/{id}`,
179
+ method: "get"
180
+ },
181
+ edit: {
182
+ path: `/${resourceName}/{id}/edit`,
183
+ method: "get"
184
+ },
185
+ update: {
186
+ path: `/${resourceName}/{id}`,
187
+ method: "put"
188
+ },
189
+ destroy: {
190
+ path: `/${resourceName}/{id}`,
191
+ method: "delete"
192
+ }
193
+ }[actionName] || {
194
+ path: `/${resourceName}/${string.snakeCase(actionName)}`,
195
+ method: "get"
196
+ };
197
+ }
198
+ };
199
+ //#endregion
200
+ export { OpenAPIGenerator };
@@ -0,0 +1,4 @@
1
+ import { BaseGenerator } from './base_generator.js';
2
+ export declare class PolicyGenerator extends BaseGenerator {
3
+ generate(name: string, definition: any): Promise<void>;
4
+ }
@@ -0,0 +1,29 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ import string from "@adonisjs/core/helpers/string";
3
+ //#region src/generators/policy_generator.ts
4
+ var PolicyGenerator = class extends BaseGenerator {
5
+ async generate(name, definition) {
6
+ const entity = this.app.generators.createEntity(name);
7
+ const actions = [];
8
+ for (const [actionName, actionDef] of Object.entries(definition)) {
9
+ if (typeof actionDef !== "object") continue;
10
+ let policyAction = actionName;
11
+ if (actionName === "index") policyAction = "viewAny";
12
+ if (actionName === "show") policyAction = "view";
13
+ if (actionName === "store") policyAction = "create";
14
+ if (actionName === "update") policyAction = "update";
15
+ if (actionName === "destroy") policyAction = "delete";
16
+ actions.push({
17
+ name: policyAction,
18
+ modelName: entity.className,
19
+ variableName: string.camelCase(entity.className)
20
+ });
21
+ }
22
+ await this.generateStub("make/policy/main.stub", {
23
+ entity,
24
+ actions
25
+ });
26
+ }
27
+ };
28
+ //#endregion
29
+ export { PolicyGenerator };
@@ -0,0 +1,4 @@
1
+ import { BaseGenerator } from './base_generator.js';
2
+ export declare class RouteGenerator extends BaseGenerator {
3
+ generate(name: string, definition: any, isApi?: boolean): Promise<void>;
4
+ }
@@ -0,0 +1,34 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ import { existsSync, readFileSync, writeFileSync } from "node:fs";
3
+ //#region src/generators/route_generator.ts
4
+ var RouteGenerator = class extends BaseGenerator {
5
+ async generate(name, definition, isApi = false) {
6
+ const nameParts = name.split(/[\/.]/);
7
+ const baseName = nameParts.pop();
8
+ const parents = nameParts.map((p) => p.toLowerCase() + "s");
9
+ const entity = this.app.generators.createEntity(baseName);
10
+ const routesPath = this.app.makePath("start/routes.ts");
11
+ if (!existsSync(routesPath)) {
12
+ this.logger.warning(`File ${routesPath} not found. Skipping route registration.`);
13
+ return;
14
+ }
15
+ const resourceName = entity.name.toLowerCase() + "s";
16
+ const fullResourcePath = [...parents, resourceName].join(".");
17
+ const controllerPath = [...nameParts.map((p) => p.toLowerCase()), entity.name.toLowerCase()].join("/");
18
+ let content = readFileSync(routesPath, "utf8");
19
+ if (content.includes(`router.resource('${fullResourcePath}'`)) return;
20
+ let routeLine = `router.resource('${fullResourcePath}', '#controllers/${controllerPath}_controller')`;
21
+ if (isApi) routeLine += ".apiOnly()";
22
+ if (definition.middleware && definition.middleware.length > 0) {
23
+ const mw = definition.middleware.map((m) => `middleware.${m}()`).join(", ");
24
+ routeLine += `.use('*', [${mw}])`;
25
+ }
26
+ if (nameParts.length > 0) {
27
+ const prefix = nameParts.map((p) => p.toLowerCase()).join("/");
28
+ writeFileSync(routesPath, content + `\nrouter.group(() => {\n ${routeLine}\n}).prefix('${prefix}')`);
29
+ } else writeFileSync(routesPath, content + `\n${routeLine}`);
30
+ this.logger.success(`Registered resource routes for ${fullResourcePath}`);
31
+ }
32
+ };
33
+ //#endregion
34
+ export { RouteGenerator };
@@ -0,0 +1,4 @@
1
+ import { BaseGenerator } from './base_generator.js';
2
+ export declare class SeederGenerator extends BaseGenerator {
3
+ generate(name: string, definition: any): Promise<void>;
4
+ }
@@ -0,0 +1,16 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ //#region src/generators/seeder_generator.ts
3
+ var SeederGenerator = class extends BaseGenerator {
4
+ async generate(name, definition) {
5
+ const entity = this.app.generators.createEntity(name);
6
+ const count = definition.seed || 10;
7
+ const data = definition.data || null;
8
+ await this.generateStub("make/seeder/main.stub", {
9
+ entity,
10
+ count,
11
+ data
12
+ });
13
+ }
14
+ };
15
+ //#endregion
16
+ export { SeederGenerator };
@@ -0,0 +1,4 @@
1
+ import { BaseGenerator } from './base_generator.js';
2
+ export declare class ServiceGenerator extends BaseGenerator {
3
+ generate(name: string): Promise<void>;
4
+ }
@@ -0,0 +1,14 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ import string from "@adonisjs/core/helpers/string";
3
+ //#region src/generators/service_generator.ts
4
+ var ServiceGenerator = class extends BaseGenerator {
5
+ async generate(name) {
6
+ const nameParts = name.split(/[\/.]/);
7
+ const baseName = nameParts.pop();
8
+ const entity = this.app.generators.createEntity(baseName);
9
+ if (nameParts.length > 0) entity.path = nameParts.map((p) => string.snakeCase(p)).join("/");
10
+ await this.generateStub("make/service/main.stub", { entity });
11
+ }
12
+ };
13
+ //#endregion
14
+ export { ServiceGenerator };
@@ -0,0 +1,5 @@
1
+ import { BaseGenerator } from './base_generator.js';
2
+ import type { BlueprintSchema } from '../types.js';
3
+ export declare class TestGenerator extends BaseGenerator {
4
+ generate(name: string, definition: any, blueprint: BlueprintSchema): Promise<void>;
5
+ }
@@ -0,0 +1,38 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ import string from "@adonisjs/core/helpers/string";
3
+ //#region src/generators/test_generator.ts
4
+ var TestGenerator = class extends BaseGenerator {
5
+ async generate(name, definition, blueprint) {
6
+ const entity = this.app.generators.createEntity(name);
7
+ const actions = [];
8
+ const pluralName = string.plural(string.snakeCase(entity.name));
9
+ for (const [actionName, actionDef] of Object.entries(definition)) {
10
+ if (typeof actionDef !== "object") continue;
11
+ let method = "get";
12
+ let url = `/${pluralName}`;
13
+ const typedDef = actionDef;
14
+ if (actionName === "store") method = "post";
15
+ else if (actionName === "show" || actionName === "edit") url = `/${pluralName}/1`;
16
+ else if (actionName === "update") {
17
+ method = "put";
18
+ url = `/${pluralName}/1`;
19
+ } else if (actionName === "destroy") {
20
+ method = "delete";
21
+ url = `/${pluralName}/1`;
22
+ } else if (actionName === "create") url = `/${pluralName}/create`;
23
+ actions.push({
24
+ name: actionName,
25
+ method,
26
+ url,
27
+ auth: !!typedDef.auth
28
+ });
29
+ }
30
+ await this.generateStub("make/test/controller.stub", {
31
+ entity,
32
+ actions,
33
+ hasAuth: actions.some((a) => a.auth) || !!blueprint.auth
34
+ });
35
+ }
36
+ };
37
+ //#endregion
38
+ export { TestGenerator };
@@ -0,0 +1,4 @@
1
+ import { BaseGenerator } from './base_generator.js';
2
+ export declare class ValidatorGenerator extends BaseGenerator {
3
+ generate(name: string, definition: any): Promise<void>;
4
+ }
@@ -0,0 +1,70 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ import string from "@adonisjs/core/helpers/string";
3
+ //#region src/generators/validator_generator.ts
4
+ var ValidatorGenerator = class extends BaseGenerator {
5
+ async generate(name, definition) {
6
+ const entity = this.app.generators.createEntity(name);
7
+ const attributes = [];
8
+ if (definition.attributes) for (const [attrName, attrType] of Object.entries(definition.attributes)) {
9
+ let vineChain = "vine.string()";
10
+ const parts = (typeof attrType === "string" ? attrType : attrType.type || "string").split(":");
11
+ const baseType = parts[0];
12
+ if (baseType === "number" || baseType === "integer") vineChain = "vine.number()";
13
+ else if (baseType === "boolean") vineChain = "vine.boolean()";
14
+ else if (baseType === "email") vineChain = "vine.string().email()";
15
+ else if (baseType === "url") vineChain = "vine.string().url()";
16
+ else if (baseType === "ip") vineChain = "vine.string().ip()";
17
+ else if (baseType === "uuid") vineChain = "vine.string().uuid()";
18
+ else if (baseType === "mobile") vineChain = "vine.string().mobile()";
19
+ else if (baseType === "postalCode") vineChain = "vine.string().postalCode()";
20
+ else if (baseType === "creditCard") vineChain = "vine.string().creditCard()";
21
+ else if (baseType === "macAddress") vineChain = "vine.string().macAddress()";
22
+ for (let i = 1; i < parts.length; i++) {
23
+ const modifier = parts[i];
24
+ if (modifier === "unique") {
25
+ const tableName = string.plural(string.snakeCase(entity.name));
26
+ const scope = parts.find((p) => p.startsWith("scope:"));
27
+ if (scope) {
28
+ const scopeColumn = scope.replace("scope:", "");
29
+ vineChain += `.unique(async (db, value, field) => {
30
+ const query = db.from('${tableName}').where('${attrName}', value)
31
+ if (field.meta.id) query.whereNot('id', field.meta.id)
32
+ const scopeValue = field.meta['${scopeColumn}'] || field.data['${scopeColumn}']
33
+ if (scopeValue) query.where('${scopeColumn}', scopeValue)
34
+ return !await query.first()
35
+ })`;
36
+ } else vineChain += `.unique(async (db, value, field) => {
37
+ const query = db.from('${tableName}').where('${attrName}', value)
38
+ if (field.meta.id) query.whereNot('id', field.meta.id)
39
+ return !await query.first()
40
+ })`;
41
+ } else if (modifier === "min" && parts[i + 1]) {
42
+ vineChain += baseType === "number" ? `.min(${parts[i + 1]})` : `.minLength(${parts[i + 1]})`;
43
+ i++;
44
+ } else if (modifier === "max" && parts[i + 1]) {
45
+ vineChain += baseType === "number" ? `.max(${parts[i + 1]})` : `.maxLength(${parts[i + 1]})`;
46
+ i++;
47
+ } else if (modifier === "optional" || modifier === "nullable") vineChain += ".optional()";
48
+ else if (modifier === "confirmed") vineChain += ".confirmed()";
49
+ else if (modifier === "regex" && parts[i + 1]) {
50
+ vineChain += `.regex(new RegExp('${parts[i + 1]}'))`;
51
+ i++;
52
+ }
53
+ }
54
+ attributes.push({
55
+ name: attrName,
56
+ vineType: vineChain.replace("vine.", "")
57
+ });
58
+ if (parts.includes("confirmed")) attributes.push({
59
+ name: `${attrName}_confirmation`,
60
+ vineType: vineChain.replace("vine.", "").replace(".confirmed()", "")
61
+ });
62
+ }
63
+ await this.generateStub("make/validator/main.stub", {
64
+ entity,
65
+ attributes
66
+ }, definition.stub);
67
+ }
68
+ };
69
+ //#endregion
70
+ export { ValidatorGenerator };
@@ -0,0 +1,4 @@
1
+ import { BaseGenerator } from './base_generator.js';
2
+ export declare class ViewGenerator extends BaseGenerator {
3
+ generate(name: string, useInertia?: boolean, adapter?: 'react' | 'vue' | 'svelte', definition?: any): Promise<void>;
4
+ }
@@ -0,0 +1,23 @@
1
+ import { BaseGenerator } from "./base_generator.js";
2
+ //#region src/generators/view_generator.ts
3
+ var ViewGenerator = class extends BaseGenerator {
4
+ async generate(name, useInertia = false, adapter = "react", definition) {
5
+ const entity = this.app.generators.createEntity(name);
6
+ let stubPath = "make/view/edge.stub";
7
+ if (useInertia) stubPath = `make/view/${adapter}.stub`;
8
+ const attributes = definition?.attributes ? Object.entries(definition.attributes).map(([attrName, attrType]) => ({
9
+ name: attrName,
10
+ type: typeof attrType === "string" ? attrType : attrType.type
11
+ })) : [];
12
+ const action = name.split("/").pop() || "show";
13
+ const folder = name.split("/").slice(0, -1).join("/");
14
+ await this.generateStub(stubPath, {
15
+ entity,
16
+ attributes,
17
+ action,
18
+ folder
19
+ });
20
+ }
21
+ };
22
+ //#endregion
23
+ export { ViewGenerator };
@@ -0,0 +1,7 @@
1
+ import type { BlueprintSchema } from './types.js';
2
+ export declare class BlueprintParser {
3
+ /**
4
+ * Parse the given draft file and validate it against the JSON schema
5
+ */
6
+ parse(filePath: string): Promise<BlueprintSchema>;
7
+ }
@@ -0,0 +1,2 @@
1
+ import { t as BlueprintParser } from "../parser-DJB5DEck.js";
2
+ export { BlueprintParser };
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,47 @@
1
+ import type { Entity } from './types.js';
2
+ import { type EventGenerator } from './generators/event_generator.js';
3
+ import { type MailGenerator } from './generators/mail_generator.js';
4
+ import { type JobGenerator } from './generators/job_generator.js';
5
+ import { type NotificationGenerator } from './generators/notification_generator.js';
6
+ import { type ServiceGenerator } from './generators/service_generator.js';
7
+ export interface StatementContext {
8
+ actionName: string;
9
+ actionDef: any;
10
+ entity: Entity;
11
+ isApi: boolean;
12
+ useInertia: boolean;
13
+ pluralName: string;
14
+ singularName: string;
15
+ generators: {
16
+ event: EventGenerator;
17
+ mail: MailGenerator;
18
+ job: JobGenerator;
19
+ notification: NotificationGenerator;
20
+ service: ServiceGenerator;
21
+ };
22
+ models?: any;
23
+ }
24
+ export interface StatementResult {
25
+ logicLines: string[];
26
+ imports?: {
27
+ models?: string[];
28
+ validators?: string[];
29
+ events?: string[];
30
+ policies?: string[];
31
+ mails?: string[];
32
+ jobs?: string[];
33
+ notifications?: string[];
34
+ services?: string[];
35
+ };
36
+ context?: string[];
37
+ }
38
+ export type StatementHandler = (value: any, context: StatementContext) => StatementResult | Promise<StatementResult>;
39
+ declare class StatementsRegistry {
40
+ private handlers;
41
+ register(name: string, handler: StatementHandler): void;
42
+ get(name: string): StatementHandler | undefined;
43
+ has(name: string): boolean;
44
+ all(): MapIterator<[string, StatementHandler]>;
45
+ }
46
+ export declare const statementsRegistry: StatementsRegistry;
47
+ export {};
@@ -0,0 +1,50 @@
1
+ export interface Entity {
2
+ name: string;
3
+ path: string;
4
+ className: string;
5
+ tableName?: string;
6
+ }
7
+ export interface ModelAttribute {
8
+ name: string;
9
+ type: string;
10
+ modifiers: string[];
11
+ }
12
+ export interface ModelRelationship {
13
+ type: 'belongsTo' | 'hasMany' | 'belongsToMany' | 'hasOne';
14
+ model: string;
15
+ }
16
+ export interface ModelDefinition {
17
+ name: string;
18
+ attributes: Record<string, string | {
19
+ type: string;
20
+ modifiers?: string[];
21
+ }>;
22
+ relationships?: Record<string, string>;
23
+ }
24
+ export interface ControllerAction {
25
+ query?: string;
26
+ render?: string;
27
+ validate?: string;
28
+ save?: string | boolean;
29
+ flash?: string;
30
+ redirect?: string;
31
+ delete?: string | boolean;
32
+ }
33
+ export interface ControllerDefinition {
34
+ name: string;
35
+ middleware?: string[];
36
+ actions: Record<string, ControllerAction>;
37
+ }
38
+ export interface BlueprintSchema {
39
+ settings?: {
40
+ api?: boolean;
41
+ inertia?: {
42
+ enabled: boolean;
43
+ adapter: 'react' | 'vue' | 'svelte';
44
+ };
45
+ };
46
+ auth?: Record<string, any> | boolean;
47
+ models?: Record<string, any>;
48
+ controllers?: Record<string, any>;
49
+ channels?: Record<string, any>;
50
+ }
@@ -0,0 +1,19 @@
1
+ //#region src/statements_registry.ts
2
+ var StatementsRegistry = class {
3
+ handlers = /* @__PURE__ */ new Map();
4
+ register(name, handler) {
5
+ this.handlers.set(name, handler);
6
+ }
7
+ get(name) {
8
+ return this.handlers.get(name);
9
+ }
10
+ has(name) {
11
+ return this.handlers.has(name);
12
+ }
13
+ all() {
14
+ return this.handlers.entries();
15
+ }
16
+ };
17
+ const statementsRegistry = new StatementsRegistry();
18
+ //#endregion
19
+ export { statementsRegistry as t };
@@ -0,0 +1,32 @@
1
+ {{{
2
+ exports({
3
+ to: app.configPath('blueprint.ts')
4
+ })
5
+ }}}
6
+ import { defineConfig } from '@anu8151/adonisjs-blueprint'
7
+
8
+ export default defineConfig({
9
+ /**
10
+ * Default view framework to use
11
+ * Options: 'edge', 'inertia'
12
+ */
13
+ viewer: 'edge',
14
+
15
+ /**
16
+ * Default Inertia adapter
17
+ * Options: 'react', 'vue', 'svelte'
18
+ */
19
+ inertia: {
20
+ adapter: 'react'
21
+ },
22
+
23
+ /**
24
+ * Custom namespaces for generated files
25
+ */
26
+ namespaces: {
27
+ models: 'app/models',
28
+ controllers: 'app/controllers',
29
+ validators: 'app/validators',
30
+ factories: 'database/factories',
31
+ }
32
+ })
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Path to the root directory where the stubs are stored. We use
3
+ * this path within commands and the configure hook
4
+ */
5
+ export declare const stubsRoot: string;