@intend-it/core 4.0.0 → 4.0.2
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/README.md +4 -0
- package/dist/index.js +99 -75
- package/package.json +3 -3
package/README.md
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
<h1>@intend-it/core</h1>
|
|
3
3
|
<p><strong>AI-Powered Code Generator for the Intend Language</strong></p>
|
|
4
4
|
<p>
|
|
5
|
+
<a href="https://intend.fly.dev">Documentation</a> •
|
|
5
6
|
<a href="https://www.npmjs.com/package/@intend-it/core"><img src="https://img.shields.io/npm/v/@intend-it/core.svg" alt="npm version"></a>
|
|
6
7
|
<a href="https://www.npmjs.com/package/@intend-it/core"><img src="https://img.shields.io/npm/dm/@intend-it/core.svg" alt="npm downloads"></a>
|
|
7
8
|
<a href="https://github.com/DRFR0ST/intend/blob/main/LICENSE"><img src="https://img.shields.io/npm/l/@intend-it/core.svg" alt="license"></a>
|
|
@@ -14,9 +15,12 @@
|
|
|
14
15
|
|
|
15
16
|
`@intend-it/core` is the heart of the Intend compiler. It takes parsed AST from `@intend-it/parser` and generates production-ready TypeScript code using AI (Google Gemini or Ollama).
|
|
16
17
|
|
|
18
|
+
**[Read the full documentation 📖](https://intend.fly.dev)**
|
|
19
|
+
|
|
17
20
|
### ✨ Key Features
|
|
18
21
|
|
|
19
22
|
- **🧠 AI Code Generation** - Transforms natural language steps into actual code
|
|
23
|
+
- **🌐 Global Context** - Define file-level rules using the `context` keyword
|
|
20
24
|
- **🔀 Hybrid Orchestration** - Mix AI steps with deterministic function calls
|
|
21
25
|
- **🔄 Self-Correction Loop** - Validates output and auto-fixes errors
|
|
22
26
|
- **⚡ Smart Caching (CAS)** - Content-addressable storage for instant rebuilds
|
package/dist/index.js
CHANGED
|
@@ -168803,8 +168803,15 @@ class TypeScriptGenerator {
|
|
|
168803
168803
|
`;
|
|
168804
168804
|
code += `if (import.meta.main) {
|
|
168805
168805
|
`;
|
|
168806
|
-
|
|
168806
|
+
if (intent.parameters.length === 0) {
|
|
168807
|
+
code += ` Promise.resolve(${intent.name}()).catch((err: any) => console.error(err));
|
|
168807
168808
|
`;
|
|
168809
|
+
} else {
|
|
168810
|
+
code += ` // CLI Auto-Run disabled: function requires arguments
|
|
168811
|
+
`;
|
|
168812
|
+
code += ` // Promise.resolve(${intent.name}(/* ...args */)).catch((err: any) => console.error(err));
|
|
168813
|
+
`;
|
|
168814
|
+
}
|
|
168808
168815
|
code += `}
|
|
168809
168816
|
`;
|
|
168810
168817
|
}
|
|
@@ -168817,7 +168824,8 @@ class TypeScriptGenerator {
|
|
|
168817
168824
|
}
|
|
168818
168825
|
generateImport(imp) {
|
|
168819
168826
|
const specifiers = imp.specifiers.join(", ");
|
|
168820
|
-
|
|
168827
|
+
const source = imp.source.replace(/\.intent$/, "");
|
|
168828
|
+
return `import { ${specifiers} } from "${source}";`;
|
|
168821
168829
|
}
|
|
168822
168830
|
generateJsDoc(intent) {
|
|
168823
168831
|
const lines = ["/**"];
|
|
@@ -169165,9 +169173,10 @@ ${request.prompt}`;
|
|
|
169165
169173
|
}
|
|
169166
169174
|
// src/ai/prompt-builder.ts
|
|
169167
169175
|
class PromptBuilder {
|
|
169168
|
-
buildContext(intent, fileImports, importedIntents = []) {
|
|
169176
|
+
buildContext(intent, fileImports, importedIntents = [], fileContext) {
|
|
169169
169177
|
const returnType = this.formatReturnType(intent.returnType);
|
|
169170
169178
|
return {
|
|
169179
|
+
fileContext,
|
|
169171
169180
|
functionName: intent.name,
|
|
169172
169181
|
parameters: intent.parameters,
|
|
169173
169182
|
returnType,
|
|
@@ -169179,27 +169188,33 @@ class PromptBuilder {
|
|
|
169179
169188
|
};
|
|
169180
169189
|
}
|
|
169181
169190
|
buildSystemPrompt() {
|
|
169182
|
-
return `You are an expert TypeScript
|
|
169183
|
-
|
|
169184
|
-
Your task is to implement function bodies based on natural language specifications.
|
|
169185
|
-
|
|
169186
|
-
Rules:
|
|
169187
|
-
1. Generate ONLY the implementation code (function body content)
|
|
169188
|
-
2. Do NOT include the function signature or braces
|
|
169189
|
-
3. Use
|
|
169190
|
-
4. Handle errors
|
|
169191
|
-
5. Return values must match the specified return type
|
|
169192
|
-
6. Follow the
|
|
169193
|
-
7. Respect all invariants (
|
|
169194
|
-
8. Ensure all postconditions are
|
|
169195
|
-
9. Use
|
|
169196
|
-
10.
|
|
169191
|
+
return `You are an expert Senior TypeScript Developer specializing in robust, production-grade code.
|
|
169192
|
+
|
|
169193
|
+
Your task is to implement function bodies based on structured natural language specifications (Intend).
|
|
169194
|
+
|
|
169195
|
+
Rules:
|
|
169196
|
+
1. Generate ONLY the implementation code (function body content).
|
|
169197
|
+
2. Do NOT include the function signature, exports, or braces surfacing the function.
|
|
169198
|
+
3. Use strict TypeScript (no 'any' unless absolutely necessary).
|
|
169199
|
+
4. Handle edge cases and errors defensively (throw descriptive Errors).
|
|
169200
|
+
5. Return values must strictly match the specified return type.
|
|
169201
|
+
6. Follow the provided steps EXACTLY in order.
|
|
169202
|
+
7. Respect all invariants (implement usage checks at the start if needed).
|
|
169203
|
+
8. Ensure all postconditions (ensures) are satisfiable by your logic.
|
|
169204
|
+
9. Use clear, semantic variable names.
|
|
169205
|
+
10. Do not hallucinate imports; use only what is provided.
|
|
169206
|
+
11. If a variable name in the requirements seems to have a typo (e.g. 'totals' instead of 'total'), fix it to match the defined variable.`;
|
|
169197
169207
|
}
|
|
169198
169208
|
buildStepPrompt(context, stepIndex) {
|
|
169199
169209
|
const step = context.steps[stepIndex];
|
|
169200
169210
|
const lines = [];
|
|
169201
169211
|
lines.push(`Implement this TypeScript function step:
|
|
169202
169212
|
`);
|
|
169213
|
+
if (context.fileContext) {
|
|
169214
|
+
lines.push(`GLOBAL CONTEXT / RULES:`);
|
|
169215
|
+
lines.push(context.fileContext);
|
|
169216
|
+
lines.push("");
|
|
169217
|
+
}
|
|
169203
169218
|
lines.push(`Function: ${context.functionName}`);
|
|
169204
169219
|
lines.push(`Parameters: ${this.formatParameters(context.parameters)}`);
|
|
169205
169220
|
lines.push(`Return Type: ${context.returnType}
|
|
@@ -169261,6 +169276,11 @@ Generate ONLY the TypeScript code for this step (no explanations, no markdown).`
|
|
|
169261
169276
|
const lines = [];
|
|
169262
169277
|
lines.push(`Implement this complete TypeScript function:
|
|
169263
169278
|
`);
|
|
169279
|
+
if (context.fileContext) {
|
|
169280
|
+
lines.push(`GLOBAL CONTEXT / RULES:`);
|
|
169281
|
+
lines.push(context.fileContext);
|
|
169282
|
+
lines.push("");
|
|
169283
|
+
}
|
|
169264
169284
|
lines.push(`Function: ${context.functionName}`);
|
|
169265
169285
|
lines.push(`Parameters: ${this.formatParameters(context.parameters)}`);
|
|
169266
169286
|
lines.push(`Return Type: ${context.returnType}
|
|
@@ -169314,6 +169334,9 @@ Generate ONLY the TypeScript code for this step (no explanations, no markdown).`
|
|
|
169314
169334
|
lines.push(`The code should:`);
|
|
169315
169335
|
lines.push(`- Follow all steps in order`);
|
|
169316
169336
|
lines.push(`- Store results in the specified variable names`);
|
|
169337
|
+
lines.push(`- Make sure that imported functions are called with the correct arguments from the context.`);
|
|
169338
|
+
lines.push(`- Make sure the return value matches the expected return type strictly.`);
|
|
169339
|
+
lines.push(`- If a Step requires a return, ensure it is returned.`);
|
|
169317
169340
|
lines.push(`- Satisfy all postconditions`);
|
|
169318
169341
|
lines.push(`- Be production-ready TypeScript`);
|
|
169319
169342
|
lines.push(`
|
|
@@ -169395,6 +169418,7 @@ Verify:`);
|
|
|
169395
169418
|
lines.push(`3. All declared variables are used`);
|
|
169396
169419
|
lines.push(`4. Return value matches required type`);
|
|
169397
169420
|
lines.push(`5. No infinite loops or unintended recursion`);
|
|
169421
|
+
lines.push(`6. Imports are correct (no .intent extension, only using provided imports)`);
|
|
169398
169422
|
lines.push(`
|
|
169399
169423
|
Respond with APPROVED or ISSUES + FIX as specified.`);
|
|
169400
169424
|
return lines.join(`
|
|
@@ -169791,7 +169815,10 @@ class TypeScriptValidator {
|
|
|
169791
169815
|
esModuleInterop: true,
|
|
169792
169816
|
skipLibCheck: true,
|
|
169793
169817
|
checkJs: false,
|
|
169794
|
-
allowJs: false
|
|
169818
|
+
allowJs: false,
|
|
169819
|
+
noImplicitReturns: true,
|
|
169820
|
+
strictNullChecks: true,
|
|
169821
|
+
noImplicitAny: true
|
|
169795
169822
|
};
|
|
169796
169823
|
const host = ts.createCompilerHost(compilerOptions);
|
|
169797
169824
|
const originalReadFile = host.readFile;
|
|
@@ -169810,6 +169837,12 @@ class TypeScriptValidator {
|
|
|
169810
169837
|
`);
|
|
169811
169838
|
if (msg.includes("Cannot find global type"))
|
|
169812
169839
|
return false;
|
|
169840
|
+
if (msg.includes("Cannot find name 'process'"))
|
|
169841
|
+
return false;
|
|
169842
|
+
if (msg.includes("Cannot find name 'console'"))
|
|
169843
|
+
return false;
|
|
169844
|
+
if (msg.includes("Cannot find name 'Buffer'"))
|
|
169845
|
+
return false;
|
|
169813
169846
|
return true;
|
|
169814
169847
|
}).map((d) => {
|
|
169815
169848
|
const line = d.file ? d.file.getLineAndCharacterOfPosition(d.start).line + 1 : 0;
|
|
@@ -169839,7 +169872,7 @@ class AICodeGenerator {
|
|
|
169839
169872
|
constructor(options) {
|
|
169840
169873
|
this.promptBuilder = new PromptBuilder;
|
|
169841
169874
|
this.validator = new TypeScriptValidator;
|
|
169842
|
-
this.mode =
|
|
169875
|
+
this.mode = "full";
|
|
169843
169876
|
this.maxAttempts = options.maxAttempts ?? 3;
|
|
169844
169877
|
this.projectContext = options.projectContext;
|
|
169845
169878
|
this.debug = options.debug ?? false;
|
|
@@ -169886,10 +169919,9 @@ class AICodeGenerator {
|
|
|
169886
169919
|
}
|
|
169887
169920
|
}
|
|
169888
169921
|
}
|
|
169889
|
-
const context = this.promptBuilder.buildContext(intent, file.imports, importedIntents);
|
|
169922
|
+
const context = this.promptBuilder.buildContext(intent, file.imports, importedIntents, file.context);
|
|
169890
169923
|
totalSteps += context.steps.length;
|
|
169891
169924
|
if (this.mode === "step-by-step") {
|
|
169892
|
-
console.warn("Step-by-step mode not fully supported for multi-intent files. Falling back to full generation.");
|
|
169893
169925
|
currentCode = await this.generateFull(currentCode, context, intent.name);
|
|
169894
169926
|
} else {
|
|
169895
169927
|
currentCode = await this.generateFull(currentCode, context, intent.name);
|
|
@@ -169917,18 +169949,22 @@ class AICodeGenerator {
|
|
|
169917
169949
|
throw new Error(`AI generation failed: ${response.error}`);
|
|
169918
169950
|
}
|
|
169919
169951
|
const cleanCode = this.sanitizeAIResponse(response.code);
|
|
169920
|
-
const updatedCode = this.injectImplementation(fileContent,
|
|
169921
|
-
|
|
169952
|
+
const { code: updatedCode, startLine, endLine } = this.injectImplementation(fileContent, functionName, cleanCode);
|
|
169953
|
+
let syntaxErrors = this.validator.validate(updatedCode);
|
|
169954
|
+
syntaxErrors = syntaxErrors.filter((e) => e.line >= startLine + 1 && e.line <= endLine + 1);
|
|
169922
169955
|
if (syntaxErrors.length > 0) {
|
|
169923
169956
|
attempts++;
|
|
169924
169957
|
if (attempts < limit) {
|
|
169925
169958
|
const errorMsg = syntaxErrors.slice(0, 5).map((e) => `Line ${e.line}: ${e.message}`).join(`
|
|
169926
169959
|
`);
|
|
169927
|
-
console.log(`
|
|
169960
|
+
console.log(`
|
|
169961
|
+
⚠️ Validation failed for ${functionName} (Attempt ${attempts}/${limit}):`);
|
|
169928
169962
|
console.log(errorMsg.split(`
|
|
169929
169963
|
`).map((l) => ` ${l}`).join(`
|
|
169930
169964
|
`));
|
|
169931
|
-
console.log(`
|
|
169965
|
+
console.log(`
|
|
169966
|
+
Retrying with AI auto-correction...
|
|
169967
|
+
`);
|
|
169932
169968
|
prompt += `
|
|
169933
169969
|
|
|
169934
169970
|
Validation Failed (Attempt ${attempts}/${limit}).
|
|
@@ -169940,14 +169976,17 @@ ${cleanCode}
|
|
|
169940
169976
|
` + `Errors encountered:
|
|
169941
169977
|
${errorMsg}
|
|
169942
169978
|
|
|
169943
|
-
` + `CRITICAL
|
|
169944
|
-
` + `1.
|
|
169945
|
-
` + `2.
|
|
169979
|
+
` + `CRITICAL: You are fixing a critical syntax/compilation error.
|
|
169980
|
+
` + `1. ANALYZE: Briefly explain why the error happened.
|
|
169981
|
+
` + `2. FIX: Generate the COMPLETE, FIXED function body wrapped in \`\`\`typescript.
|
|
169982
|
+
` + `Do not return partial snippets. Return the full function body.
|
|
169946
169983
|
`;
|
|
169947
169984
|
} else {
|
|
169948
|
-
|
|
169949
|
-
|
|
169950
|
-
|
|
169985
|
+
const errorMsg = syntaxErrors.slice(0, 5).map((e) => `Line ${e.line}: ${e.message}`).join(`
|
|
169986
|
+
`);
|
|
169987
|
+
throw new Error(`Validation failed for ${functionName} after ${limit} attempts.
|
|
169988
|
+
Errors:
|
|
169989
|
+
${errorMsg}`);
|
|
169951
169990
|
}
|
|
169952
169991
|
continue;
|
|
169953
169992
|
}
|
|
@@ -169957,10 +169996,12 @@ ${errorMsg}
|
|
|
169957
169996
|
}
|
|
169958
169997
|
attempts++;
|
|
169959
169998
|
if (attempts < limit) {
|
|
169960
|
-
console.log(`
|
|
169999
|
+
console.log(`
|
|
170000
|
+
\uD83D\uDD0D Logic review found issues for ${functionName} (Attempt ${attempts}/${limit}):`);
|
|
169961
170001
|
console.log(` ${logicIssues.issues.slice(0, 3).join(`
|
|
169962
170002
|
`)}`);
|
|
169963
|
-
console.log(` Retrying with AI auto-correction
|
|
170003
|
+
console.log(` Retrying with AI auto-correction...
|
|
170004
|
+
`);
|
|
169964
170005
|
prompt += `
|
|
169965
170006
|
|
|
169966
170007
|
Logic Review Failed (Attempt ${attempts}/${limit}).
|
|
@@ -169975,17 +170016,23 @@ ${logicIssues.issues.join(`
|
|
|
169975
170016
|
|
|
169976
170017
|
` + `Suggested fix: ${logicIssues.fix}
|
|
169977
170018
|
|
|
169978
|
-
` + `CRITICAL
|
|
170019
|
+
` + `CRITICAL: You are fixing a LOGICAL issue.
|
|
170020
|
+
` + `1. ANALYZE: Briefly explain the logic flaw.
|
|
170021
|
+
` + `2. FIX: Generate the COMPLETE, FIXED function body wrapped in \`\`\`typescript.
|
|
170022
|
+
` + `Ensure every step from the requirements is fully implemented.
|
|
169979
170023
|
`;
|
|
169980
170024
|
} else {
|
|
169981
|
-
|
|
169982
|
-
|
|
170025
|
+
throw new Error(`Logic verification failed for ${functionName} after ${limit} attempts.
|
|
170026
|
+
Issues:
|
|
170027
|
+
${logicIssues.issues.join(`
|
|
170028
|
+
`)}`);
|
|
169983
170029
|
}
|
|
169984
170030
|
}
|
|
169985
170031
|
return fileContent;
|
|
169986
170032
|
}
|
|
169987
170033
|
sanitizeAIResponse(code) {
|
|
169988
170034
|
let sanitized = code.replace(/```typescript\s*/g, "").replace(/```\s*/g, "");
|
|
170035
|
+
sanitized = sanitized.replace(/^(Here is|Sure|I have|Certainly).+$/gim, "");
|
|
169989
170036
|
sanitized = sanitized.replace(/^\s*import\s+.*;?\s*$/gm, "");
|
|
169990
170037
|
return sanitized.trim();
|
|
169991
170038
|
}
|
|
@@ -170029,40 +170076,9 @@ ${logicIssues.issues.join(`
|
|
|
170029
170076
|
}
|
|
170030
170077
|
}
|
|
170031
170078
|
async explainFailure(functionName, code, errors) {
|
|
170032
|
-
|
|
170033
|
-
`);
|
|
170034
|
-
const prompt = `
|
|
170035
|
-
The following TypeScript implementation for '${functionName}' failed validation after multiple self-correction attempts.
|
|
170036
|
-
|
|
170037
|
-
Code:
|
|
170038
|
-
${code}
|
|
170039
|
-
|
|
170040
|
-
Errors:
|
|
170041
|
-
${errorMsg}
|
|
170042
|
-
|
|
170043
|
-
Please explain to the user why this code is failing and what they might need to fix in their .intend file or configuration.
|
|
170044
|
-
Focus on the root cause. Keep it concise.
|
|
170045
|
-
`;
|
|
170046
|
-
try {
|
|
170047
|
-
console.log(` \uD83E\uDD16 Analyzing failure...`);
|
|
170048
|
-
const response = await this.provider.generateCode({
|
|
170049
|
-
systemPrompt: "You are a helpful coding assistant explaining compile errors.",
|
|
170050
|
-
prompt,
|
|
170051
|
-
debug: this.debug
|
|
170052
|
-
});
|
|
170053
|
-
if (response.success) {
|
|
170054
|
-
console.log(`
|
|
170055
|
-
==================================================`);
|
|
170056
|
-
console.log("\uD83E\uDD16 AI DIAGNOSTICS:");
|
|
170057
|
-
console.log(response.code);
|
|
170058
|
-
console.log(`==================================================
|
|
170059
|
-
`);
|
|
170060
|
-
}
|
|
170061
|
-
} catch (err) {
|
|
170062
|
-
console.warn("Failed to generate diagnostics.");
|
|
170063
|
-
}
|
|
170079
|
+
return;
|
|
170064
170080
|
}
|
|
170065
|
-
injectImplementation(fileContent,
|
|
170081
|
+
injectImplementation(fileContent, functionName, implementation) {
|
|
170066
170082
|
const lines = fileContent.split(`
|
|
170067
170083
|
`);
|
|
170068
170084
|
let startLine = -1;
|
|
@@ -170090,8 +170106,12 @@ Focus on the root cause. Keep it concise.
|
|
|
170090
170106
|
}
|
|
170091
170107
|
}
|
|
170092
170108
|
if (!foundStart || endLine === -1) {
|
|
170093
|
-
|
|
170094
|
-
|
|
170109
|
+
throw new Error(`Fatal: Could not filter function body for injection.
|
|
170110
|
+
Function: ${functionName}
|
|
170111
|
+
Regex: ${regex}
|
|
170112
|
+
Start found: ${foundStart}, End found: ${endLine !== -1}
|
|
170113
|
+
|
|
170114
|
+
Possible cause: Formatting mismatch between template and injector.`);
|
|
170095
170115
|
}
|
|
170096
170116
|
const pre = lines.slice(0, startLine + 1).join(`
|
|
170097
170117
|
`);
|
|
@@ -170104,9 +170124,13 @@ Focus on the root cause. Keep it concise.
|
|
|
170104
170124
|
return "";
|
|
170105
170125
|
}).join(`
|
|
170106
170126
|
`);
|
|
170107
|
-
return
|
|
170108
|
-
|
|
170109
|
-
|
|
170127
|
+
return {
|
|
170128
|
+
code: `${pre}
|
|
170129
|
+
${indentedImpl}
|
|
170130
|
+
${post}`,
|
|
170131
|
+
startLine: startLine + 1,
|
|
170132
|
+
endLine: endLine + 1
|
|
170133
|
+
};
|
|
170110
170134
|
}
|
|
170111
170135
|
async testConnection() {
|
|
170112
170136
|
return await this.provider.testConnection();
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@intend-it/core",
|
|
3
|
-
"version": "4.0.
|
|
3
|
+
"version": "4.0.2",
|
|
4
4
|
"description": "Core compiler and AI integration for the Intend programming language",
|
|
5
5
|
"main": "./dist/index.js",
|
|
6
6
|
"types": "./dist/index.d.ts",
|
|
@@ -35,7 +35,7 @@
|
|
|
35
35
|
],
|
|
36
36
|
"license": "MIT",
|
|
37
37
|
"dependencies": {
|
|
38
|
-
"@intend-it/parser": "^1.3.
|
|
38
|
+
"@intend-it/parser": "^1.3.2",
|
|
39
39
|
"@google/generative-ai": "^0.21.0"
|
|
40
40
|
},
|
|
41
41
|
"devDependencies": {
|
|
@@ -43,6 +43,6 @@
|
|
|
43
43
|
"typescript": "^5.0.0"
|
|
44
44
|
},
|
|
45
45
|
"peerDependencies": {
|
|
46
|
-
"@intend-it/parser": ">=1.3.
|
|
46
|
+
"@intend-it/parser": ">=1.3.2"
|
|
47
47
|
}
|
|
48
48
|
}
|