create-efc-app 0.2.5 → 0.3.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.
- package/dist/index.js +113 -41
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -2606,14 +2606,16 @@ export const GET = async (_req: Request, res: Response) => {
|
|
|
2606
2606
|
${roleGuard} // TODO: generate CSV of all users and stream response
|
|
2607
2607
|
res.setHeader('Content-Type', 'text/csv');
|
|
2608
2608
|
res.setHeader('Content-Disposition', 'attachment; filename="users.csv"');
|
|
2609
|
-
res.send('id,name,email,role,createdAt
|
|
2609
|
+
res.send('id,name,email,role,createdAt
|
|
2610
|
+
');
|
|
2610
2611
|
};
|
|
2611
2612
|
` : `${RA}${rr3}${exportMeta}${mwAdmin3}
|
|
2612
2613
|
export const GET = async (_req, res) => {
|
|
2613
2614
|
${roleGuard} // TODO: generate CSV of all users and stream response
|
|
2614
2615
|
res.setHeader('Content-Type', 'text/csv');
|
|
2615
2616
|
res.setHeader('Content-Disposition', 'attachment; filename="users.csv"');
|
|
2616
|
-
res.send('id,name,email,role,createdAt
|
|
2617
|
+
res.send('id,name,email,role,createdAt
|
|
2618
|
+
');
|
|
2617
2619
|
};
|
|
2618
2620
|
`;
|
|
2619
2621
|
await fs.outputFile(path.join(dest, "src", "api", "admin", "users", `export.${ext}`), exportContent);
|
|
@@ -3014,10 +3016,6 @@ ${roleGuard} const { status, page = 1, limit = 20 } = req.query;
|
|
|
3014
3016
|
}
|
|
3015
3017
|
|
|
3016
3018
|
// src/index.ts
|
|
3017
|
-
function cancel2(msg = "Cancelled") {
|
|
3018
|
-
p.cancel(msg);
|
|
3019
|
-
process.exit(0);
|
|
3020
|
-
}
|
|
3021
3019
|
async function main() {
|
|
3022
3020
|
console.log();
|
|
3023
3021
|
p.intro(pc.bgCyan(pc.black(" create-efc-app ")));
|
|
@@ -3027,7 +3025,10 @@ async function main() {
|
|
|
3027
3025
|
defaultValue: "my-api",
|
|
3028
3026
|
validate: (v) => !v.trim() ? "Project name is required" : void 0
|
|
3029
3027
|
});
|
|
3030
|
-
if (p.isCancel(projectName))
|
|
3028
|
+
if (p.isCancel(projectName)) {
|
|
3029
|
+
p.cancel("Cancelled");
|
|
3030
|
+
process.exit(0);
|
|
3031
|
+
}
|
|
3031
3032
|
const language = await p.select({
|
|
3032
3033
|
message: "Language:",
|
|
3033
3034
|
options: [
|
|
@@ -3035,7 +3036,10 @@ async function main() {
|
|
|
3035
3036
|
{ value: "javascript", label: "JavaScript" }
|
|
3036
3037
|
]
|
|
3037
3038
|
});
|
|
3038
|
-
if (p.isCancel(language))
|
|
3039
|
+
if (p.isCancel(language)) {
|
|
3040
|
+
p.cancel("Cancelled");
|
|
3041
|
+
process.exit(0);
|
|
3042
|
+
}
|
|
3039
3043
|
const database = await p.select({
|
|
3040
3044
|
message: "Database:",
|
|
3041
3045
|
options: [
|
|
@@ -3043,7 +3047,10 @@ async function main() {
|
|
|
3043
3047
|
{ value: "postgresql", label: "PostgreSQL", hint: "Drizzle ORM" }
|
|
3044
3048
|
]
|
|
3045
3049
|
});
|
|
3046
|
-
if (p.isCancel(database))
|
|
3050
|
+
if (p.isCancel(database)) {
|
|
3051
|
+
p.cancel("Cancelled");
|
|
3052
|
+
process.exit(0);
|
|
3053
|
+
}
|
|
3047
3054
|
const authStrategy = await p.select({
|
|
3048
3055
|
message: "Authentication strategy:",
|
|
3049
3056
|
options: [
|
|
@@ -3051,25 +3058,28 @@ async function main() {
|
|
|
3051
3058
|
{ value: "localStorage", label: "localStorage", hint: "bearer token \u2014 for SPAs" }
|
|
3052
3059
|
]
|
|
3053
3060
|
});
|
|
3054
|
-
if (p.isCancel(authStrategy))
|
|
3055
|
-
|
|
3056
|
-
|
|
3057
|
-
|
|
3058
|
-
|
|
3059
|
-
|
|
3060
|
-
|
|
3061
|
-
{ value: "userPortal", label: "User portal", hint: "auth, profile, billing routes" },
|
|
3062
|
-
{ value: "adminPortal", label: "Admin portal", hint: "dashboard, user mgmt, analytics" },
|
|
3063
|
-
{ value: "rbac", label: "Role-based access control", hint: "requireRole middleware" },
|
|
3064
|
-
{ value: "mailer", label: "Mailer", hint: "nodemailer + SMTP" }
|
|
3065
|
-
],
|
|
3066
|
-
initialValues: ["cluster", "tasks", "routeDocs", "userPortal", "adminPortal", "rbac"],
|
|
3067
|
-
required: false
|
|
3061
|
+
if (p.isCancel(authStrategy)) {
|
|
3062
|
+
p.cancel("Cancelled");
|
|
3063
|
+
process.exit(0);
|
|
3064
|
+
}
|
|
3065
|
+
const cluster = await p.confirm({
|
|
3066
|
+
message: "Enable multi-core clustering?",
|
|
3067
|
+
initialValue: true
|
|
3068
3068
|
});
|
|
3069
|
-
if (p.isCancel(
|
|
3070
|
-
|
|
3069
|
+
if (p.isCancel(cluster)) {
|
|
3070
|
+
p.cancel("Cancelled");
|
|
3071
|
+
process.exit(0);
|
|
3072
|
+
}
|
|
3073
|
+
const tasks = await p.confirm({
|
|
3074
|
+
message: "Enable background tasks?",
|
|
3075
|
+
initialValue: true
|
|
3076
|
+
});
|
|
3077
|
+
if (p.isCancel(tasks)) {
|
|
3078
|
+
p.cancel("Cancelled");
|
|
3079
|
+
process.exit(0);
|
|
3080
|
+
}
|
|
3071
3081
|
let taskBackend;
|
|
3072
|
-
if (
|
|
3082
|
+
if (tasks) {
|
|
3073
3083
|
const backend = await p.select({
|
|
3074
3084
|
message: "Task queue backend:",
|
|
3075
3085
|
options: [
|
|
@@ -3077,25 +3087,79 @@ async function main() {
|
|
|
3077
3087
|
{ value: "pg-boss", label: "pg-boss", hint: "PostgreSQL" }
|
|
3078
3088
|
]
|
|
3079
3089
|
});
|
|
3080
|
-
if (p.isCancel(backend))
|
|
3090
|
+
if (p.isCancel(backend)) {
|
|
3091
|
+
p.cancel("Cancelled");
|
|
3092
|
+
process.exit(0);
|
|
3093
|
+
}
|
|
3081
3094
|
taskBackend = backend;
|
|
3082
3095
|
}
|
|
3096
|
+
const routeDocs = await p.confirm({
|
|
3097
|
+
message: "Include route documentation (meta exports for the API dashboard)?",
|
|
3098
|
+
initialValue: true
|
|
3099
|
+
});
|
|
3100
|
+
if (p.isCancel(routeDocs)) {
|
|
3101
|
+
p.cancel("Cancelled");
|
|
3102
|
+
process.exit(0);
|
|
3103
|
+
}
|
|
3104
|
+
const userPortal = await p.confirm({
|
|
3105
|
+
message: "Build user portal?",
|
|
3106
|
+
initialValue: true
|
|
3107
|
+
});
|
|
3108
|
+
if (p.isCancel(userPortal)) {
|
|
3109
|
+
p.cancel("Cancelled");
|
|
3110
|
+
process.exit(0);
|
|
3111
|
+
}
|
|
3112
|
+
const adminPortal = await p.confirm({
|
|
3113
|
+
message: "Build admin portal?",
|
|
3114
|
+
initialValue: true
|
|
3115
|
+
});
|
|
3116
|
+
if (p.isCancel(adminPortal)) {
|
|
3117
|
+
p.cancel("Cancelled");
|
|
3118
|
+
process.exit(0);
|
|
3119
|
+
}
|
|
3120
|
+
let rbac = false;
|
|
3121
|
+
if (userPortal || adminPortal) {
|
|
3122
|
+
const rbacAnswer = await p.confirm({
|
|
3123
|
+
message: "Enable role-based access control (RBAC)?",
|
|
3124
|
+
initialValue: true
|
|
3125
|
+
});
|
|
3126
|
+
if (p.isCancel(rbacAnswer)) {
|
|
3127
|
+
p.cancel("Cancelled");
|
|
3128
|
+
process.exit(0);
|
|
3129
|
+
}
|
|
3130
|
+
rbac = rbacAnswer;
|
|
3131
|
+
}
|
|
3132
|
+
const mailerAnswer = await p.confirm({
|
|
3133
|
+
message: "Enable mailer (nodemailer)?",
|
|
3134
|
+
initialValue: false
|
|
3135
|
+
});
|
|
3136
|
+
if (p.isCancel(mailerAnswer)) {
|
|
3137
|
+
p.cancel("Cancelled");
|
|
3138
|
+
process.exit(0);
|
|
3139
|
+
}
|
|
3140
|
+
const mailer = mailerAnswer;
|
|
3083
3141
|
let smtpHost;
|
|
3084
3142
|
let smtpPort;
|
|
3085
|
-
if (
|
|
3143
|
+
if (mailer) {
|
|
3086
3144
|
const host = await p.text({
|
|
3087
3145
|
message: "SMTP host:",
|
|
3088
3146
|
placeholder: "smtp.gmail.com",
|
|
3089
3147
|
defaultValue: "smtp.gmail.com"
|
|
3090
3148
|
});
|
|
3091
|
-
if (p.isCancel(host))
|
|
3149
|
+
if (p.isCancel(host)) {
|
|
3150
|
+
p.cancel("Cancelled");
|
|
3151
|
+
process.exit(0);
|
|
3152
|
+
}
|
|
3092
3153
|
smtpHost = host;
|
|
3093
3154
|
const port = await p.text({
|
|
3094
3155
|
message: "SMTP port:",
|
|
3095
3156
|
placeholder: "587",
|
|
3096
3157
|
defaultValue: "587"
|
|
3097
3158
|
});
|
|
3098
|
-
if (p.isCancel(port))
|
|
3159
|
+
if (p.isCancel(port)) {
|
|
3160
|
+
p.cancel("Cancelled");
|
|
3161
|
+
process.exit(0);
|
|
3162
|
+
}
|
|
3099
3163
|
smtpPort = port;
|
|
3100
3164
|
}
|
|
3101
3165
|
const opts = {
|
|
@@ -3103,13 +3167,13 @@ async function main() {
|
|
|
3103
3167
|
language,
|
|
3104
3168
|
database,
|
|
3105
3169
|
authStrategy,
|
|
3106
|
-
cluster
|
|
3107
|
-
tasks
|
|
3108
|
-
routeDocs
|
|
3109
|
-
userPortal
|
|
3110
|
-
adminPortal
|
|
3111
|
-
rbac
|
|
3112
|
-
mailer
|
|
3170
|
+
cluster,
|
|
3171
|
+
tasks,
|
|
3172
|
+
routeDocs,
|
|
3173
|
+
userPortal,
|
|
3174
|
+
adminPortal,
|
|
3175
|
+
rbac,
|
|
3176
|
+
mailer,
|
|
3113
3177
|
...taskBackend !== void 0 && { taskBackend },
|
|
3114
3178
|
...smtpHost !== void 0 && { smtpHost },
|
|
3115
3179
|
...smtpPort !== void 0 && { smtpPort }
|
|
@@ -3144,14 +3208,22 @@ Your project is ready!
|
|
|
3144
3208
|
}
|
|
3145
3209
|
function npmInstall(projectDir) {
|
|
3146
3210
|
return new Promise((resolve, reject) => {
|
|
3147
|
-
const child = spawn("npm", ["install"], {
|
|
3148
|
-
|
|
3211
|
+
const child = spawn("npm", ["install"], {
|
|
3212
|
+
cwd: projectDir,
|
|
3213
|
+
stdio: "ignore"
|
|
3214
|
+
});
|
|
3215
|
+
child.on("exit", (code) => code === 0 ? resolve() : reject(new Error(`npm install failed`)));
|
|
3149
3216
|
});
|
|
3150
3217
|
}
|
|
3151
3218
|
function npmInstallGlobal() {
|
|
3152
3219
|
return new Promise((resolve, reject) => {
|
|
3153
|
-
const child = spawn("npm", ["install", "-g", "express-file-cluster"], {
|
|
3154
|
-
|
|
3220
|
+
const child = spawn("npm", ["install", "-g", "express-file-cluster"], {
|
|
3221
|
+
stdio: "ignore"
|
|
3222
|
+
});
|
|
3223
|
+
child.on(
|
|
3224
|
+
"exit",
|
|
3225
|
+
(code) => code === 0 ? resolve() : reject(new Error("global install failed"))
|
|
3226
|
+
);
|
|
3155
3227
|
});
|
|
3156
3228
|
}
|
|
3157
3229
|
main().catch((err) => {
|