@exanderal/stackcraft 0.1.1 → 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 (91) hide show
  1. package/README.md +79 -8
  2. package/dist/create/index.d.ts.map +1 -1
  3. package/dist/create/index.js +24 -1
  4. package/dist/create/index.js.map +1 -1
  5. package/dist/create/scaffold.d.ts.map +1 -1
  6. package/dist/create/scaffold.js +8 -2
  7. package/dist/create/scaffold.js.map +1 -1
  8. package/dist/create/scaffolders/__tests__/web-vite.test.js +1 -0
  9. package/dist/create/scaffolders/__tests__/web-vite.test.js.map +1 -1
  10. package/dist/create/scaffolders/api-nestjs-graphql.d.ts +3 -0
  11. package/dist/create/scaffolders/api-nestjs-graphql.d.ts.map +1 -0
  12. package/dist/create/scaffolders/api-nestjs-graphql.js +31 -0
  13. package/dist/create/scaffolders/api-nestjs-graphql.js.map +1 -0
  14. package/dist/create/scaffolders/api-nestjs-rest.d.ts.map +1 -1
  15. package/dist/create/scaffolders/api-nestjs-rest.js +19 -2
  16. package/dist/create/scaffolders/api-nestjs-rest.js.map +1 -1
  17. package/dist/create/types.d.ts +3 -1
  18. package/dist/create/types.d.ts.map +1 -1
  19. package/package.json +1 -1
  20. package/templates/api-nestjs-graphql/.prettierrc +4 -0
  21. package/templates/api-nestjs-graphql/eslint.config.mjs +34 -0
  22. package/templates/api-nestjs-graphql/nest-cli.json +8 -0
  23. package/templates/api-nestjs-graphql/package.json +81 -0
  24. package/templates/api-nestjs-graphql/project.json +21 -0
  25. package/templates/api-nestjs-graphql/src/app.module.ts +21 -0
  26. package/templates/api-nestjs-graphql/src/common/entities/base.entity.ts +21 -0
  27. package/templates/api-nestjs-graphql/src/common/repositories/entity.repository.ts +21 -0
  28. package/templates/api-nestjs-graphql/src/common/repositories/readonly-entity.repository.ts +22 -0
  29. package/templates/api-nestjs-graphql/src/common/services/entity.service.ts +24 -0
  30. package/templates/api-nestjs-graphql/src/common/services/readonly-entity.service.ts +23 -0
  31. package/templates/api-nestjs-graphql/src/main.ts +8 -0
  32. package/templates/api-nestjs-graphql/src/modules/database/database.module.ts +18 -0
  33. package/templates/api-nestjs-graphql/src/modules/health/__tests__/health.controller.spec.ts +20 -0
  34. package/templates/api-nestjs-graphql/src/modules/health/__tests__/health.service.spec.ts +18 -0
  35. package/templates/api-nestjs-graphql/src/modules/health/health.controller.ts +12 -0
  36. package/templates/api-nestjs-graphql/src/modules/health/health.module.ts +9 -0
  37. package/templates/api-nestjs-graphql/src/modules/health/health.service.ts +8 -0
  38. package/templates/api-nestjs-graphql/test/app.e2e-spec.ts +29 -0
  39. package/templates/api-nestjs-graphql/test/jest-e2e.json +9 -0
  40. package/templates/api-nestjs-graphql/tsconfig.build.json +4 -0
  41. package/templates/api-nestjs-graphql/tsconfig.json +21 -0
  42. package/templates/api-nestjs-rest/package.json +5 -2
  43. package/templates/api-nestjs-rest/project.json +1 -1
  44. package/templates/api-nestjs-rest/src/app.module.ts +8 -5
  45. package/templates/api-nestjs-rest/src/common/entities/base.entity.ts +16 -0
  46. package/templates/api-nestjs-rest/src/common/repositories/entity.repository.ts +21 -0
  47. package/templates/api-nestjs-rest/src/common/repositories/readonly-entity.repository.ts +22 -0
  48. package/templates/api-nestjs-rest/src/common/services/entity.service.ts +24 -0
  49. package/templates/api-nestjs-rest/src/common/services/readonly-entity.service.ts +23 -0
  50. package/templates/api-nestjs-rest/src/modules/database/database.module.ts +18 -0
  51. package/templates/api-nestjs-rest/src/modules/health/__tests__/health.controller.spec.ts +20 -0
  52. package/templates/api-nestjs-rest/src/modules/health/__tests__/health.service.spec.ts +18 -0
  53. package/templates/api-nestjs-rest/src/modules/health/health.controller.ts +12 -0
  54. package/templates/api-nestjs-rest/src/modules/health/health.module.ts +9 -0
  55. package/templates/api-nestjs-rest/src/modules/health/health.service.ts +8 -0
  56. package/templates/api-nestjs-rest/test/app.e2e-spec.ts +9 -5
  57. package/templates/base/package.json +5 -1
  58. package/templates/base/pnpm-workspace.yaml +1 -0
  59. package/templates/base/tools/generators/controller/files/__fileName__.controller.ts__tmpl__ +36 -0
  60. package/templates/base/tools/generators/controller/index.js +22 -0
  61. package/templates/base/tools/generators/controller/schema.json +18 -0
  62. package/templates/base/tools/generators/generators.json +19 -0
  63. package/templates/base/tools/generators/module/files/__fileName__.model.ts__tmpl__ +8 -0
  64. package/templates/base/tools/generators/module/files/__fileName__.module.ts__tmpl__ +12 -0
  65. package/templates/base/tools/generators/module/files/__fileName__.repository.ts__tmpl__ +15 -0
  66. package/templates/base/tools/generators/module/files/__fileName__.service.ts__tmpl__ +11 -0
  67. package/templates/base/tools/generators/module/files/__tests__/__fileName__.integration.spec.ts__tmpl__ +31 -0
  68. package/templates/base/tools/generators/module/graphql-files/__fileName__.model.ts__tmpl__ +11 -0
  69. package/templates/base/tools/generators/module/index.js +26 -0
  70. package/templates/base/tools/generators/module/schema.json +23 -0
  71. package/templates/base/tools/generators/package.json +6 -0
  72. package/templates/base/tools/generators/resolver/files/__fileName__.resolver.ts__tmpl__ +28 -0
  73. package/templates/base/tools/generators/resolver/index.js +22 -0
  74. package/templates/base/tools/generators/resolver/schema.json +18 -0
  75. package/templates/web-nextjs/package.json +3 -0
  76. package/templates/web-nextjs/postcss.config.mjs +7 -0
  77. package/templates/web-nextjs/src/app/globals.css +1 -0
  78. package/templates/web-nextjs/src/components/TemplateComponent/TemplateComponent.behaviour.ts +39 -0
  79. package/templates/web-nextjs/src/components/TemplateComponent/TemplateComponent.tsx +14 -0
  80. package/templates/web-vite/package.json +2 -0
  81. package/templates/web-vite/src/components/TemplateComponent/TemplateComponent.behaviour.ts +39 -0
  82. package/templates/web-vite/src/components/TemplateComponent/TemplateComponent.tsx +14 -0
  83. package/templates/web-vite/src/index.css +1 -8
  84. package/templates/web-vite/vite.config.ts +3 -3
  85. package/templates/api-nestjs-rest/src/app.controller.spec.ts +0 -22
  86. package/templates/api-nestjs-rest/src/app.controller.ts +0 -12
  87. package/templates/api-nestjs-rest/src/app.service.ts +0 -8
  88. package/templates/web-nextjs/app/globals.css +0 -10
  89. /package/templates/web-nextjs/{app → src/app}/favicon.ico +0 -0
  90. /package/templates/web-nextjs/{app → src/app}/layout.tsx +0 -0
  91. /package/templates/web-nextjs/{app → src/app}/page.tsx +0 -0
@@ -0,0 +1,8 @@
1
+ import { NestFactory } from '@nestjs/core';
2
+ import { AppModule } from './app.module';
3
+
4
+ async function bootstrap() {
5
+ const app = await NestFactory.create(AppModule);
6
+ await app.listen(process.env.PORT ?? 3000);
7
+ }
8
+ bootstrap();
@@ -0,0 +1,18 @@
1
+ import { Module } from '@nestjs/common';
2
+ import { TypeOrmModule } from '@nestjs/typeorm';
3
+
4
+ @Module({
5
+ imports: [
6
+ TypeOrmModule.forRoot({
7
+ type: '{{dbType}}' as 'postgres' | 'mysql',
8
+ host: process.env.DB_HOST ?? 'localhost',
9
+ port: parseInt(process.env.DB_PORT ?? '{{dbPort}}', 10),
10
+ username: process.env.DB_USER ?? 'postgres',
11
+ password: process.env.DB_PASSWORD ?? '',
12
+ database: process.env.DB_NAME ?? '{{projectName}}',
13
+ entities: [],
14
+ synchronize: process.env.NODE_ENV !== 'production',
15
+ }),
16
+ ],
17
+ })
18
+ export class DatabaseModule {}
@@ -0,0 +1,20 @@
1
+ import { Test, TestingModule } from '@nestjs/testing';
2
+ import { HealthController } from './health.controller';
3
+ import { HealthService } from './health.service';
4
+
5
+ describe('HealthController', () => {
6
+ let controller: HealthController;
7
+
8
+ beforeEach(async () => {
9
+ const module: TestingModule = await Test.createTestingModule({
10
+ controllers: [HealthController],
11
+ providers: [HealthService],
12
+ }).compile();
13
+
14
+ controller = module.get<HealthController>(HealthController);
15
+ });
16
+
17
+ it('returns ok status', () => {
18
+ expect(controller.check()).toEqual({ status: 'ok' });
19
+ });
20
+ });
@@ -0,0 +1,18 @@
1
+ import { Test, TestingModule } from '@nestjs/testing';
2
+ import { HealthService } from './health.service';
3
+
4
+ describe('HealthService', () => {
5
+ let service: HealthService;
6
+
7
+ beforeEach(async () => {
8
+ const module: TestingModule = await Test.createTestingModule({
9
+ providers: [HealthService],
10
+ }).compile();
11
+
12
+ service = module.get<HealthService>(HealthService);
13
+ });
14
+
15
+ it('returns ok status', () => {
16
+ expect(service.check()).toEqual({ status: 'ok' });
17
+ });
18
+ });
@@ -0,0 +1,12 @@
1
+ import { Controller, Get } from '@nestjs/common';
2
+ import { HealthService } from './health.service';
3
+
4
+ @Controller('health')
5
+ export class HealthController {
6
+ constructor(private readonly healthService: HealthService) {}
7
+
8
+ @Get()
9
+ check() {
10
+ return this.healthService.check();
11
+ }
12
+ }
@@ -0,0 +1,9 @@
1
+ import { Module } from '@nestjs/common';
2
+ import { HealthController } from './health.controller';
3
+ import { HealthService } from './health.service';
4
+
5
+ @Module({
6
+ controllers: [HealthController],
7
+ providers: [HealthService],
8
+ })
9
+ export class HealthModule {}
@@ -0,0 +1,8 @@
1
+ import { Injectable } from '@nestjs/common';
2
+
3
+ @Injectable()
4
+ export class HealthService {
5
+ check() {
6
+ return { status: 'ok' };
7
+ }
8
+ }
@@ -0,0 +1,29 @@
1
+ import { INestApplication } from '@nestjs/common';
2
+ import { Test, TestingModule } from '@nestjs/testing';
3
+ import * as request from 'supertest';
4
+ import { App } from 'supertest/types';
5
+ import { AppModule } from './../src/app.module';
6
+
7
+ describe('App (e2e)', () => {
8
+ let app: INestApplication<App>;
9
+
10
+ beforeEach(async () => {
11
+ const moduleFixture: TestingModule = await Test.createTestingModule({
12
+ imports: [AppModule],
13
+ }).compile();
14
+
15
+ app = moduleFixture.createNestApplication();
16
+ await app.init();
17
+ });
18
+
19
+ afterEach(async () => {
20
+ await app.close();
21
+ });
22
+
23
+ it('/health (GET)', () => {
24
+ return request(app.getHttpServer())
25
+ .get('/health')
26
+ .expect(200)
27
+ .expect({ status: 'ok' });
28
+ });
29
+ });
@@ -0,0 +1,9 @@
1
+ {
2
+ "moduleFileExtensions": ["js", "json", "ts"],
3
+ "rootDir": ".",
4
+ "testEnvironment": "node",
5
+ "testRegex": ".e2e-spec.ts$",
6
+ "transform": {
7
+ "^.+\\.(t|j)s$": "ts-jest"
8
+ }
9
+ }
@@ -0,0 +1,4 @@
1
+ {
2
+ "extends": "./tsconfig.json",
3
+ "exclude": ["node_modules", "test", "dist", "**/*spec.ts"]
4
+ }
@@ -0,0 +1,21 @@
1
+ {
2
+ "compilerOptions": {
3
+ "module": "commonjs",
4
+ "declaration": true,
5
+ "removeComments": true,
6
+ "emitDecoratorMetadata": true,
7
+ "experimentalDecorators": true,
8
+ "allowSyntheticDefaultImports": true,
9
+ "target": "ES2023",
10
+ "sourceMap": true,
11
+ "outDir": "./dist",
12
+ "baseUrl": "./",
13
+ "incremental": true,
14
+ "skipLibCheck": true,
15
+ "strictNullChecks": true,
16
+ "forceConsistentCasingInFileNames": true,
17
+ "noImplicitAny": false,
18
+ "strictBindCallApply": false,
19
+ "noFallthroughCasesInSwitch": false
20
+ }
21
+ }
@@ -1,5 +1,5 @@
1
1
  {
2
- "name": "{{projectName}}-api",
2
+ "name": "{{projectName}}-backend",
3
3
  "version": "0.0.1",
4
4
  "description": "",
5
5
  "author": "",
@@ -22,10 +22,13 @@
22
22
  },
23
23
  "dependencies": {
24
24
  "@nestjs/common": "^11.0.1",
25
+ "@nestjs/config": "^3.0.0",
25
26
  "@nestjs/core": "^11.0.1",
26
27
  "@nestjs/platform-express": "^11.0.1",
28
+ "@nestjs/typeorm": "^10.0.0",
27
29
  "reflect-metadata": "^0.2.2",
28
- "rxjs": "^7.8.1"
30
+ "rxjs": "^7.8.1",
31
+ "typeorm": "^0.3.0"
29
32
  },
30
33
  "devDependencies": {
31
34
  "@eslint/eslintrc": "^3.2.0",
@@ -1,5 +1,5 @@
1
1
  {
2
- "name": "api",
2
+ "name": "backend",
3
3
  "targets": {
4
4
  "dev": {
5
5
  "executor": "nx:run-commands",
@@ -1,10 +1,13 @@
1
1
  import { Module } from '@nestjs/common';
2
- import { AppController } from './app.controller';
3
- import { AppService } from './app.service';
2
+ import { ConfigModule } from '@nestjs/config';
3
+ import { DatabaseModule } from './modules/database/database.module';
4
+ import { HealthModule } from './modules/health/health.module';
4
5
 
5
6
  @Module({
6
- imports: [],
7
- controllers: [AppController],
8
- providers: [AppService],
7
+ imports: [
8
+ ConfigModule.forRoot({ isGlobal: true }),
9
+ DatabaseModule,
10
+ HealthModule,
11
+ ],
9
12
  })
10
13
  export class AppModule {}
@@ -0,0 +1,16 @@
1
+ import {
2
+ CreateDateColumn,
3
+ PrimaryGeneratedColumn,
4
+ UpdateDateColumn,
5
+ } from 'typeorm';
6
+
7
+ export abstract class BaseEntity {
8
+ @PrimaryGeneratedColumn('uuid')
9
+ id: string;
10
+
11
+ @CreateDateColumn()
12
+ createdAt: Date;
13
+
14
+ @UpdateDateColumn()
15
+ updatedAt: Date;
16
+ }
@@ -0,0 +1,21 @@
1
+ import { DeepPartial } from 'typeorm';
2
+ import { BaseEntity } from '../entities/base.entity';
3
+ import { ReadonlyEntityRepository } from './readonly-entity.repository';
4
+
5
+ export abstract class EntityRepository<
6
+ T extends BaseEntity,
7
+ > extends ReadonlyEntityRepository<T> {
8
+ async create(data: DeepPartial<T>): Promise<T> {
9
+ const entity = this.repo.create(data);
10
+ return this.repo.save(entity);
11
+ }
12
+
13
+ async update(id: string, data: DeepPartial<T>): Promise<T> {
14
+ await this.repo.update(id, data as any);
15
+ return this.findById(id) as Promise<T>;
16
+ }
17
+
18
+ async remove(id: string): Promise<void> {
19
+ await this.repo.delete(id);
20
+ }
21
+ }
@@ -0,0 +1,22 @@
1
+ import { FindManyOptions, FindOptionsWhere, In, Repository } from 'typeorm';
2
+ import { BaseEntity } from '../entities/base.entity';
3
+
4
+ export abstract class ReadonlyEntityRepository<T extends BaseEntity> {
5
+ constructor(protected readonly repo: Repository<T>) {}
6
+
7
+ findAll(options?: FindManyOptions<T>): Promise<T[]> {
8
+ return this.repo.find(options);
9
+ }
10
+
11
+ findByIds(ids: string[]): Promise<T[]> {
12
+ return this.repo.findBy({ id: In(ids) } as FindOptionsWhere<T>);
13
+ }
14
+
15
+ findById(id: string): Promise<T | null> {
16
+ return this.repo.findOneBy({ id } as FindOptionsWhere<T>);
17
+ }
18
+
19
+ findOne(where: FindOptionsWhere<T>): Promise<T | null> {
20
+ return this.repo.findOneBy(where);
21
+ }
22
+ }
@@ -0,0 +1,24 @@
1
+ import { DeepPartial } from 'typeorm';
2
+ import { BaseEntity } from '../entities/base.entity';
3
+ import { EntityRepository } from '../repositories/entity.repository';
4
+ import { ReadonlyEntityService } from './readonly-entity.service';
5
+
6
+ export abstract class EntityService<
7
+ T extends BaseEntity,
8
+ > extends ReadonlyEntityService<T> {
9
+ constructor(protected readonly repository: EntityRepository<T>) {
10
+ super(repository);
11
+ }
12
+
13
+ create(data: DeepPartial<T>): Promise<T> {
14
+ return this.repository.create(data);
15
+ }
16
+
17
+ update(id: string, data: DeepPartial<T>): Promise<T> {
18
+ return this.repository.update(id, data);
19
+ }
20
+
21
+ remove(id: string): Promise<void> {
22
+ return this.repository.remove(id);
23
+ }
24
+ }
@@ -0,0 +1,23 @@
1
+ import { FindManyOptions, FindOptionsWhere } from 'typeorm';
2
+ import { BaseEntity } from '../entities/base.entity';
3
+ import { ReadonlyEntityRepository } from '../repositories/readonly-entity.repository';
4
+
5
+ export abstract class ReadonlyEntityService<T extends BaseEntity> {
6
+ constructor(protected readonly repository: ReadonlyEntityRepository<T>) {}
7
+
8
+ findAll(options?: FindManyOptions<T>): Promise<T[]> {
9
+ return this.repository.findAll(options);
10
+ }
11
+
12
+ findByIds(ids: string[]): Promise<T[]> {
13
+ return this.repository.findByIds(ids);
14
+ }
15
+
16
+ findById(id: string): Promise<T | null> {
17
+ return this.repository.findById(id);
18
+ }
19
+
20
+ findOne(where: FindOptionsWhere<T>): Promise<T | null> {
21
+ return this.repository.findOne(where);
22
+ }
23
+ }
@@ -0,0 +1,18 @@
1
+ import { Module } from '@nestjs/common';
2
+ import { TypeOrmModule } from '@nestjs/typeorm';
3
+
4
+ @Module({
5
+ imports: [
6
+ TypeOrmModule.forRoot({
7
+ type: '{{dbType}}' as 'postgres' | 'mysql',
8
+ host: process.env.DB_HOST ?? 'localhost',
9
+ port: parseInt(process.env.DB_PORT ?? '{{dbPort}}', 10),
10
+ username: process.env.DB_USER ?? 'postgres',
11
+ password: process.env.DB_PASSWORD ?? '',
12
+ database: process.env.DB_NAME ?? '{{projectName}}',
13
+ entities: [],
14
+ synchronize: process.env.NODE_ENV !== 'production',
15
+ }),
16
+ ],
17
+ })
18
+ export class DatabaseModule {}
@@ -0,0 +1,20 @@
1
+ import { Test, TestingModule } from '@nestjs/testing';
2
+ import { HealthController } from './health.controller';
3
+ import { HealthService } from './health.service';
4
+
5
+ describe('HealthController', () => {
6
+ let controller: HealthController;
7
+
8
+ beforeEach(async () => {
9
+ const module: TestingModule = await Test.createTestingModule({
10
+ controllers: [HealthController],
11
+ providers: [HealthService],
12
+ }).compile();
13
+
14
+ controller = module.get<HealthController>(HealthController);
15
+ });
16
+
17
+ it('returns ok status', () => {
18
+ expect(controller.check()).toEqual({ status: 'ok' });
19
+ });
20
+ });
@@ -0,0 +1,18 @@
1
+ import { Test, TestingModule } from '@nestjs/testing';
2
+ import { HealthService } from './health.service';
3
+
4
+ describe('HealthService', () => {
5
+ let service: HealthService;
6
+
7
+ beforeEach(async () => {
8
+ const module: TestingModule = await Test.createTestingModule({
9
+ providers: [HealthService],
10
+ }).compile();
11
+
12
+ service = module.get<HealthService>(HealthService);
13
+ });
14
+
15
+ it('returns ok status', () => {
16
+ expect(service.check()).toEqual({ status: 'ok' });
17
+ });
18
+ });
@@ -0,0 +1,12 @@
1
+ import { Controller, Get } from '@nestjs/common';
2
+ import { HealthService } from './health.service';
3
+
4
+ @Controller('health')
5
+ export class HealthController {
6
+ constructor(private readonly healthService: HealthService) {}
7
+
8
+ @Get()
9
+ check() {
10
+ return this.healthService.check();
11
+ }
12
+ }
@@ -0,0 +1,9 @@
1
+ import { Module } from '@nestjs/common';
2
+ import { HealthController } from './health.controller';
3
+ import { HealthService } from './health.service';
4
+
5
+ @Module({
6
+ controllers: [HealthController],
7
+ providers: [HealthService],
8
+ })
9
+ export class HealthModule {}
@@ -0,0 +1,8 @@
1
+ import { Injectable } from '@nestjs/common';
2
+
3
+ @Injectable()
4
+ export class HealthService {
5
+ check() {
6
+ return { status: 'ok' };
7
+ }
8
+ }
@@ -1,10 +1,10 @@
1
- import { Test, TestingModule } from '@nestjs/testing';
2
1
  import { INestApplication } from '@nestjs/common';
2
+ import { Test, TestingModule } from '@nestjs/testing';
3
3
  import * as request from 'supertest';
4
4
  import { App } from 'supertest/types';
5
5
  import { AppModule } from './../src/app.module';
6
6
 
7
- describe('AppController (e2e)', () => {
7
+ describe('App (e2e)', () => {
8
8
  let app: INestApplication<App>;
9
9
 
10
10
  beforeEach(async () => {
@@ -16,10 +16,14 @@ describe('AppController (e2e)', () => {
16
16
  await app.init();
17
17
  });
18
18
 
19
- it('/ (GET)', () => {
19
+ afterEach(async () => {
20
+ await app.close();
21
+ });
22
+
23
+ it('/health (GET)', () => {
20
24
  return request(app.getHttpServer())
21
- .get('/')
25
+ .get('/health')
22
26
  .expect(200)
23
- .expect('Hello World!');
27
+ .expect({ status: 'ok' });
24
28
  });
25
29
  });
@@ -6,9 +6,13 @@
6
6
  "dev": "nx run-many -t dev",
7
7
  "build": "nx run-many -t build",
8
8
  "test": "nx run-many -t test",
9
- "lint": "nx run-many -t lint"
9
+ "lint": "nx run-many -t lint",
10
+ "generate:module": "nx g @local/generators:module",
11
+ "generate:resolver": "nx g @local/generators:resolver",
12
+ "generate:controller": "nx g @local/generators:controller"
10
13
  },
11
14
  "devDependencies": {
15
+ "@nx/devkit": "^20.0.0",
12
16
  "nx": "^20.0.0"
13
17
  }
14
18
  }
@@ -1,3 +1,4 @@
1
1
  packages:
2
2
  - 'apps/*'
3
3
  - 'packages/*' # shared code: graphql types, ui components, etc.
4
+ - 'tools/generators'
@@ -0,0 +1,36 @@
1
+ import {
2
+ Controller,
3
+ Delete,
4
+ Get,
5
+ Param,
6
+ ParseUUIDPipe,
7
+ Query,
8
+ } from '@nestjs/common';
9
+ import { FindManyOptions } from 'typeorm';
10
+ import { <%= className %>Model } from '../../modules/<%= fileName %>/<%= fileName %>.model';
11
+ import { <%= className %>Service } from '../../modules/<%= fileName %>/<%= fileName %>.service';
12
+
13
+ @Controller('<%= fileName %>s')
14
+ export class <%= className %>Controller {
15
+ constructor(private readonly service: <%= className %>Service) {}
16
+
17
+ @Get()
18
+ findAll(@Query() query: FindManyOptions<<%= className %>Model>) {
19
+ return this.service.findAll(query);
20
+ }
21
+
22
+ @Get('by-ids')
23
+ findByIds(@Query('ids') ids: string) {
24
+ return this.service.findByIds(ids.split(','));
25
+ }
26
+
27
+ @Get(':id')
28
+ findById(@Param('id', ParseUUIDPipe) id: string) {
29
+ return this.service.findById(id);
30
+ }
31
+
32
+ @Delete(':id')
33
+ remove(@Param('id', ParseUUIDPipe) id: string) {
34
+ return this.service.remove(id);
35
+ }
36
+ }
@@ -0,0 +1,22 @@
1
+ const { formatFiles, generateFiles, names } = require('@nx/devkit');
2
+ const { execSync } = require('node:child_process');
3
+ const { join } = require('node:path');
4
+
5
+ module.exports = async function (tree, options) {
6
+ const n = names(options.name);
7
+ const controllerPath = `apps/backend/src/api/${n.fileName}`;
8
+
9
+ generateFiles(tree, join(__dirname, 'files'), controllerPath, { ...n, tmpl: '' });
10
+
11
+ await formatFiles(tree);
12
+
13
+ console.log(`\n✓ Controller created at ${controllerPath}/`);
14
+ console.log(` → Import ${n.className}Module and register ${n.className}Controller in your module\n`);
15
+
16
+ return () => {
17
+ execSync(`npx prettier --write ${controllerPath}`, {
18
+ cwd: tree.root,
19
+ stdio: 'inherit',
20
+ });
21
+ };
22
+ };
@@ -0,0 +1,18 @@
1
+ {
2
+ "$schema": "http://json-schema.org/schema",
3
+ "cli": "nx",
4
+ "id": "controller",
5
+ "title": "Create a REST controller",
6
+ "type": "object",
7
+ "properties": {
8
+ "name": {
9
+ "type": "string",
10
+ "description": "Module name to generate a controller for (e.g. trainer)",
11
+ "$default": {
12
+ "$source": "argv",
13
+ "index": 0
14
+ }
15
+ }
16
+ },
17
+ "required": ["name"]
18
+ }
@@ -0,0 +1,19 @@
1
+ {
2
+ "generators": {
3
+ "module": {
4
+ "factory": "./module/index",
5
+ "schema": "./module/schema.json",
6
+ "description": "Create a NestJS domain module (model, repository, service)"
7
+ },
8
+ "resolver": {
9
+ "factory": "./resolver/index",
10
+ "schema": "./resolver/schema.json",
11
+ "description": "Create a GraphQL resolver in src/resolvers/"
12
+ },
13
+ "controller": {
14
+ "factory": "./controller/index",
15
+ "schema": "./controller/schema.json",
16
+ "description": "Create a REST controller in src/api/"
17
+ }
18
+ }
19
+ }
@@ -0,0 +1,8 @@
1
+ import { Column, Entity } from 'typeorm';
2
+ import { BaseEntity } from '../../common/entities/base.entity';
3
+
4
+ @Entity('<%= fileName %>s')
5
+ export class <%= className %>Model extends BaseEntity {
6
+ // @Column()
7
+ // name: string;
8
+ }
@@ -0,0 +1,12 @@
1
+ import { Module } from '@nestjs/common';
2
+ import { TypeOrmModule } from '@nestjs/typeorm';
3
+ import { <%= className %>Model } from './<%= fileName %>.model';
4
+ import { <%= className %>Repository } from './<%= fileName %>.repository';
5
+ import { <%= className %>Service } from './<%= fileName %>.service';
6
+
7
+ @Module({
8
+ imports: [TypeOrmModule.forFeature([<%= className %>Model])],
9
+ providers: [<%= className %>Service, <%= className %>Repository],
10
+ exports: [<%= className %>Service, <%= className %>Repository],
11
+ })
12
+ export class <%= className %>Module {}
@@ -0,0 +1,15 @@
1
+ import { Injectable } from '@nestjs/common';
2
+ import { InjectRepository } from '@nestjs/typeorm';
3
+ import { Repository } from 'typeorm';
4
+ import { EntityRepository } from '../../common/repositories/entity.repository';
5
+ import { <%= className %>Model } from './<%= fileName %>.model';
6
+
7
+ @Injectable()
8
+ export class <%= className %>Repository extends EntityRepository<<%= className %>Model> {
9
+ constructor(
10
+ @InjectRepository(<%= className %>Model)
11
+ repo: Repository<<%= className %>Model>,
12
+ ) {
13
+ super(repo);
14
+ }
15
+ }
@@ -0,0 +1,11 @@
1
+ import { Injectable } from '@nestjs/common';
2
+ import { EntityService } from '../../common/services/entity.service';
3
+ import { <%= className %>Model } from './<%= fileName %>.model';
4
+ import { <%= className %>Repository } from './<%= fileName %>.repository';
5
+
6
+ @Injectable()
7
+ export class <%= className %>Service extends EntityService<<%= className %>Model> {
8
+ constructor(repository: <%= className %>Repository) {
9
+ super(repository);
10
+ }
11
+ }