@avleon/cli 0.0.6 → 0.0.27
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/avcli.js +26 -0
- package/dist/cli.js +24 -55
- package/dist/controller.js +106 -101
- package/dist/create.js +82 -50
- package/dist/helpers/file-helper.js +21 -0
- package/dist/helpers/path-helper.js +21 -0
- package/dist/paths.js +12 -1
- package/package.json +16 -8
- package/pnpm-workspace.yaml +2 -0
- package/stubs/app/app-controller.stub +11 -0
- package/stubs/app/app-minimal.stub +17 -0
- package/stubs/config.stub +11 -0
- package/stubs/controllers/basic-controller.stub +12 -0
- package/stubs/controllers/rest-controller.stub +32 -0
- package/stubs/model.stub +0 -0
- package/stubs/models/basic-model.stub +6 -0
- package/stubs/models/entity-model.stub +23 -0
- package/stubs/serve.stub +10 -0
- package/stubs/services/basic-service.stub +8 -0
- package/stubs/services/rest-service.stub +34 -0
- package/tsconfig.json +2 -2
- package/src/av-cli.ts +0 -95
- package/src/cli.interface.ts +0 -55
- package/src/cli.ts +0 -241
- package/src/commands.ts +0 -56
- package/src/controller.ts +0 -106
- package/src/create.ts +0 -145
- package/src/index.ts +0 -1
- package/src/paths.ts +0 -29
- /package/{src/stubs/model.stub → stubs/app/app-withdb.stub} +0 -0
- /package/{src/stubs → stubs}/basic-controller.stub +0 -0
package/package.json
CHANGED
|
@@ -1,35 +1,43 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@avleon/cli",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.27",
|
|
4
4
|
"bin": {
|
|
5
|
-
"avleon": "./dist/cli.js"
|
|
5
|
+
"avleon": "./dist/cli.js",
|
|
6
|
+
"av":"./dist/cli.js"
|
|
6
7
|
},
|
|
7
8
|
"description": "",
|
|
8
9
|
"main": "dist/index.js",
|
|
9
10
|
"types": "dist/index.d.ts",
|
|
10
11
|
"scripts": {
|
|
11
|
-
"build": "tsc",
|
|
12
|
+
"build": "rimraf dist & tsc",
|
|
12
13
|
"clean": "rm -rf ./dist",
|
|
13
14
|
"watch": "tsc-watch"
|
|
14
15
|
},
|
|
15
|
-
"keywords": [
|
|
16
|
+
"keywords": [
|
|
17
|
+
"cli",
|
|
18
|
+
"backend-api"
|
|
19
|
+
],
|
|
16
20
|
"author": "Tareq Hossain",
|
|
17
21
|
"license": "ISC",
|
|
18
22
|
"devDependencies": {
|
|
19
23
|
"@types/fs-extra": "^11.0.4",
|
|
24
|
+
"@types/lodash": "^4.17.16",
|
|
20
25
|
"@types/node": "^22.9.3",
|
|
21
26
|
"nodemon": "^3.1.7",
|
|
22
27
|
"tsc-watch": "^6.2.1",
|
|
28
|
+
"tsup": "^8.4.0",
|
|
23
29
|
"typescript": "^5.7.2"
|
|
24
30
|
},
|
|
25
31
|
"dependencies": {
|
|
26
|
-
"chalk": "^4",
|
|
27
|
-
"prettier": "^3.3.3",
|
|
32
|
+
"chalk": "^5.4.1",
|
|
28
33
|
"cli-table3": "^0.6.5",
|
|
29
|
-
"fs-extra": "^11.2.0"
|
|
34
|
+
"fs-extra": "^11.2.0",
|
|
35
|
+
"lodash": "^4.17.21",
|
|
36
|
+
"prettier": "^3.3.3",
|
|
37
|
+
"rimraf": "^6.0.1"
|
|
30
38
|
},
|
|
31
39
|
"repository": {
|
|
32
40
|
"type": "git",
|
|
33
41
|
"url": "git+https://github.com/avleonjs/avleon-cli"
|
|
34
42
|
}
|
|
35
|
-
}
|
|
43
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { Builder, AppConfig } from '@avleon/core';
|
|
2
|
+
import { HomeController } from './controllers/home.controller';
|
|
3
|
+
|
|
4
|
+
const builder = Builder.createAppBuilder();
|
|
5
|
+
|
|
6
|
+
const app = builder.build();
|
|
7
|
+
app.useOpenApi((config:AppConfig)=> config.openApi);
|
|
8
|
+
app.useControllers([HomeController]);
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
app.run();
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import { Builder, AppConfig } from '@avleon/core';
|
|
2
|
+
const builder = Builder.createAppBuilder();
|
|
3
|
+
|
|
4
|
+
builder.services.addOpenApi();
|
|
5
|
+
builder.services.addServices();
|
|
6
|
+
builder.services.addAuthentication();
|
|
7
|
+
builder.servicse.addControllers();
|
|
8
|
+
const app = builder.build();
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
|
|
12
|
+
if(app.isDevelopment()){
|
|
13
|
+
app.useOpenApi((config:AppConfig)=> config.openApi);
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
app.mapGet('/', () => "Hello World!");
|
|
17
|
+
export default app;
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { ApiController, Get, Post, Update, Delete, Param, Body, HttpResponse } from '@avleon/core';
|
|
2
|
+
|
|
3
|
+
|
|
4
|
+
@ApiController('/{controller}s')
|
|
5
|
+
export class {Controller}{
|
|
6
|
+
|
|
7
|
+
@Get()
|
|
8
|
+
index(){
|
|
9
|
+
return HttpResponse.Ok("{Controller}");
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
@Get('/:id')
|
|
13
|
+
findOne(@Param('id') id:{pktype}){
|
|
14
|
+
return HttpResponse.Ok(`Item found with id:${id}`);
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
@Post()
|
|
18
|
+
create(@Body() body:{bodyType}){
|
|
19
|
+
return HttpResponse.Ok("Created");
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
@Update('/:id')
|
|
23
|
+
update(@Param('id') id:{pktype}, updateBody:{updateBodyType}){
|
|
24
|
+
return HttpResponse.Ok(`Item updated with id:${id}`)
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
@Delete('/:id')
|
|
28
|
+
delete(@Param('id') id:{pktype}){
|
|
29
|
+
return HttpResponse.Ok(`Item delted with id:${id}`)
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
}
|
package/stubs/model.stub
ADDED
|
File without changes
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
|
|
2
|
+
import {Entity, PrimaryGeneratedColumn, Column, CreateDateColumn, UpdateDateColumn} from 'typeorm';
|
|
3
|
+
|
|
4
|
+
@Entity({name:"{Model}"})
|
|
5
|
+
export class {Model}{
|
|
6
|
+
|
|
7
|
+
@PrimaryGeneratedColumn()
|
|
8
|
+
id:number;
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
// your fields
|
|
12
|
+
|
|
13
|
+
// @Column()
|
|
14
|
+
// name:string
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
@CreateDateColumn()
|
|
18
|
+
createdAt: Date;
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
@UpdateDateColumn()
|
|
22
|
+
updatedAt: Date;
|
|
23
|
+
}
|
package/stubs/serve.stub
ADDED
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { AppService, Collection } from '@avleon/core';
|
|
2
|
+
|
|
3
|
+
@AppService
|
|
4
|
+
export class {Service}{
|
|
5
|
+
|
|
6
|
+
constructor(
|
|
7
|
+
private readonly {modelRepository}:Collection.fromRepository({Model})
|
|
8
|
+
)
|
|
9
|
+
|
|
10
|
+
findAll(options?:any){
|
|
11
|
+
if(options && options.page){
|
|
12
|
+
return this.{modelRepository}.paginate(options.page)
|
|
13
|
+
}
|
|
14
|
+
return this.{modelRepository}.find();
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
findOne(id:{pktype}){
|
|
18
|
+
return this.{modelRepository}.findOne({where:{id}}) ;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
create(createBody:{createBodyType}){
|
|
22
|
+
const newItem = this.{modelRepository}.create();
|
|
23
|
+
return await this.{modelRepository}.save();
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
update(id:{pktype}, updateBody:{updateBodyType}){
|
|
27
|
+
return this.{modelRepository}.update({id}, updateBody);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
delete(id:{pktype}){
|
|
31
|
+
return this.modelRepository.delete({id});
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
}
|
package/tsconfig.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"compilerOptions": {
|
|
3
|
-
"target": "
|
|
3
|
+
"target": "ES2021",
|
|
4
4
|
"module": "CommonJS",
|
|
5
5
|
"moduleResolution": "node",
|
|
6
6
|
"outDir": "./dist",
|
|
@@ -10,6 +10,6 @@
|
|
|
10
10
|
"forceConsistentCasingInFileNames": true,
|
|
11
11
|
"skipLibCheck": true
|
|
12
12
|
},
|
|
13
|
-
"include": ["src/**/*"],
|
|
13
|
+
"include": ["src/**/*", "src/stubs"],
|
|
14
14
|
"exclude": ["node_modules", "dist"]
|
|
15
15
|
}
|
package/src/av-cli.ts
DELETED
|
@@ -1,95 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
import { AvCli, CreateModelOptions } from "./cli.interface";
|
|
3
|
-
import { commandList, CommandType } from "./commands";
|
|
4
|
-
|
|
5
|
-
type ProjectFileType =
|
|
6
|
-
| "controller"
|
|
7
|
-
| "service"
|
|
8
|
-
| "model"
|
|
9
|
-
| "util"
|
|
10
|
-
| "helper"
|
|
11
|
-
| "config";
|
|
12
|
-
|
|
13
|
-
interface FilePathExtractor {
|
|
14
|
-
name: string;
|
|
15
|
-
ext?: string;
|
|
16
|
-
parent: string;
|
|
17
|
-
givenPath: string;
|
|
18
|
-
outputPath?: string;
|
|
19
|
-
newFileName: string;
|
|
20
|
-
className: string;
|
|
21
|
-
exsits: boolean;
|
|
22
|
-
force: boolean;
|
|
23
|
-
fileType?: ProjectFileType;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
function formatFileName(name: string) {
|
|
27
|
-
return name
|
|
28
|
-
.replace(/[_\s]+/g, "-")
|
|
29
|
-
.replace(/([a-z])([A-Z])/g, "$1-$2")
|
|
30
|
-
.replace(
|
|
31
|
-
/((-|_|\.)+(Controller|Service|Model))|(Controller|Service|Model)/gi,
|
|
32
|
-
"",
|
|
33
|
-
)
|
|
34
|
-
.toLowerCase();
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
function formatClassName(name: string) {
|
|
38
|
-
return name
|
|
39
|
-
.replace(/[_\s-]+/g, " ")
|
|
40
|
-
.replace(/([a-z])([A-Z])/g, "$1 $2")
|
|
41
|
-
.toLowerCase()
|
|
42
|
-
.replace(/\b\w/g, (char) => char.toUpperCase())
|
|
43
|
-
.replace(/\s+/g, "");
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
export function PathExtractor(givenPath: string, options: string[]) {
|
|
47
|
-
let pathSplits = givenPath.split("/");
|
|
48
|
-
let splitSize = pathSplits.length;
|
|
49
|
-
let hasSubDirectory = splitSize > 0;
|
|
50
|
-
let name = hasSubDirectory ? pathSplits[splitSize - 1] : pathSplits[0];
|
|
51
|
-
let className = formatClassName(name);
|
|
52
|
-
let fileType = "any";
|
|
53
|
-
let isRest = false;
|
|
54
|
-
let isForced = false;
|
|
55
|
-
if (options.includes("make:controller") || options.includes("m:c")) {
|
|
56
|
-
fileType = "controller";
|
|
57
|
-
className = name.toLowerCase().replace(/controller|Controller/g, "");
|
|
58
|
-
}
|
|
59
|
-
if (options.includes("make:model") || options.includes("m:m")) {
|
|
60
|
-
fileType = "model";
|
|
61
|
-
className = name.toLowerCase().replace(/controller|Controller/g, "");
|
|
62
|
-
}
|
|
63
|
-
|
|
64
|
-
if (options.includes("make:service") || options.includes("m:s")) {
|
|
65
|
-
fileType = "service";
|
|
66
|
-
className = name.toLowerCase().replace(/controller|Controller/g, "");
|
|
67
|
-
}
|
|
68
|
-
|
|
69
|
-
if (options.includes("make:util") || options.includes("m:u")) {
|
|
70
|
-
fileType = "util";
|
|
71
|
-
className = name.toLowerCase().replace(/controller|Controller/g, "");
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
if (options.includes("make:config")) {
|
|
75
|
-
fileType = "config";
|
|
76
|
-
className = name.toLowerCase().replace(/controller|Controller/g, "");
|
|
77
|
-
}
|
|
78
|
-
|
|
79
|
-
if (options.includes("--rest") || options.includes("-r")) {
|
|
80
|
-
isRest = true;
|
|
81
|
-
className = name.toLowerCase().replace(/controller|Controller/g, "");
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
if (options.includes("--force") || options.includes("-f")) {
|
|
85
|
-
isForced = true;
|
|
86
|
-
className = name.toLowerCase().replace(/controller|Controller/g, "");
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
let outputFileName = formatFileName(name);
|
|
90
|
-
|
|
91
|
-
let outputPath = givenPath + "." + fileType + ".ts";
|
|
92
|
-
|
|
93
|
-
return {};
|
|
94
|
-
}
|
|
95
|
-
|
package/src/cli.interface.ts
DELETED
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
import { CommandType } from "./commands";
|
|
2
|
-
|
|
3
|
-
export interface AvCli {
|
|
4
|
-
commands: CommandType[];
|
|
5
|
-
|
|
6
|
-
createModel(): void;
|
|
7
|
-
createService(): void;
|
|
8
|
-
createController(): void;
|
|
9
|
-
createProject(): void;
|
|
10
|
-
createResource(): void;
|
|
11
|
-
createRestService(): void;
|
|
12
|
-
createRestController(): void;
|
|
13
|
-
displayHelp(): void;
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
type BaseBuildOptions = {
|
|
17
|
-
force: boolean;
|
|
18
|
-
};
|
|
19
|
-
|
|
20
|
-
export type CreateModelOptions = {
|
|
21
|
-
orm: boolean; //default false
|
|
22
|
-
timestamps: boolean; // timestamp true
|
|
23
|
-
fields: any;
|
|
24
|
-
} & BaseBuildOptions;
|
|
25
|
-
|
|
26
|
-
export type CreateControllerOptions = {
|
|
27
|
-
service: Function;
|
|
28
|
-
model: Function;
|
|
29
|
-
rest: boolean;
|
|
30
|
-
} & BaseBuildOptions;
|
|
31
|
-
|
|
32
|
-
export type CreateServiceOptions = {
|
|
33
|
-
model: Function;
|
|
34
|
-
rest: boolean;
|
|
35
|
-
orm: boolean;
|
|
36
|
-
} & BaseBuildOptions;
|
|
37
|
-
|
|
38
|
-
export type CreateApplicationOptions = {
|
|
39
|
-
orm: boolean;
|
|
40
|
-
minimal: boolean;
|
|
41
|
-
} & BaseBuildOptions;
|
|
42
|
-
|
|
43
|
-
export interface IBuilder {
|
|
44
|
-
content: string;
|
|
45
|
-
parse(content: string): IBuilder;
|
|
46
|
-
process(content: string): IBuilder;
|
|
47
|
-
format(content: string, parseOptions: any): IBuilder;
|
|
48
|
-
build(): string;
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
export interface ModelBuilder extends IBuilder {}
|
|
52
|
-
export interface ProjectBuilder extends IBuilder {}
|
|
53
|
-
export interface ControllerBuilder extends IBuilder {}
|
|
54
|
-
export interface ServiceBuilder extends IBuilder {}
|
|
55
|
-
export interface ResourceBuilder extends IBuilder {}
|
package/src/cli.ts
DELETED
|
@@ -1,241 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
import Table, { HorizontalTableRow } from "cli-table3";
|
|
3
|
-
import path from "path";
|
|
4
|
-
import fs from "fs/promises";
|
|
5
|
-
import fsExtra from 'fs-extra';
|
|
6
|
-
import { existsSync } from "fs";
|
|
7
|
-
import * as prettier from "prettier";
|
|
8
|
-
import chalk from "chalk";
|
|
9
|
-
import { createController } from "./controller";
|
|
10
|
-
import { commandList } from "./commands";
|
|
11
|
-
import { exec, execSync } from "child_process";
|
|
12
|
-
import { createApplication } from "./create";
|
|
13
|
-
|
|
14
|
-
export function iqraCli() { }
|
|
15
|
-
|
|
16
|
-
const listedCommands = commandList.flatMap(x => x.Command).concat(commandList.flatMap(x => x.Alias.split(","))).flatMap(a => a.trim());
|
|
17
|
-
|
|
18
|
-
/**
|
|
19
|
-
* @description Displaying basic info
|
|
20
|
-
* @since v0.0.2
|
|
21
|
-
* */
|
|
22
|
-
async function printLogo() {
|
|
23
|
-
try {
|
|
24
|
-
const packageInfo = await fs.readFile(
|
|
25
|
-
path.join(__dirname, "../package.json"),
|
|
26
|
-
"utf8",
|
|
27
|
-
);
|
|
28
|
-
const parsedPackInfo = JSON.parse(packageInfo);
|
|
29
|
-
console.log(`Name: Avleon CLI`, "\r");
|
|
30
|
-
console.log(`Version: ${parsedPackInfo.version}`, "\r");
|
|
31
|
-
} catch (error) {
|
|
32
|
-
throw new Error("Can't read packag info");
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
|
|
36
|
-
async function displayCommandList(info = { logo: true, all: false }) {
|
|
37
|
-
if (info.logo) {
|
|
38
|
-
await printLogo();
|
|
39
|
-
}
|
|
40
|
-
console.log("Available commandList:");
|
|
41
|
-
|
|
42
|
-
if (info.all) {
|
|
43
|
-
const table = new Table({
|
|
44
|
-
head: ["Command", "Alias", "Available Options", "Description"],
|
|
45
|
-
colWidths: [20, 10, 30, 50],
|
|
46
|
-
wrapOnWordBoundary: true,
|
|
47
|
-
wordWrap: true,
|
|
48
|
-
});
|
|
49
|
-
commandList.forEach((c) => {
|
|
50
|
-
table.push([c.Command, c.Alias, c.Options, c.Description]);
|
|
51
|
-
});
|
|
52
|
-
console.log(table.toString());
|
|
53
|
-
} else {
|
|
54
|
-
const table = new Table({
|
|
55
|
-
head: ["Command", "Alias", "Available Options"],
|
|
56
|
-
colWidths: [20, 10, 50],
|
|
57
|
-
wrapOnWordBoundary: true,
|
|
58
|
-
wordWrap: true,
|
|
59
|
-
});
|
|
60
|
-
commandList.forEach((c) => {
|
|
61
|
-
table.push([c.Command, c.Alias, c.Options]);
|
|
62
|
-
});
|
|
63
|
-
console.log(table.toString());
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
async function createModel(name: string, options = { force: false }) {
|
|
69
|
-
if (!name) {
|
|
70
|
-
throw new Error(
|
|
71
|
-
"Model name not found . use --name or node artisan make:model ModelName",
|
|
72
|
-
);
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
const modelFolderExists = existsSync(
|
|
76
|
-
path.join(process.cwd(), "./src/models"),
|
|
77
|
-
);
|
|
78
|
-
if (!modelFolderExists) {
|
|
79
|
-
await fs.mkdir(path.join(process.cwd(), "./src/models"), {
|
|
80
|
-
recursive: true,
|
|
81
|
-
});
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
const modelName = name.at(0).toUpperCase() + name.slice(1);
|
|
85
|
-
const modelExists = existsSync(
|
|
86
|
-
path.join(process.cwd(), `./src/models/${modelName.toLowerCase()}.ts`),
|
|
87
|
-
);
|
|
88
|
-
|
|
89
|
-
if (modelExists && !options.force) {
|
|
90
|
-
console.log(
|
|
91
|
-
chalk.bold(chalk.red("Model already exists!")),
|
|
92
|
-
chalk.greenBright("Use -f or --force to overwrite.\r"),
|
|
93
|
-
);
|
|
94
|
-
return;
|
|
95
|
-
}
|
|
96
|
-
|
|
97
|
-
const model = `
|
|
98
|
-
import {Entity, PrimaryGeneratedColumn, CreateDateColumn, UpdateDateColumn } from 'typeorm';
|
|
99
|
-
\t
|
|
100
|
-
@Entity({name:'${modelName}'})
|
|
101
|
-
export class ${modelName}{
|
|
102
|
-
|
|
103
|
-
@PrimaryGeneratedColumn()
|
|
104
|
-
id:number;
|
|
105
|
-
|
|
106
|
-
@CreateDateColumn()
|
|
107
|
-
createdAt: Date;
|
|
108
|
-
|
|
109
|
-
@UpdateDateColumn()
|
|
110
|
-
updatedAt: Date;
|
|
111
|
-
}
|
|
112
|
-
`;
|
|
113
|
-
|
|
114
|
-
const formatModel = await prettier.format(model, {
|
|
115
|
-
singleQuote: true,
|
|
116
|
-
singleAttributePerLine: true,
|
|
117
|
-
parser: "typescript",
|
|
118
|
-
});
|
|
119
|
-
|
|
120
|
-
await fs.writeFile(
|
|
121
|
-
path.join(process.cwd(), "./src/models/" + modelName.toLowerCase() + ".ts"),
|
|
122
|
-
formatModel,
|
|
123
|
-
);
|
|
124
|
-
|
|
125
|
-
console.log("Model created succssessfully!");
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
async function createXApplication(fname: string) {
|
|
129
|
-
if (existsSync(process.cwd() + fname)) {
|
|
130
|
-
throw new Error("Application already exists");
|
|
131
|
-
}
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
const projectPath = path.join(process.cwd(), fname);
|
|
135
|
-
const templateDir = path.resolve("D:\\projects\\node\\iqra\\packages\\cli\\src\\stubs");
|
|
136
|
-
|
|
137
|
-
//await fs.mkdir(projectPath);
|
|
138
|
-
|
|
139
|
-
//await fsExtra.copy(templateDir, projectPath + '/');
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
// Define project path
|
|
143
|
-
// const projectPath = path.resolve('new_test');
|
|
144
|
-
|
|
145
|
-
// Clone the repository and move the required folder
|
|
146
|
-
const cloneCommand = `
|
|
147
|
-
git clone -n --depth=1 --filter=tree:0 https://github.com/xtareq/iqra temp_repo &&
|
|
148
|
-
cd temp_repo &&
|
|
149
|
-
git sparse-checkout init --no-cone &&
|
|
150
|
-
git sparse-checkout set examples/iqra_test &&
|
|
151
|
-
git checkout &&
|
|
152
|
-
mv examples/iqra_test ${projectPath} &&
|
|
153
|
-
cd ..
|
|
154
|
-
`;
|
|
155
|
-
|
|
156
|
-
try {
|
|
157
|
-
// Execute the cloning and moving process
|
|
158
|
-
console.log('Cloning and setting up the repository...');
|
|
159
|
-
exec(cloneCommand, {});
|
|
160
|
-
|
|
161
|
-
// Check if the projectPath exists before proceeding
|
|
162
|
-
if (!fsExtra.existsSync(projectPath)) {
|
|
163
|
-
throw new Error(`Project path "${projectPath}" was not created.`);
|
|
164
|
-
}
|
|
165
|
-
|
|
166
|
-
// Remove the Git origin from the new project
|
|
167
|
-
console.log('Removing Git origin...');
|
|
168
|
-
execSync(`cd ${projectPath} && git remote remove origin`, { stdio: 'inherit' });
|
|
169
|
-
|
|
170
|
-
// Clean up the temporary repository
|
|
171
|
-
console.log('Cleaning up temporary files...');
|
|
172
|
-
fsExtra.removeSync('./temp_repo');
|
|
173
|
-
|
|
174
|
-
console.log(`Project created successfully in ${projectPath}`);
|
|
175
|
-
} catch (error) {
|
|
176
|
-
console.error('An error occurred:', error);
|
|
177
|
-
|
|
178
|
-
// Cleanup in case of failure
|
|
179
|
-
if (fsExtra.existsSync('./temp_repo')) {
|
|
180
|
-
console.log('Cleaning up temporary repository...');
|
|
181
|
-
fsExtra.removeSync('./temp_repo');
|
|
182
|
-
}
|
|
183
|
-
if (fsExtra.existsSync(projectPath)) {
|
|
184
|
-
console.log('Cleaning up project path...');
|
|
185
|
-
fsExtra.removeSync(projectPath);
|
|
186
|
-
}
|
|
187
|
-
}
|
|
188
|
-
|
|
189
|
-
}
|
|
190
|
-
|
|
191
|
-
export async function run() {
|
|
192
|
-
try {
|
|
193
|
-
const args = process.argv.slice(2);
|
|
194
|
-
if (args.length < 1) {
|
|
195
|
-
await displayCommandList({ logo: true, all: false });
|
|
196
|
-
} else {
|
|
197
|
-
const cmdList = commandList
|
|
198
|
-
.flatMap((x) => x.Command)
|
|
199
|
-
.concat(
|
|
200
|
-
...commandList.flatMap((f) => f.Alias.split(",").map((s) => s.trim())),
|
|
201
|
-
);
|
|
202
|
-
if (!listedCommands.includes(args[0].trim())) {
|
|
203
|
-
console.error("Invalid command");
|
|
204
|
-
await displayCommandList({ logo: false, all: false });
|
|
205
|
-
} else {
|
|
206
|
-
let force = false;
|
|
207
|
-
if (args.some((x) => x == "-f" || x == "--force")) {
|
|
208
|
-
force = true;
|
|
209
|
-
}
|
|
210
|
-
if (args[0] == "new") {
|
|
211
|
-
const fname = args[1];
|
|
212
|
-
await createApplication(fname);
|
|
213
|
-
}
|
|
214
|
-
if (args[0] == "make:model") {
|
|
215
|
-
await createModel(args[1], { force });
|
|
216
|
-
}
|
|
217
|
-
if (args[0] == "make:controller" || args[0] == "m:c") {
|
|
218
|
-
let resource = false;
|
|
219
|
-
if (args.some((x) => x == "-r" || x == "--resource")) {
|
|
220
|
-
resource = true;
|
|
221
|
-
}
|
|
222
|
-
let model = null;
|
|
223
|
-
if (args.some((x) => x == "-m" || x == "--model")) {
|
|
224
|
-
const index = args.includes("-m")
|
|
225
|
-
? args.indexOf("-m")
|
|
226
|
-
: args.indexOf("--model");
|
|
227
|
-
if (args[index + 1] == undefined) {
|
|
228
|
-
throw new Error("Model not defined");
|
|
229
|
-
}
|
|
230
|
-
const modelName = args[index + 1];
|
|
231
|
-
model = modelName;
|
|
232
|
-
}
|
|
233
|
-
await createController(args[1], { force, resource, model });
|
|
234
|
-
}
|
|
235
|
-
}
|
|
236
|
-
}
|
|
237
|
-
} catch (error) {
|
|
238
|
-
console.log("CLI ERROR:", error);
|
|
239
|
-
}
|
|
240
|
-
}
|
|
241
|
-
run()
|