@akanjs/devkit 0.0.143 → 0.0.145

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.
@@ -0,0 +1,45 @@
1
+ import { select } from "@inquirer/prompts";
2
+ import fsPromise from "fs/promises";
3
+ class Prompter {
4
+ static async selectGuideline() {
5
+ const guideNames = (await fsPromise.readdir(`${__dirname}/src/guidelines`)).filter((name) => !name.startsWith("_"));
6
+ return await select({ message: "Select a guideline", choices: guideNames.map((name) => ({ name, value: name })) });
7
+ }
8
+ static async getGuideJson(guideName) {
9
+ const filePath = `${__dirname}/src/guidelines/${guideName}/${guideName}.generate.json`;
10
+ const guideJson = await fsPromise.readFile(filePath, "utf-8");
11
+ return JSON.parse(guideJson);
12
+ }
13
+ static async getInstruction(guideName) {
14
+ const filePath = `${__dirname}/src/guidelines/${guideName}/${guideName}.instruction.md`;
15
+ const content = await fsPromise.readFile(filePath, "utf-8");
16
+ return content;
17
+ }
18
+ async makeTsFileUpdatePrompt({ context, request }) {
19
+ return `You are a senior developer writing TypeScript-based programs using Akan.js, an in-house framework. Here's an overview of the Akan.js framework:
20
+ ${await this.getDocumentation("framework")}
21
+ Please understand the following background information, write code that meets the requirements, verify that it satisfies the validation conditions, and return the result.
22
+
23
+ # Background Information
24
+ \`\`\`markdown
25
+ ${context}
26
+ \`\`\`
27
+
28
+ # Requirements
29
+ \`\`\`markdown
30
+ ${request}
31
+ \`\`\`
32
+ `;
33
+ }
34
+ async getDocumentation(guideName) {
35
+ const filePath = `${__dirname}/src/guidelines/${guideName}/${guideName}.instruction.md`;
36
+ const document = await fsPromise.readFile(filePath, "utf-8");
37
+ return `\`\`\`markdown
38
+ ${document}
39
+ \`\`\`
40
+ `;
41
+ }
42
+ }
43
+ export {
44
+ Prompter
45
+ };
@@ -0,0 +1,170 @@
1
+ import chalk from "chalk";
2
+ import * as fs from "fs";
3
+ import * as path from "path";
4
+ import * as ts from "typescript";
5
+ class TypeChecker {
6
+ configPath;
7
+ configFile;
8
+ config;
9
+ constructor(executor) {
10
+ const configPath = this.#findConfigFile(executor.cwdPath);
11
+ if (!configPath)
12
+ throw new Error("No tsconfig.json found in the project");
13
+ this.configPath = configPath;
14
+ this.configFile = ts.readConfigFile(this.configPath, (fileName) => ts.sys.readFile(fileName));
15
+ const parsedConfig = ts.parseJsonConfigFileContent(
16
+ this.configFile.config,
17
+ ts.sys,
18
+ path.dirname(this.configPath),
19
+ void 0,
20
+ this.configPath
21
+ );
22
+ if (parsedConfig.errors.length > 0) {
23
+ const errorMessages = parsedConfig.errors.map((error) => ts.flattenDiagnosticMessageText(error.messageText, "\n")).join("\n");
24
+ throw new Error(`Error parsing tsconfig.json:
25
+ ${errorMessages}`);
26
+ }
27
+ this.config = parsedConfig;
28
+ }
29
+ /**
30
+ * Find tsconfig.json by walking up the directory tree
31
+ */
32
+ #findConfigFile(searchPath) {
33
+ return ts.findConfigFile(searchPath, (fileName) => ts.sys.fileExists(fileName), "tsconfig.json");
34
+ }
35
+ /**
36
+ * Type-check a single TypeScript file
37
+ * @param filePath - Path to the TypeScript file to check
38
+ * @returns Array of diagnostic messages
39
+ */
40
+ check(filePath) {
41
+ const program = ts.createProgram([filePath], this.config.options);
42
+ const diagnostics = [
43
+ ...program.getSemanticDiagnostics(),
44
+ ...program.getSyntacticDiagnostics(),
45
+ ...program.getDeclarationDiagnostics()
46
+ ];
47
+ const errors = diagnostics.filter((diagnostic) => diagnostic.category === ts.DiagnosticCategory.Error);
48
+ const warnings = diagnostics.filter((diagnostic) => diagnostic.category === ts.DiagnosticCategory.Warning);
49
+ return { diagnostics, errors, warnings };
50
+ }
51
+ /**
52
+ * Format diagnostics for console output
53
+ * @param diagnostics - Array of TypeScript diagnostics
54
+ * @returns Formatted string
55
+ */
56
+ formatDiagnostics(diagnostics) {
57
+ if (diagnostics.length === 0)
58
+ return chalk.bold("\u2705 No type errors found");
59
+ const output = [];
60
+ let errorCount = 0;
61
+ let warningCount = 0;
62
+ let suggestionCount = 0;
63
+ const diagnosticsByFile = /* @__PURE__ */ new Map();
64
+ diagnostics.forEach((diagnostic) => {
65
+ if (diagnostic.category === ts.DiagnosticCategory.Error)
66
+ errorCount++;
67
+ else if (diagnostic.category === ts.DiagnosticCategory.Warning)
68
+ warningCount++;
69
+ else if (diagnostic.category === ts.DiagnosticCategory.Suggestion)
70
+ suggestionCount++;
71
+ if (diagnostic.file) {
72
+ const fileName = diagnostic.file.fileName;
73
+ if (!diagnosticsByFile.has(fileName))
74
+ diagnosticsByFile.set(fileName, []);
75
+ const fileDiagnostics = diagnosticsByFile.get(fileName);
76
+ if (fileDiagnostics)
77
+ fileDiagnostics.push(diagnostic);
78
+ } else {
79
+ if (!diagnosticsByFile.has(""))
80
+ diagnosticsByFile.set("", []);
81
+ const fileDiagnostics = diagnosticsByFile.get("");
82
+ if (fileDiagnostics)
83
+ fileDiagnostics.push(diagnostic);
84
+ }
85
+ });
86
+ diagnosticsByFile.forEach((fileDiagnostics, fileName) => {
87
+ if (fileName)
88
+ output.push(`
89
+ ${chalk.cyan(fileName)}`);
90
+ fileDiagnostics.forEach((diagnostic) => {
91
+ const categoryText = diagnostic.category === ts.DiagnosticCategory.Error ? "error" : diagnostic.category === ts.DiagnosticCategory.Warning ? "warning" : "suggestion";
92
+ const categoryColor = diagnostic.category === ts.DiagnosticCategory.Error ? chalk.red : diagnostic.category === ts.DiagnosticCategory.Warning ? chalk.yellow : chalk.blue;
93
+ const icon = diagnostic.category === ts.DiagnosticCategory.Error ? "\u274C" : diagnostic.category === ts.DiagnosticCategory.Warning ? "\u26A0\uFE0F" : "\u{1F4A1}";
94
+ const message = ts.flattenDiagnosticMessageText(diagnostic.messageText, "\n");
95
+ const tsCode = chalk.dim(`(TS${diagnostic.code})`);
96
+ if (diagnostic.file && diagnostic.start !== void 0) {
97
+ const { line, character } = diagnostic.file.getLineAndCharacterOfPosition(diagnostic.start);
98
+ output.push(`
99
+ ${icon} ${categoryColor(categoryText)}: ${message} ${tsCode}`);
100
+ output.push(` ${chalk.gray("at")} ${fileName}:${chalk.bold(`${line + 1}:${character + 1}`)}`);
101
+ const sourceLines = diagnostic.file.text.split("\n");
102
+ if (line < sourceLines.length) {
103
+ const sourceLine = sourceLines[line];
104
+ const lineNumber = (line + 1).toString().padStart(5, " ");
105
+ output.push(`
106
+ ${chalk.dim(lineNumber + " |")} ${sourceLine}`);
107
+ const underlinePrefix = " ".repeat(character);
108
+ const length = diagnostic.length ?? 1;
109
+ const underline = "~".repeat(Math.max(1, length));
110
+ output.push(
111
+ `${chalk.dim(" ".repeat(lineNumber.length) + " |")} ${underlinePrefix}${categoryColor(underline)}`
112
+ );
113
+ }
114
+ } else
115
+ output.push(`
116
+ ${icon} ${categoryColor(categoryText)}: ${message} ${tsCode}`);
117
+ });
118
+ });
119
+ const summary = [];
120
+ if (errorCount > 0)
121
+ summary.push(chalk.red(`${errorCount} error(s)`));
122
+ if (warningCount > 0)
123
+ summary.push(chalk.yellow(`${warningCount} warning(s)`));
124
+ if (suggestionCount > 0)
125
+ summary.push(chalk.blue(`${suggestionCount} suggestion(s)`));
126
+ return `
127
+ ${summary.join(", ")} found` + output.join("\n");
128
+ }
129
+ /**
130
+ * Get detailed diagnostic information with code snippet
131
+ * @param filePath - Path to the TypeScript file to check
132
+ * @returns Object containing diagnostics and detailed information
133
+ */
134
+ getDetailedDiagnostics(filePath) {
135
+ const { diagnostics } = this.check(filePath);
136
+ const sourceFile = ts.createSourceFile(filePath, fs.readFileSync(filePath, "utf8"), ts.ScriptTarget.Latest, true);
137
+ const details = diagnostics.map((diagnostic) => {
138
+ if (diagnostic.file && diagnostic.start !== void 0) {
139
+ const { line, character } = diagnostic.file.getLineAndCharacterOfPosition(diagnostic.start);
140
+ const message = ts.flattenDiagnosticMessageText(diagnostic.messageText, "\n");
141
+ const lines = sourceFile.text.split("\n");
142
+ const codeSnippet = line < lines.length ? lines[line] : void 0;
143
+ return { line: line + 1, column: character + 1, message, code: diagnostic.code, codeSnippet };
144
+ }
145
+ return {
146
+ line: 0,
147
+ column: 0,
148
+ message: ts.flattenDiagnosticMessageText(diagnostic.messageText, "\n"),
149
+ code: diagnostic.code
150
+ };
151
+ });
152
+ return { diagnostics, details };
153
+ }
154
+ /**
155
+ * Check if a file has type errors
156
+ * @param filePath - Path to the TypeScript file to check
157
+ * @returns true if there are no type errors, false otherwise
158
+ */
159
+ hasNoTypeErrors(filePath) {
160
+ try {
161
+ const { diagnostics } = this.check(filePath);
162
+ return diagnostics.length === 0;
163
+ } catch (error) {
164
+ return false;
165
+ }
166
+ }
167
+ }
168
+ export {
169
+ TypeChecker
170
+ };
@@ -1,49 +1,75 @@
1
+ import { Logger } from "@akanjs/common";
1
2
  import axios from "axios";
2
3
  import FormData from "form-data";
3
4
  import fs from "fs";
4
- const uploadRelease = async (projectName, {
5
+ import { Spinner } from "./spinner";
6
+ const spinning = (message) => {
7
+ const spinner = new Spinner(message, { prefix: message, enableSpin: true }).start();
8
+ return spinner;
9
+ };
10
+ const uploadRelease = async (appName, {
5
11
  workspaceRoot,
6
12
  environment,
7
13
  buildNum,
8
14
  platformVersion,
9
15
  local
10
16
  }) => {
17
+ const logger = new Logger("uploadRelease");
11
18
  const basePath = local ? "http://localhost:8080/backend" : "https://akasys.akamir.com/backend";
12
- const buildPath = `${workspaceRoot}/releases/builds/${projectName}-release.tar.gz`;
13
- const appBuildPath = `${workspaceRoot}/releases/builds/${projectName}-appBuild.zip`;
14
- const sourcePath = `${workspaceRoot}/releases/sources/${projectName}-source.tar.gz`;
15
- const formData = new FormData();
16
- const build = fs.readFileSync(buildPath);
17
- const source = fs.readFileSync(sourcePath);
18
- const appBuild = fs.readFileSync(appBuildPath);
19
- const buildStat = fs.statSync(buildPath);
20
- const sourceStat = fs.statSync(sourcePath);
21
- const appBuildStat = fs.statSync(appBuildPath);
22
- formData.append("files", build, `${projectName}-release.tar.gz`);
23
- formData.append("files", source, `${projectName}-source.tar.gz`);
24
- formData.append("files", appBuild, `${projectName}-appBuild.zip`);
25
- formData.append(
26
- "metas",
27
- JSON.stringify([
28
- { lastModifiedAt: buildStat.mtime, size: buildStat.size },
29
- { lastModifiedAt: sourceStat.mtime, size: sourceStat.size },
30
- { lastModifiedAt: appBuildStat.mtime, size: appBuildStat.size }
31
- ])
32
- );
33
- formData.append("type", "release");
19
+ const buildPath = `${workspaceRoot}/releases/builds/${appName}-release.tar.gz`;
20
+ const appBuildPath = `${workspaceRoot}/releases/builds/${appName}-appBuild.zip`;
21
+ const sourcePath = `${workspaceRoot}/releases/sources/${appName}-source.tar.gz`;
22
+ const readingFilesSpinner = spinning("Reading files...");
34
23
  try {
35
- const [buildFile, sourceFile, appBuildFile] = (await axios.post(`${basePath}/file/addFilesRestApi`, formData)).data;
36
- const major = platformVersion ? parseInt(platformVersion.split(".")[0]) : 1;
37
- const minor = platformVersion ? parseInt(platformVersion.split(".")[1]) : 0;
38
- const patch = platformVersion ? parseInt(platformVersion.split(".")[2]) : 0;
39
- const latestRelease = await axios.get(
40
- `${basePath}/release/findVersionRelease?appName=${projectName}&branch=${environment}&major=${major}&minor=${minor}`
24
+ const build = fs.readFileSync(buildPath);
25
+ const source = fs.readFileSync(sourcePath);
26
+ const appBuild = fs.readFileSync(appBuildPath);
27
+ const buildStat = fs.statSync(buildPath);
28
+ const sourceStat = fs.statSync(sourcePath);
29
+ const appBuildStat = fs.statSync(appBuildPath);
30
+ readingFilesSpinner.succeed("Reading files... done");
31
+ const preparingFormSpinner = spinning("Preparing form data...");
32
+ const formData = new FormData();
33
+ formData.append("files", build, `${appName}-release.tar.gz`);
34
+ formData.append("files", source, `${appName}-source.tar.gz`);
35
+ formData.append("files", appBuild, `${appName}-appBuild.zip`);
36
+ formData.append(
37
+ "metas",
38
+ JSON.stringify([
39
+ { lastModifiedAt: buildStat.mtime, size: buildStat.size },
40
+ { lastModifiedAt: sourceStat.mtime, size: sourceStat.size },
41
+ { lastModifiedAt: appBuildStat.mtime, size: appBuildStat.size }
42
+ ])
41
43
  );
42
- const release = (await axios.post(
43
- `${basePath}/release/pushRelease/${projectName}/${environment}/${major}/${minor}/${sourceFile.id}/${buildFile.id}/${appBuildFile.id}`
44
- )).data;
45
- return release;
44
+ formData.append("type", "release");
45
+ preparingFormSpinner.succeed("Preparing form data... done");
46
+ try {
47
+ const uploadingFilesSpinner = spinning("Uploading files to server...");
48
+ const [buildFile, sourceFile, appBuildFile] = (await axios.post(`${basePath}/file/addFilesRestApi`, formData)).data;
49
+ uploadingFilesSpinner.succeed("Uploading files to server... done");
50
+ const fetchingAppSpinner = spinning(`Fetching dev app information for ${appName}...`);
51
+ const major = platformVersion ? parseInt(platformVersion.split(".")[0]) : 1;
52
+ const minor = platformVersion ? parseInt(platformVersion.split(".")[1]) : 0;
53
+ const patch = platformVersion ? parseInt(platformVersion.split(".")[2]) : 0;
54
+ const devApp = (await axios.get(`${basePath}/devApp/devAppInName/${appName}`)).data;
55
+ fetchingAppSpinner.succeed(`Fetching dev app information for ${appName}... done`);
56
+ const pushingReleaseSpinner = spinning(`Pushing release to ${environment} environment...`);
57
+ const release = (await axios.post(
58
+ `${basePath}/release/pushRelease/${devApp.id}/${environment}/${major}/${minor}/${sourceFile.id}/${buildFile.id}/${appBuildFile.id}`
59
+ )).data;
60
+ pushingReleaseSpinner.succeed(`Pushing release to ${environment} environment... done`);
61
+ new Spinner(`Successfully pushed release to ${appName}-${environment} server. `, {
62
+ prefix: `Successfully pushed release to ${appName}-${environment} server. `,
63
+ enableSpin: false
64
+ }).succeed(`Successfully pushed release to ${appName}-${environment} server. `);
65
+ return release;
66
+ } catch (e) {
67
+ const errorMessage = e instanceof Error ? e.message : "Unknown error";
68
+ return null;
69
+ }
46
70
  } catch (e) {
71
+ const errorMessage = e instanceof Error ? e.message : "Unknown error";
72
+ readingFilesSpinner.fail(`Reading files failed: ${errorMessage}`);
47
73
  return null;
48
74
  }
49
75
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@akanjs/devkit",
3
- "version": "0.0.143",
3
+ "version": "0.0.145",
4
4
  "sourceType": "module",
5
5
  "publishConfig": {
6
6
  "access": "public"
@@ -17,6 +17,7 @@
17
17
  "dependencies": {
18
18
  "@inquirer/prompts": "^7.2.1",
19
19
  "@langchain/core": "^0.3.56",
20
+ "@langchain/deepseek": "^0.0.1",
20
21
  "@langchain/openai": "^0.5.10",
21
22
  "@trapezedev/project": "^7.1.3",
22
23
  "axios": "^1.7.9",
@@ -25,6 +26,7 @@
25
26
  "dotenv": "^16.4.7",
26
27
  "esbuild": "^0.19.2",
27
28
  "esbuild-plugin-d.ts": "^1.3.1",
29
+ "eslint": "^9.19.0",
28
30
  "form-data": "^4.0.1",
29
31
  "js-yaml": "^4.1.0",
30
32
  "ora": "^3.4.0",
package/src/aiEditor.d.ts CHANGED
@@ -1,9 +1,14 @@
1
1
  import { BaseMessage } from "@langchain/core/messages";
2
+ import type { Executor, WorkspaceExecutor } from "./executors";
3
+ import type { FileContent } from "./types";
2
4
  export declare const supportedLlmModels: readonly ["deepseek-chat", "deepseek-reasoner"];
3
5
  export type SupportedLlmModel = (typeof supportedLlmModels)[number];
4
6
  interface EditOptions {
7
+ onReasoning?: (reasoning: string) => void;
5
8
  onChunk?: (chunk: string) => void;
6
9
  maxTry?: number;
10
+ validate?: string[];
11
+ approve?: boolean;
7
12
  }
8
13
  export declare class AiSession {
9
14
  #private;
@@ -19,13 +24,27 @@ export declare class AiSession {
19
24
  model: SupportedLlmModel;
20
25
  apiKey: string;
21
26
  } | null): typeof AiSession;
22
- readonly messageHistory: BaseMessage[];
23
- constructor(messageHistory?: BaseMessage[]);
24
- ask(question: string, { onChunk, }?: EditOptions): Promise<{
27
+ static clearCache(workspaceRoot: string): void;
28
+ messageHistory: BaseMessage[];
29
+ readonly sessionKey: string;
30
+ isCacheLoaded: boolean;
31
+ workspace: WorkspaceExecutor;
32
+ constructor(type: string, { workspace, cacheKey, isContinued }: {
33
+ workspace: WorkspaceExecutor;
34
+ cacheKey?: string;
35
+ isContinued?: boolean;
36
+ });
37
+ ask(question: string, { onReasoning, onChunk, }?: EditOptions): Promise<{
25
38
  content: string;
26
39
  messageHistory: BaseMessage[];
27
40
  }>;
28
- edit(question: string, { onChunk, maxTry }?: EditOptions): Promise<string>;
41
+ edit(question: string, { onChunk, onReasoning, maxTry, validate, approve }?: EditOptions): Promise<string>;
29
42
  editTypescript(question: string, options?: EditOptions): Promise<string>;
43
+ addToolMessgaes(messages: {
44
+ type: string;
45
+ content: string;
46
+ }[]): this;
47
+ writeTypescripts(question: string, executor: Executor, options?: EditOptions): Promise<FileContent[]>;
48
+ editMarkdown(request: string, options?: EditOptions): Promise<string>;
30
49
  }
31
50
  export {};
@@ -1,8 +1,10 @@
1
1
  import { Logger } from "@akanjs/common";
2
2
  import { type AppConfigResult, AppScanResult, type LibConfigResult, LibScanResult, PkgScanResult, WorkspaceScanResult } from "@akanjs/config";
3
3
  import { type ExecOptions, type ForkOptions, type SpawnOptions } from "child_process";
4
+ import { Linter } from "./linter";
4
5
  import { Spinner } from "./spinner";
5
- import type { PackageJson, TsConfigJson } from "./types";
6
+ import { TypeChecker } from "./typeChecker";
7
+ import type { FileContent, PackageJson, TsConfigJson } from "./types";
6
8
  export declare const execEmoji: {
7
9
  workspace: string;
8
10
  app: string;
@@ -20,23 +22,24 @@ export declare class Executor {
20
22
  logger: Logger;
21
23
  cwdPath: string;
22
24
  emoji: string;
25
+ typeChecker: TypeChecker | null;
26
+ linter: Linter | null;
23
27
  constructor(name: string, cwdPath: string);
24
28
  exec(command: string, options?: ExecOptions): Promise<unknown>;
25
- spawn(command: string, args?: string[], options?: SpawnOptions): Promise<{
26
- code: number | null;
27
- signal: string | null;
28
- }>;
29
+ spawn(command: string, args?: string[], options?: SpawnOptions): Promise<string>;
29
30
  fork(modulePath: string, args?: string[], options?: ForkOptions): Promise<unknown>;
31
+ getPath(filePath: string): string;
30
32
  mkdir(dirPath: string): this;
33
+ readdir(dirPath: string): Promise<string[]>;
31
34
  exists(filePath: string): boolean;
32
35
  remove(filePath: string): this;
33
36
  removeDir(dirPath: string): this;
34
37
  writeFile(filePath: string, content: string | object, { overwrite }?: {
35
38
  overwrite?: boolean;
36
- }): this;
39
+ }): FileContent;
37
40
  writeJson(filePath: string, content: object): this;
38
- getLocalFile(filePath: string): {
39
- filepath: string;
41
+ getLocalFile(targetPath: string): {
42
+ filePath: string;
40
43
  content: string;
41
44
  };
42
45
  readFile(filePath: string): string;
@@ -50,7 +53,7 @@ export declare class Executor {
50
53
  enableSpin?: boolean | undefined;
51
54
  }): Spinner;
52
55
  getTsConfig(pathname?: string): TsConfigJson;
53
- applyTemplate({ basePath, template, scanResult, dict, overwrite, }: {
56
+ _applyTemplate({ basePath, template, scanResult, dict, overwrite, }: {
54
57
  basePath: string;
55
58
  template: string;
56
59
  scanResult?: AppScanResult | LibScanResult | null;
@@ -58,7 +61,32 @@ export declare class Executor {
58
61
  [key: string]: string;
59
62
  };
60
63
  overwrite?: boolean;
61
- }): Promise<void>;
64
+ }): Promise<FileContent[]>;
65
+ applyTemplate(options: {
66
+ basePath: string;
67
+ template: string;
68
+ dict?: {
69
+ [key: string]: string;
70
+ };
71
+ overwrite?: boolean;
72
+ }): Promise<FileContent[]>;
73
+ getTypeChecker(): TypeChecker;
74
+ typeCheck(filePath: string): {
75
+ diagnostics: import("typescript").Diagnostic[];
76
+ errors: import("typescript").Diagnostic[];
77
+ warnings: import("typescript").Diagnostic[];
78
+ message: string;
79
+ };
80
+ getLinter(): Linter;
81
+ lint(filePath: string, { fix, dryRun }?: {
82
+ fix?: boolean;
83
+ dryRun?: boolean;
84
+ }): Promise<{
85
+ results: import("eslint").ESLint.LintResult[];
86
+ message: string;
87
+ errors: import("eslint").Linter.LintMessage[];
88
+ warnings: import("eslint").Linter.LintMessage[];
89
+ }>;
62
90
  }
63
91
  interface ExecutorOptions {
64
92
  workspaceRoot: string;
@@ -91,19 +119,19 @@ export declare class WorkspaceExecutor extends Executor {
91
119
  add?: boolean;
92
120
  }): Promise<void>;
93
121
  getScalarConstantFiles(): Promise<{
94
- filepath: string;
122
+ filePath: string;
95
123
  content: string;
96
124
  }[]>;
97
125
  getConstantFiles(): Promise<{
98
- filepath: string;
126
+ filePath: string;
99
127
  content: string;
100
128
  }[]>;
101
129
  getDictionaryFiles(): Promise<{
102
- filepath: string;
130
+ filePath: string;
103
131
  content: string;
104
132
  }[]>;
105
133
  getViewFiles(): Promise<{
106
- filepath: string;
134
+ filePath: string;
107
135
  content: string;
108
136
  }[]>;
109
137
  }
@@ -126,8 +154,8 @@ export declare class SysExecutor extends Executor {
126
154
  }, libScanResults?: {
127
155
  [key: string]: LibScanResult;
128
156
  }): Promise<AppScanResult | LibScanResult>;
129
- getLocalFile(filePath: string): {
130
- filepath: string;
157
+ getLocalFile(targetPath: string): {
158
+ filePath: string;
131
159
  content: string;
132
160
  };
133
161
  getDatabaseModules(): Promise<string[]>;
@@ -137,33 +165,45 @@ export declare class SysExecutor extends Executor {
137
165
  getUnitComponents(): Promise<string[]>;
138
166
  getTemplateComponents(): Promise<string[]>;
139
167
  getViewsSourceCode(): Promise<{
140
- filepath: string;
168
+ filePath: string;
141
169
  content: string;
142
170
  }[]>;
143
171
  getUnitsSourceCode(): Promise<{
144
- filepath: string;
172
+ filePath: string;
145
173
  content: string;
146
174
  }[]>;
147
175
  getTemplatesSourceCode(): Promise<{
148
- filepath: string;
176
+ filePath: string;
149
177
  content: string;
150
178
  }[]>;
151
179
  getScalarConstantFiles(): Promise<{
152
- filepath: string;
180
+ filePath: string;
153
181
  content: string;
154
182
  }[]>;
155
183
  getScalarDictionaryFiles(): Promise<{
156
- filepath: string;
184
+ filePath: string;
157
185
  content: string;
158
186
  }[]>;
159
187
  getConstantFiles(): Promise<{
160
- filepath: string;
188
+ filePath: string;
189
+ content: string;
190
+ }[]>;
191
+ getConstantFilesWithLibs(): Promise<{
192
+ filePath: string;
161
193
  content: string;
162
194
  }[]>;
163
195
  getDictionaryFiles(): Promise<{
164
- filepath: string;
196
+ filePath: string;
165
197
  content: string;
166
198
  }[]>;
199
+ applyTemplate(options: {
200
+ basePath: string;
201
+ template: string;
202
+ dict?: {
203
+ [key: string]: string;
204
+ };
205
+ overwrite?: boolean;
206
+ }): Promise<FileContent[]>;
167
207
  setTsPaths(): this;
168
208
  }
169
209
  interface AppExecutorOptions {
@@ -0,0 +1,19 @@
1
+ export interface GuideScan {
2
+ type: "example" | "source" | "usage" | (string & {});
3
+ description: string;
4
+ path: string;
5
+ filterText?: string;
6
+ sample?: number;
7
+ }
8
+ export interface GuideUpdate {
9
+ filePath: string;
10
+ contents: string[];
11
+ rules: string[];
12
+ }
13
+ export interface GuideGenerateJson {
14
+ title: string;
15
+ description: string;
16
+ scans: GuideScan[];
17
+ update: GuideUpdate;
18
+ page: string;
19
+ }
package/src/index.d.ts CHANGED
@@ -16,3 +16,5 @@ export * from "./commandDecorators";
16
16
  export * from "./aiEditor";
17
17
  export * from "./builder";
18
18
  export * from "./spinner";
19
+ export * from "./prompter";
20
+ export * from "./guideline";