@strapi/cloud-cli 4.25.3 → 4.25.4
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 +106 -67
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +107 -65
- package/dist/index.mjs.map +1 -1
- package/dist/src/index.d.ts +1 -0
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/list-projects/action.d.ts +4 -0
- package/dist/src/list-projects/action.d.ts.map +1 -0
- package/dist/src/list-projects/command.d.ts +7 -0
- package/dist/src/list-projects/command.d.ts.map +1 -0
- package/dist/src/list-projects/index.d.ts +7 -0
- package/dist/src/list-projects/index.d.ts.map +1 -0
- package/dist/src/services/cli-api.d.ts +6 -1
- package/dist/src/services/cli-api.d.ts.map +1 -1
- package/dist/src/utils/compress-files.d.ts.map +1 -1
- package/dist/src/utils/pkg.d.ts.map +1 -1
- package/package.json +5 -5
package/dist/index.mjs
CHANGED
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import crypto$1 from "crypto";
|
|
2
|
-
import fse from "fs-extra";
|
|
2
|
+
import * as fse from "fs-extra";
|
|
3
|
+
import fse__default from "fs-extra";
|
|
3
4
|
import * as path from "path";
|
|
4
5
|
import path__default from "path";
|
|
5
6
|
import chalk from "chalk";
|
|
6
7
|
import axios, { AxiosError } from "axios";
|
|
7
8
|
import * as crypto from "node:crypto";
|
|
8
9
|
import { env } from "@strapi/utils";
|
|
9
|
-
import * as fs from "fs";
|
|
10
10
|
import * as tar from "tar";
|
|
11
11
|
import { minimatch } from "minimatch";
|
|
12
12
|
import inquirer from "inquirer";
|
|
@@ -18,7 +18,6 @@ import jwt from "jsonwebtoken";
|
|
|
18
18
|
import stringify from "fast-safe-stringify";
|
|
19
19
|
import ora from "ora";
|
|
20
20
|
import * as cliProgress from "cli-progress";
|
|
21
|
-
import fs$1 from "fs/promises";
|
|
22
21
|
import pkgUp from "pkg-up";
|
|
23
22
|
import * as yup from "yup";
|
|
24
23
|
import _ from "lodash";
|
|
@@ -41,23 +40,6 @@ const IGNORED_PATTERNS = [
|
|
|
41
40
|
"**/.idea/**",
|
|
42
41
|
"**/.vscode/**"
|
|
43
42
|
];
|
|
44
|
-
const getFiles = (dirPath, ignorePatterns = [], arrayOfFiles = [], subfolder = "") => {
|
|
45
|
-
const entries = fs.readdirSync(path.join(dirPath, subfolder));
|
|
46
|
-
entries.forEach((entry) => {
|
|
47
|
-
const entryPathFromRoot = path.join(subfolder, entry);
|
|
48
|
-
const entryPath = path.relative(dirPath, entryPathFromRoot);
|
|
49
|
-
const isIgnored = isIgnoredFile(dirPath, entryPathFromRoot, ignorePatterns);
|
|
50
|
-
if (isIgnored) {
|
|
51
|
-
return;
|
|
52
|
-
}
|
|
53
|
-
if (fs.statSync(entryPath).isDirectory()) {
|
|
54
|
-
getFiles(dirPath, ignorePatterns, arrayOfFiles, entryPathFromRoot);
|
|
55
|
-
} else {
|
|
56
|
-
arrayOfFiles.push(entryPath);
|
|
57
|
-
}
|
|
58
|
-
});
|
|
59
|
-
return arrayOfFiles;
|
|
60
|
-
};
|
|
61
43
|
const isIgnoredFile = (folderPath, file, ignorePatterns) => {
|
|
62
44
|
ignorePatterns.push(...IGNORED_PATTERNS);
|
|
63
45
|
const relativeFilePath = path.join(folderPath, file);
|
|
@@ -75,16 +57,35 @@ const isIgnoredFile = (folderPath, file, ignorePatterns) => {
|
|
|
75
57
|
}
|
|
76
58
|
return isIgnored;
|
|
77
59
|
};
|
|
78
|
-
const
|
|
60
|
+
const getFiles = async (dirPath, ignorePatterns = [], subfolder = "") => {
|
|
61
|
+
const arrayOfFiles = [];
|
|
62
|
+
const entries = await fse.readdir(path.join(dirPath, subfolder));
|
|
63
|
+
for (const entry of entries) {
|
|
64
|
+
const entryPathFromRoot = path.join(subfolder, entry);
|
|
65
|
+
const entryPath = path.relative(dirPath, entryPathFromRoot);
|
|
66
|
+
const isIgnored = isIgnoredFile(dirPath, entryPathFromRoot, ignorePatterns);
|
|
67
|
+
if (!isIgnored) {
|
|
68
|
+
if (fse.statSync(entryPath).isDirectory()) {
|
|
69
|
+
const subFiles = await getFiles(dirPath, ignorePatterns, entryPathFromRoot);
|
|
70
|
+
arrayOfFiles.push(...subFiles);
|
|
71
|
+
} else {
|
|
72
|
+
arrayOfFiles.push(entryPath);
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
return arrayOfFiles;
|
|
77
|
+
};
|
|
78
|
+
const readGitignore = async (folderPath) => {
|
|
79
79
|
const gitignorePath = path.resolve(folderPath, ".gitignore");
|
|
80
|
-
|
|
80
|
+
const pathExist = await fse.pathExists(gitignorePath);
|
|
81
|
+
if (!pathExist)
|
|
81
82
|
return [];
|
|
82
|
-
const gitignoreContent =
|
|
83
|
+
const gitignoreContent = await fse.readFile(gitignorePath, "utf8");
|
|
83
84
|
return gitignoreContent.split(/\r?\n/).filter((line) => Boolean(line.trim()) && !line.startsWith("#"));
|
|
84
85
|
};
|
|
85
86
|
const compressFilesToTar = async (storagePath, folderToCompress, filename) => {
|
|
86
|
-
const ignorePatterns = readGitignore(folderToCompress);
|
|
87
|
-
const filesToCompress = getFiles(folderToCompress, ignorePatterns);
|
|
87
|
+
const ignorePatterns = await readGitignore(folderToCompress);
|
|
88
|
+
const filesToCompress = await getFiles(folderToCompress, ignorePatterns);
|
|
88
89
|
return tar.c(
|
|
89
90
|
{
|
|
90
91
|
gzip: true,
|
|
@@ -97,7 +98,7 @@ const APP_FOLDER_NAME = "com.strapi.cli";
|
|
|
97
98
|
const CONFIG_FILENAME = "config.json";
|
|
98
99
|
async function checkDirectoryExists(directoryPath) {
|
|
99
100
|
try {
|
|
100
|
-
const fsStat = await
|
|
101
|
+
const fsStat = await fse__default.lstat(directoryPath);
|
|
101
102
|
return fsStat.isDirectory();
|
|
102
103
|
} catch (e) {
|
|
103
104
|
return false;
|
|
@@ -105,14 +106,14 @@ async function checkDirectoryExists(directoryPath) {
|
|
|
105
106
|
}
|
|
106
107
|
async function getTmpStoragePath() {
|
|
107
108
|
const storagePath = path__default.join(os.tmpdir(), APP_FOLDER_NAME);
|
|
108
|
-
await
|
|
109
|
+
await fse__default.ensureDir(storagePath);
|
|
109
110
|
return storagePath;
|
|
110
111
|
}
|
|
111
112
|
async function getConfigPath() {
|
|
112
113
|
const configDirs = XDGAppPaths(APP_FOLDER_NAME).configDirs();
|
|
113
114
|
const configPath = configDirs.find(checkDirectoryExists);
|
|
114
115
|
if (!configPath) {
|
|
115
|
-
await
|
|
116
|
+
await fse__default.ensureDir(configDirs[0]);
|
|
116
117
|
return configDirs[0];
|
|
117
118
|
}
|
|
118
119
|
return configPath;
|
|
@@ -120,9 +121,9 @@ async function getConfigPath() {
|
|
|
120
121
|
async function getLocalConfig() {
|
|
121
122
|
const configPath = await getConfigPath();
|
|
122
123
|
const configFilePath = path__default.join(configPath, CONFIG_FILENAME);
|
|
123
|
-
await
|
|
124
|
+
await fse__default.ensureFile(configFilePath);
|
|
124
125
|
try {
|
|
125
|
-
return await
|
|
126
|
+
return await fse__default.readJSON(configFilePath, { encoding: "utf8", throws: true });
|
|
126
127
|
} catch (e) {
|
|
127
128
|
return {};
|
|
128
129
|
}
|
|
@@ -130,10 +131,10 @@ async function getLocalConfig() {
|
|
|
130
131
|
async function saveLocalConfig(data) {
|
|
131
132
|
const configPath = await getConfigPath();
|
|
132
133
|
const configFilePath = path__default.join(configPath, CONFIG_FILENAME);
|
|
133
|
-
await
|
|
134
|
+
await fse__default.writeJson(configFilePath, data, { encoding: "utf8", spaces: 2, mode: 384 });
|
|
134
135
|
}
|
|
135
136
|
const name = "@strapi/cloud-cli";
|
|
136
|
-
const version = "4.25.
|
|
137
|
+
const version = "4.25.3";
|
|
137
138
|
const description = "Commands to interact with the Strapi Cloud";
|
|
138
139
|
const keywords = [
|
|
139
140
|
"strapi",
|
|
@@ -178,7 +179,7 @@ const scripts = {
|
|
|
178
179
|
watch: "pack-up watch"
|
|
179
180
|
};
|
|
180
181
|
const dependencies = {
|
|
181
|
-
"@strapi/utils": "4.25.
|
|
182
|
+
"@strapi/utils": "4.25.3",
|
|
182
183
|
axios: "1.6.0",
|
|
183
184
|
chalk: "4.1.2",
|
|
184
185
|
"cli-progress": "3.12.0",
|
|
@@ -203,8 +204,8 @@ const devDependencies = {
|
|
|
203
204
|
"@types/cli-progress": "3.11.5",
|
|
204
205
|
"@types/eventsource": "1.1.15",
|
|
205
206
|
"@types/lodash": "^4.14.191",
|
|
206
|
-
"eslint-config-custom": "4.25.
|
|
207
|
-
tsconfig: "4.25.
|
|
207
|
+
"eslint-config-custom": "4.25.3",
|
|
208
|
+
tsconfig: "4.25.3"
|
|
208
209
|
};
|
|
209
210
|
const engines = {
|
|
210
211
|
node: ">=18.0.0 <=20.x.x",
|
|
@@ -257,7 +258,7 @@ async function cloudApiFactory({ logger }, token) {
|
|
|
257
258
|
deploy({ filePath, project }, { onUploadProgress }) {
|
|
258
259
|
return axiosCloudAPI.post(
|
|
259
260
|
`/deploy/${project.name}`,
|
|
260
|
-
{ file:
|
|
261
|
+
{ file: fse__default.createReadStream(filePath) },
|
|
261
262
|
{
|
|
262
263
|
headers: {
|
|
263
264
|
"Content-Type": "multipart/form-data"
|
|
@@ -300,8 +301,19 @@ async function cloudApiFactory({ logger }, token) {
|
|
|
300
301
|
throw error;
|
|
301
302
|
}
|
|
302
303
|
},
|
|
303
|
-
listProjects() {
|
|
304
|
-
|
|
304
|
+
async listProjects() {
|
|
305
|
+
try {
|
|
306
|
+
const response = await axiosCloudAPI.get("/projects");
|
|
307
|
+
if (response.status !== 200) {
|
|
308
|
+
throw new Error("Error fetching cloud projects from the server.");
|
|
309
|
+
}
|
|
310
|
+
return response;
|
|
311
|
+
} catch (error) {
|
|
312
|
+
logger.debug(
|
|
313
|
+
"🥲 Oops! Couldn't retrieve your project's list from the server. Please try again."
|
|
314
|
+
);
|
|
315
|
+
throw error;
|
|
316
|
+
}
|
|
305
317
|
},
|
|
306
318
|
track(event, payload = {}) {
|
|
307
319
|
return axiosCloudAPI.post("/track", {
|
|
@@ -316,18 +328,18 @@ async function save(data, { directoryPath } = {}) {
|
|
|
316
328
|
const alreadyInFileData = await retrieve({ directoryPath });
|
|
317
329
|
const storedData = { ...alreadyInFileData, ...data };
|
|
318
330
|
const pathToFile = path__default.join(directoryPath || process.cwd(), LOCAL_SAVE_FILENAME);
|
|
319
|
-
await
|
|
320
|
-
await
|
|
331
|
+
await fse__default.ensureDir(path__default.dirname(pathToFile));
|
|
332
|
+
await fse__default.writeJson(pathToFile, storedData, { encoding: "utf8" });
|
|
321
333
|
}
|
|
322
334
|
async function retrieve({
|
|
323
335
|
directoryPath
|
|
324
336
|
} = {}) {
|
|
325
337
|
const pathToFile = path__default.join(directoryPath || process.cwd(), LOCAL_SAVE_FILENAME);
|
|
326
|
-
const pathExists = await
|
|
338
|
+
const pathExists = await fse__default.pathExists(pathToFile);
|
|
327
339
|
if (!pathExists) {
|
|
328
340
|
return {};
|
|
329
341
|
}
|
|
330
|
-
return
|
|
342
|
+
return fse__default.readJSON(pathToFile, { encoding: "utf8" });
|
|
331
343
|
}
|
|
332
344
|
const strapiInfoSave = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
333
345
|
__proto__: null,
|
|
@@ -599,7 +611,7 @@ const loadPkg = async ({ cwd, logger }) => {
|
|
|
599
611
|
if (!pkgPath) {
|
|
600
612
|
throw new Error("Could not find a package.json in the current directory");
|
|
601
613
|
}
|
|
602
|
-
const buffer = await
|
|
614
|
+
const buffer = await fse.readFile(pkgPath);
|
|
603
615
|
const pkg = JSON.parse(buffer.toString());
|
|
604
616
|
logger.debug("Loaded package.json:", os.EOL, pkg);
|
|
605
617
|
return pkg;
|
|
@@ -839,7 +851,7 @@ async function createProject$1(ctx, cloudApi, projectInput) {
|
|
|
839
851
|
throw e;
|
|
840
852
|
}
|
|
841
853
|
}
|
|
842
|
-
const action$
|
|
854
|
+
const action$3 = async (ctx) => {
|
|
843
855
|
const { logger } = ctx;
|
|
844
856
|
const { getValidToken, eraseToken } = await tokenServiceFactory(ctx);
|
|
845
857
|
const token = await getValidToken(ctx, promptLogin);
|
|
@@ -996,13 +1008,13 @@ async function upload(ctx, project, token, maxProjectFileSize) {
|
|
|
996
1008
|
process.exit(1);
|
|
997
1009
|
}
|
|
998
1010
|
const tarFilePath = path__default.resolve(storagePath, compressedFilename);
|
|
999
|
-
const fileStats = await
|
|
1011
|
+
const fileStats = await fse__default.stat(tarFilePath);
|
|
1000
1012
|
if (fileStats.size > maxProjectFileSize) {
|
|
1001
1013
|
ctx.logger.log(
|
|
1002
1014
|
"Unable to proceed: Your project is too big to be transferred, please use a git repo instead."
|
|
1003
1015
|
);
|
|
1004
1016
|
try {
|
|
1005
|
-
await
|
|
1017
|
+
await fse__default.remove(tarFilePath);
|
|
1006
1018
|
} catch (e) {
|
|
1007
1019
|
ctx.logger.log("Unable to remove file: ", tarFilePath);
|
|
1008
1020
|
ctx.logger.debug(e);
|
|
@@ -1041,7 +1053,7 @@ async function upload(ctx, project, token, maxProjectFileSize) {
|
|
|
1041
1053
|
}
|
|
1042
1054
|
ctx.logger.debug(e);
|
|
1043
1055
|
} finally {
|
|
1044
|
-
await
|
|
1056
|
+
await fse__default.remove(tarFilePath);
|
|
1045
1057
|
}
|
|
1046
1058
|
process.exit(0);
|
|
1047
1059
|
} catch (e) {
|
|
@@ -1054,7 +1066,7 @@ async function getProject(ctx) {
|
|
|
1054
1066
|
const { project } = await retrieve();
|
|
1055
1067
|
if (!project) {
|
|
1056
1068
|
try {
|
|
1057
|
-
return await action$
|
|
1069
|
+
return await action$3(ctx);
|
|
1058
1070
|
} catch (e) {
|
|
1059
1071
|
ctx.logger.error("An error occurred while deploying the project. Please try again later.");
|
|
1060
1072
|
ctx.logger.debug(e);
|
|
@@ -1063,7 +1075,7 @@ async function getProject(ctx) {
|
|
|
1063
1075
|
}
|
|
1064
1076
|
return project;
|
|
1065
1077
|
}
|
|
1066
|
-
const action$
|
|
1078
|
+
const action$2 = async (ctx) => {
|
|
1067
1079
|
const { getValidToken } = await tokenServiceFactory(ctx);
|
|
1068
1080
|
const token = await getValidToken(ctx, promptLogin);
|
|
1069
1081
|
if (!token) {
|
|
@@ -1137,16 +1149,16 @@ const runAction = (name2, action2) => (...args) => {
|
|
|
1137
1149
|
process.exit(1);
|
|
1138
1150
|
});
|
|
1139
1151
|
};
|
|
1140
|
-
const command$
|
|
1141
|
-
command2.command("cloud:deploy").alias("deploy").description("Deploy a Strapi Cloud project").option("-d, --debug", "Enable debugging mode with verbose logs").option("-s, --silent", "Don't log anything").action(() => runAction("deploy", action$
|
|
1152
|
+
const command$4 = ({ command: command2, ctx }) => {
|
|
1153
|
+
command2.command("cloud:deploy").alias("deploy").description("Deploy a Strapi Cloud project").option("-d, --debug", "Enable debugging mode with verbose logs").option("-s, --silent", "Don't log anything").action(() => runAction("deploy", action$2)(ctx));
|
|
1142
1154
|
};
|
|
1143
1155
|
const deployProject = {
|
|
1144
1156
|
name: "deploy-project",
|
|
1145
1157
|
description: "Deploy a Strapi Cloud project",
|
|
1146
|
-
action: action$
|
|
1147
|
-
command: command$
|
|
1158
|
+
action: action$2,
|
|
1159
|
+
command: command$4
|
|
1148
1160
|
};
|
|
1149
|
-
const command$
|
|
1161
|
+
const command$3 = ({ command: command2, ctx }) => {
|
|
1150
1162
|
command2.command("cloud:login").alias("login").description("Strapi Cloud Login").addHelpText(
|
|
1151
1163
|
"after",
|
|
1152
1164
|
"\nAfter running this command, you will be prompted to enter your authentication information."
|
|
@@ -1156,10 +1168,10 @@ const login = {
|
|
|
1156
1168
|
name: "login",
|
|
1157
1169
|
description: "Strapi Cloud Login",
|
|
1158
1170
|
action: loginAction,
|
|
1159
|
-
command: command$
|
|
1171
|
+
command: command$3
|
|
1160
1172
|
};
|
|
1161
1173
|
const openModule = import("open");
|
|
1162
|
-
const action = async (ctx) => {
|
|
1174
|
+
const action$1 = async (ctx) => {
|
|
1163
1175
|
const { logger } = ctx;
|
|
1164
1176
|
const { retrieveToken, eraseToken } = await tokenServiceFactory(ctx);
|
|
1165
1177
|
const token = await retrieveToken();
|
|
@@ -1195,31 +1207,61 @@ const action = async (ctx) => {
|
|
|
1195
1207
|
logger.debug("Failed to track logout event", e);
|
|
1196
1208
|
}
|
|
1197
1209
|
};
|
|
1198
|
-
const command$
|
|
1199
|
-
command2.command("cloud:logout").alias("logout").description("Strapi Cloud Logout").option("-d, --debug", "Enable debugging mode with verbose logs").option("-s, --silent", "Don't log anything").action(() => runAction("logout", action)(ctx));
|
|
1210
|
+
const command$2 = ({ command: command2, ctx }) => {
|
|
1211
|
+
command2.command("cloud:logout").alias("logout").description("Strapi Cloud Logout").option("-d, --debug", "Enable debugging mode with verbose logs").option("-s, --silent", "Don't log anything").action(() => runAction("logout", action$1)(ctx));
|
|
1200
1212
|
};
|
|
1201
1213
|
const logout = {
|
|
1202
1214
|
name: "logout",
|
|
1203
1215
|
description: "Strapi Cloud Logout",
|
|
1204
|
-
action,
|
|
1205
|
-
command: command$
|
|
1216
|
+
action: action$1,
|
|
1217
|
+
command: command$2
|
|
1206
1218
|
};
|
|
1207
|
-
const command = ({ command: command2, ctx }) => {
|
|
1208
|
-
command2.command("cloud:create-project").description("Create a Strapi Cloud project").option("-d, --debug", "Enable debugging mode with verbose logs").option("-s, --silent", "Don't log anything").action(() => runAction("cloud:create-project", action$
|
|
1219
|
+
const command$1 = ({ command: command2, ctx }) => {
|
|
1220
|
+
command2.command("cloud:create-project").description("Create a Strapi Cloud project").option("-d, --debug", "Enable debugging mode with verbose logs").option("-s, --silent", "Don't log anything").action(() => runAction("cloud:create-project", action$3)(ctx));
|
|
1209
1221
|
};
|
|
1210
1222
|
const createProject = {
|
|
1211
1223
|
name: "create-project",
|
|
1212
1224
|
description: "Create a new project",
|
|
1213
|
-
action: action$
|
|
1225
|
+
action: action$3,
|
|
1226
|
+
command: command$1
|
|
1227
|
+
};
|
|
1228
|
+
const action = async (ctx) => {
|
|
1229
|
+
const { getValidToken } = await tokenServiceFactory(ctx);
|
|
1230
|
+
const token = await getValidToken(ctx, promptLogin);
|
|
1231
|
+
const { logger } = ctx;
|
|
1232
|
+
if (!token) {
|
|
1233
|
+
return;
|
|
1234
|
+
}
|
|
1235
|
+
const cloudApiService = await cloudApiFactory(ctx, token);
|
|
1236
|
+
const spinner = logger.spinner("Fetching your projects...").start();
|
|
1237
|
+
try {
|
|
1238
|
+
const {
|
|
1239
|
+
data: { data: projectList }
|
|
1240
|
+
} = await cloudApiService.listProjects();
|
|
1241
|
+
spinner.succeed();
|
|
1242
|
+
logger.log(projectList);
|
|
1243
|
+
} catch (e) {
|
|
1244
|
+
ctx.logger.debug("Failed to list projects", e);
|
|
1245
|
+
spinner.fail("An error occurred while fetching your projects from Strapi Cloud.");
|
|
1246
|
+
}
|
|
1247
|
+
};
|
|
1248
|
+
const command = ({ command: command2, ctx }) => {
|
|
1249
|
+
command2.command("cloud:projects").alias("projects").description("List Strapi Cloud projects").option("-d, --debug", "Enable debugging mode with verbose logs").option("-s, --silent", "Don't log anything").action(() => runAction("listProjects", action)(ctx));
|
|
1250
|
+
};
|
|
1251
|
+
const listProjects = {
|
|
1252
|
+
name: "list-projects",
|
|
1253
|
+
description: "List Strapi Cloud projects",
|
|
1254
|
+
action,
|
|
1214
1255
|
command
|
|
1215
1256
|
};
|
|
1216
1257
|
const cli = {
|
|
1217
1258
|
deployProject,
|
|
1218
1259
|
login,
|
|
1219
1260
|
logout,
|
|
1220
|
-
createProject
|
|
1261
|
+
createProject,
|
|
1262
|
+
listProjects
|
|
1221
1263
|
};
|
|
1222
|
-
const cloudCommands = [deployProject, login, logout];
|
|
1264
|
+
const cloudCommands = [deployProject, login, logout, listProjects];
|
|
1223
1265
|
async function initCloudCLIConfig() {
|
|
1224
1266
|
const localConfig = await getLocalConfig();
|
|
1225
1267
|
if (!localConfig.deviceId) {
|