@hyperfixi/patterns-reference 3.1.1 → 3.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/CHANGELOG.md +186 -1
- package/README.md +47 -36
- package/data/engine-verification.json +58 -65
- package/data/patterns.db +0 -0
- package/data/patterns.db.stamp +1 -0
- package/dist/api/index.d.mts +2 -2
- package/dist/api/index.d.ts +2 -2
- package/dist/api/index.js +198 -98
- package/dist/api/index.mjs +197 -100
- package/dist/{index-6GkHj5yJ.d.mts → index-CoDUfq2P.d.mts} +39 -3
- package/dist/{index-6GkHj5yJ.d.ts → index-CoDUfq2P.d.ts} +39 -3
- package/dist/index.d.mts +87 -13
- package/dist/index.d.ts +87 -13
- package/dist/index.js +261 -144
- package/dist/index.mjs +258 -146
- package/dist/{llm-B5nGz8V1.d.mts → llm-CCCSw-yp.d.ts} +21 -10
- package/dist/{llm-rEdJQScF.d.ts → llm-PxnriEZ_.d.mts} +21 -10
- package/dist/sync/index.d.mts +1 -1
- package/dist/sync/index.d.ts +1 -1
- package/dist/sync/index.js +4 -1
- package/dist/sync/index.mjs +4 -1
- package/package.json +16 -16
- package/src/adapters/llm-adapter.ts +64 -42
- package/src/api/engine-filter.ts +37 -0
- package/src/api/llm.ts +54 -64
- package/src/api/patterns.ts +92 -30
- package/src/api/roles.ts +6 -4
- package/src/api/translations.ts +34 -27
- package/src/database/connection.ts +16 -4
- package/src/html-snippets.ts +39 -10
- package/src/index.ts +12 -2
- package/src/registry/patterns-provider.ts +3 -1
- package/src/sync/db-stamp.ts +7 -4
- package/src/sync/markup-attributes.ts +15 -0
- package/src/sync/verify-parses.ts +42 -0
- package/src/types/better-sqlite3.d.ts +2 -0
- package/src/types/index.ts +44 -2
- package/src/sync/span-mask.ts +0 -166
- package/src/sync/translation-checks.ts +0 -282
package/dist/api/index.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
+
var semantic = require('@lokascript/semantic');
|
|
3
4
|
var Database = require('better-sqlite3');
|
|
4
5
|
var fs = require('fs');
|
|
5
6
|
var url = require('url');
|
|
@@ -9,9 +10,87 @@ function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
|
|
|
9
10
|
|
|
10
11
|
var Database__default = /*#__PURE__*/_interopDefault(Database);
|
|
11
12
|
|
|
13
|
+
var __defProp = Object.defineProperty;
|
|
14
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
15
|
+
var __esm = (fn, res) => function __init() {
|
|
16
|
+
return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
|
|
17
|
+
};
|
|
18
|
+
var __export = (target, all) => {
|
|
19
|
+
for (var name in all)
|
|
20
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
21
|
+
};
|
|
22
|
+
|
|
12
23
|
// ../../node_modules/tsup/assets/cjs_shims.js
|
|
13
|
-
var getImportMetaUrl
|
|
14
|
-
var
|
|
24
|
+
var getImportMetaUrl, importMetaUrl;
|
|
25
|
+
var init_cjs_shims = __esm({
|
|
26
|
+
"../../node_modules/tsup/assets/cjs_shims.js"() {
|
|
27
|
+
getImportMetaUrl = () => typeof document === "undefined" ? new URL(`file:${__filename}`).href : document.currentScript && document.currentScript.tagName.toUpperCase() === "SCRIPT" ? document.currentScript.src : new URL("main.js", document.baseURI).href;
|
|
28
|
+
importMetaUrl = /* @__PURE__ */ getImportMetaUrl();
|
|
29
|
+
}
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
// src/sync/markup-attributes.ts
|
|
33
|
+
function findHyperscriptAttributes(markup) {
|
|
34
|
+
const spans = [];
|
|
35
|
+
ATTRIBUTE.lastIndex = 0;
|
|
36
|
+
let match;
|
|
37
|
+
while ((match = ATTRIBUTE.exec(markup)) !== null) {
|
|
38
|
+
const body = match[2] ?? match[3];
|
|
39
|
+
const start = match.index + match[0].length - body.length - 1;
|
|
40
|
+
spans.push({ start, end: start + body.length, body });
|
|
41
|
+
}
|
|
42
|
+
return spans;
|
|
43
|
+
}
|
|
44
|
+
function isMarkupRow(code) {
|
|
45
|
+
return /^\s*<[a-zA-Z!]/.test(code);
|
|
46
|
+
}
|
|
47
|
+
function hyperscriptBodies(code) {
|
|
48
|
+
if (!isMarkupRow(code)) return [code];
|
|
49
|
+
const bodies = findHyperscriptAttributes(code).map((span) => span.body);
|
|
50
|
+
for (const match of code.matchAll(HX_LIVE_ATTRIBUTE)) bodies.push(match[2] ?? match[3] ?? "");
|
|
51
|
+
return bodies.filter((body) => body.trim().length > 0);
|
|
52
|
+
}
|
|
53
|
+
var ATTRIBUTE, HX_LIVE_ATTRIBUTE;
|
|
54
|
+
var init_markup_attributes = __esm({
|
|
55
|
+
"src/sync/markup-attributes.ts"() {
|
|
56
|
+
init_cjs_shims();
|
|
57
|
+
ATTRIBUTE = /(^|[\s"'])_\s*=\s*(?:"([^"]*)"|'([^']*)')/g;
|
|
58
|
+
HX_LIVE_ATTRIBUTE = /(^|[\s"'])hx-live\s*=\s*(?:"([^"]*)"|'([^']*)')/g;
|
|
59
|
+
}
|
|
60
|
+
});
|
|
61
|
+
|
|
62
|
+
// src/sync/verify-parses.ts
|
|
63
|
+
var verify_parses_exports = {};
|
|
64
|
+
__export(verify_parses_exports, {
|
|
65
|
+
verifyParses: () => verifyParses
|
|
66
|
+
});
|
|
67
|
+
function verifyParses(code, language, translatable = true) {
|
|
68
|
+
const bodies = hyperscriptBodies(code);
|
|
69
|
+
if (bodies.length === 0) return false;
|
|
70
|
+
const parseLanguage = translatable ? language : "en";
|
|
71
|
+
return bodies.every((body) => {
|
|
72
|
+
try {
|
|
73
|
+
return semantic.canParse(body, parseLanguage);
|
|
74
|
+
} catch {
|
|
75
|
+
return false;
|
|
76
|
+
}
|
|
77
|
+
});
|
|
78
|
+
}
|
|
79
|
+
var init_verify_parses = __esm({
|
|
80
|
+
"src/sync/verify-parses.ts"() {
|
|
81
|
+
init_cjs_shims();
|
|
82
|
+
init_markup_attributes();
|
|
83
|
+
}
|
|
84
|
+
});
|
|
85
|
+
|
|
86
|
+
// src/api/index.ts
|
|
87
|
+
init_cjs_shims();
|
|
88
|
+
|
|
89
|
+
// src/api/patterns.ts
|
|
90
|
+
init_cjs_shims();
|
|
91
|
+
|
|
92
|
+
// src/database/connection.ts
|
|
93
|
+
init_cjs_shims();
|
|
15
94
|
var __filename2 = url.fileURLToPath(importMetaUrl);
|
|
16
95
|
var __dirname$1 = path.dirname(__filename2);
|
|
17
96
|
var DEFAULT_DB_PATH = process.env.LSP_DB_PATH || process.env.HYPERSCRIPT_LSP_DB || path.join(__dirname$1, "../data/patterns.db");
|
|
@@ -19,6 +98,7 @@ var dbInstance = null;
|
|
|
19
98
|
var currentDbPath = null;
|
|
20
99
|
var openFileId = null;
|
|
21
100
|
var lastIdentityCheckAt = 0;
|
|
101
|
+
var openReadonly = false;
|
|
22
102
|
var IDENTITY_TTL_MS = 1e3;
|
|
23
103
|
function fileIdentity(path) {
|
|
24
104
|
try {
|
|
@@ -30,7 +110,9 @@ function fileIdentity(path) {
|
|
|
30
110
|
}
|
|
31
111
|
function getDatabase(options = {}) {
|
|
32
112
|
const dbPath = options.dbPath ?? DEFAULT_DB_PATH;
|
|
33
|
-
|
|
113
|
+
const readonly = options.readonly ?? false;
|
|
114
|
+
const canServe = !openReadonly || readonly;
|
|
115
|
+
if (dbInstance !== null && currentDbPath === dbPath && canServe) {
|
|
34
116
|
const now = Date.now();
|
|
35
117
|
if (now - lastIdentityCheckAt < IDENTITY_TTL_MS) {
|
|
36
118
|
return dbInstance;
|
|
@@ -46,9 +128,8 @@ function getDatabase(options = {}) {
|
|
|
46
128
|
if (dbInstance !== null) {
|
|
47
129
|
dbInstance.close();
|
|
48
130
|
}
|
|
49
|
-
dbInstance = new Database__default.default(dbPath, {
|
|
50
|
-
|
|
51
|
-
});
|
|
131
|
+
dbInstance = new Database__default.default(dbPath, { readonly });
|
|
132
|
+
openReadonly = readonly;
|
|
52
133
|
dbInstance.pragma("foreign_keys = ON");
|
|
53
134
|
currentDbPath = dbPath;
|
|
54
135
|
openFileId = fileIdentity(dbPath);
|
|
@@ -56,12 +137,26 @@ function getDatabase(options = {}) {
|
|
|
56
137
|
return dbInstance;
|
|
57
138
|
}
|
|
58
139
|
|
|
140
|
+
// src/api/patterns.ts
|
|
141
|
+
init_markup_attributes();
|
|
142
|
+
|
|
143
|
+
// src/api/engine-filter.ts
|
|
144
|
+
init_cjs_shims();
|
|
145
|
+
function runsOn(column, engine) {
|
|
146
|
+
if (engine === null) return { sql: `${column} IS NULL`, params: [] };
|
|
147
|
+
if (engine === "both") return { sql: `${column} = 'both'`, params: [] };
|
|
148
|
+
return { sql: `${column} IN ('both', ?)`, params: [engine] };
|
|
149
|
+
}
|
|
150
|
+
function exampleCondition(column, engine) {
|
|
151
|
+
return engine === void 0 ? { sql: `${column} IS NOT NULL`, params: [] } : runsOn(column, engine);
|
|
152
|
+
}
|
|
153
|
+
|
|
59
154
|
// src/api/patterns.ts
|
|
60
155
|
async function getPatternById(id, options) {
|
|
61
156
|
const db = getDatabase({ ...options, readonly: true });
|
|
62
157
|
const row = db.prepare(
|
|
63
158
|
`
|
|
64
|
-
SELECT id, title, raw_code, description, feature, engine, created_at
|
|
159
|
+
SELECT id, title, raw_code, description, feature, engine, translatable, created_at
|
|
65
160
|
FROM code_examples
|
|
66
161
|
WHERE id = ?
|
|
67
162
|
`
|
|
@@ -72,7 +167,7 @@ async function getPatternsByCategory(category, options) {
|
|
|
72
167
|
const db = getDatabase({ ...options, readonly: true });
|
|
73
168
|
const rows = db.prepare(
|
|
74
169
|
`
|
|
75
|
-
SELECT id, title, raw_code, description, feature, engine, created_at
|
|
170
|
+
SELECT id, title, raw_code, description, feature, engine, translatable, created_at
|
|
76
171
|
FROM code_examples
|
|
77
172
|
WHERE feature = ?
|
|
78
173
|
ORDER BY title
|
|
@@ -84,7 +179,7 @@ async function getPatternsByCommand(command, options) {
|
|
|
84
179
|
const db = getDatabase({ ...options, readonly: true });
|
|
85
180
|
const rows = db.prepare(
|
|
86
181
|
`
|
|
87
|
-
SELECT id, title, raw_code, description, feature, engine, created_at
|
|
182
|
+
SELECT id, title, raw_code, description, feature, engine, translatable, created_at
|
|
88
183
|
FROM code_examples
|
|
89
184
|
WHERE raw_code LIKE ?
|
|
90
185
|
ORDER BY title
|
|
@@ -92,32 +187,45 @@ async function getPatternsByCommand(command, options) {
|
|
|
92
187
|
).all(`%${command}%`);
|
|
93
188
|
return rows.filter((row) => new RegExp(`\\b${command}\\b`, "i").test(row.raw_code)).map(mapRowToPattern);
|
|
94
189
|
}
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
190
|
+
function engineFilter(searchOptions) {
|
|
191
|
+
return searchOptions.engine === void 0 ? { sql: "1 = 1", params: [] } : runsOn("engine", searchOptions.engine);
|
|
192
|
+
}
|
|
193
|
+
function usableIn(db, language) {
|
|
98
194
|
const rows = db.prepare(
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
ORDER BY title
|
|
104
|
-
LIMIT ? OFFSET ?
|
|
105
|
-
`
|
|
106
|
-
).all(`%${query}%`, `%${query}%`, `%${query}%`, limit, offset);
|
|
107
|
-
return rows.map(mapRowToPattern);
|
|
195
|
+
"SELECT code_example_id AS id FROM pattern_translations WHERE language = ? AND verified_parses = 1"
|
|
196
|
+
).all(language);
|
|
197
|
+
const verified = new Set(rows.map((row) => row.id));
|
|
198
|
+
return (pattern) => verified.has(pattern.id) || hyperscriptBodies(pattern.rawCode).length === 0;
|
|
108
199
|
}
|
|
109
|
-
|
|
200
|
+
function queryPatterns(searchOptions, defaultLimit, connOptions, match = { sql: "1 = 1", params: [] }) {
|
|
110
201
|
const db = getDatabase({ ...connOptions, readonly: true });
|
|
111
|
-
const { limit =
|
|
202
|
+
const { limit = defaultLimit, offset = 0, category, difficulty, language } = searchOptions;
|
|
203
|
+
const runs = engineFilter(searchOptions);
|
|
204
|
+
const inCategory = category === void 0 ? { sql: "1 = 1", params: [] } : { sql: "feature = ?", params: [category] };
|
|
112
205
|
const rows = db.prepare(
|
|
113
206
|
`
|
|
114
|
-
SELECT id, title, raw_code, description, feature, engine, created_at
|
|
207
|
+
SELECT id, title, raw_code, description, feature, engine, translatable, created_at
|
|
115
208
|
FROM code_examples
|
|
209
|
+
WHERE (${match.sql}) AND ${runs.sql} AND ${inCategory.sql}
|
|
116
210
|
ORDER BY title
|
|
117
|
-
LIMIT ? OFFSET ?
|
|
118
211
|
`
|
|
119
|
-
).all(
|
|
120
|
-
|
|
212
|
+
).all(...match.params, ...runs.params, ...inCategory.params);
|
|
213
|
+
const inLanguage = language === void 0 ? null : usableIn(db, language);
|
|
214
|
+
return rows.map(mapRowToPattern).filter((pattern) => difficulty === void 0 || pattern.difficulty === difficulty).filter((pattern) => inLanguage === null || inLanguage(pattern)).slice(offset, offset + limit);
|
|
215
|
+
}
|
|
216
|
+
async function searchPatterns(query, searchOptions = {}, connOptions) {
|
|
217
|
+
const like = `%${query}%`;
|
|
218
|
+
const inTranslation = searchOptions.language === void 0 ? { sql: "", params: [] } : {
|
|
219
|
+
sql: " OR id IN (SELECT code_example_id FROM pattern_translations WHERE language = ? AND hyperscript LIKE ?)",
|
|
220
|
+
params: [searchOptions.language, like]
|
|
221
|
+
};
|
|
222
|
+
return queryPatterns(searchOptions, 50, connOptions, {
|
|
223
|
+
sql: `title LIKE ? OR raw_code LIKE ? OR description LIKE ?${inTranslation.sql}`,
|
|
224
|
+
params: [like, like, like, ...inTranslation.params]
|
|
225
|
+
});
|
|
226
|
+
}
|
|
227
|
+
async function getAllPatterns(searchOptions = {}, connOptions) {
|
|
228
|
+
return queryPatterns(searchOptions, 1e3, connOptions);
|
|
121
229
|
}
|
|
122
230
|
async function getPatternStats(connOptions) {
|
|
123
231
|
const db = getDatabase({ ...connOptions, readonly: true });
|
|
@@ -172,6 +280,7 @@ function mapRowToPattern(row) {
|
|
|
172
280
|
tags: extractTags(row.raw_code),
|
|
173
281
|
difficulty: inferDifficulty(row.raw_code),
|
|
174
282
|
engine: row.engine || null,
|
|
283
|
+
translatable: row.translatable !== 0,
|
|
175
284
|
createdAt: new Date(row.created_at)
|
|
176
285
|
};
|
|
177
286
|
}
|
|
@@ -196,6 +305,7 @@ function inferDifficulty(code) {
|
|
|
196
305
|
}
|
|
197
306
|
|
|
198
307
|
// src/api/translations.ts
|
|
308
|
+
init_cjs_shims();
|
|
199
309
|
async function getTranslation(patternId, language, options) {
|
|
200
310
|
const db = getDatabase({ ...options, readonly: true });
|
|
201
311
|
const row = db.prepare(
|
|
@@ -257,32 +367,35 @@ async function verifyTranslation(translation, options) {
|
|
|
257
367
|
let parseSuccess = false;
|
|
258
368
|
let errorMessage = null;
|
|
259
369
|
let confidence = translation.confidence;
|
|
370
|
+
const db = getDatabase(options);
|
|
371
|
+
const example = db.prepare("SELECT translatable FROM code_examples WHERE id = ?").get(translation.codeExampleId);
|
|
260
372
|
try {
|
|
261
|
-
const {
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
373
|
+
const { verifyParses: verifyParses2 } = await Promise.resolve().then(() => (init_verify_parses(), verify_parses_exports));
|
|
374
|
+
parseSuccess = verifyParses2(
|
|
375
|
+
translation.hyperscript,
|
|
376
|
+
translation.language,
|
|
377
|
+
example?.translatable !== 0
|
|
378
|
+
);
|
|
379
|
+
if (!parseSuccess) errorMessage = "the semantic parser rejected it (or it has no hyperscript)";
|
|
268
380
|
} catch (e) {
|
|
269
381
|
errorMessage = e.message;
|
|
270
382
|
}
|
|
271
|
-
|
|
272
|
-
|
|
383
|
+
db.transaction(() => {
|
|
384
|
+
db.prepare(
|
|
385
|
+
`
|
|
386
|
+
UPDATE pattern_translations
|
|
387
|
+
SET verified_parses = ?, updated_at = datetime('now')
|
|
388
|
+
WHERE id = ?
|
|
273
389
|
`
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
390
|
+
).run(parseSuccess ? 1 : 0, translation.id);
|
|
391
|
+
db.prepare(
|
|
392
|
+
`
|
|
393
|
+
INSERT INTO pattern_tests
|
|
394
|
+
(code_example_id, language, test_type, success, error_message, test_date)
|
|
395
|
+
VALUES (?, ?, 'parse', ?, ?, datetime('now'))
|
|
280
396
|
`
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
VALUES (?, ?, datetime('now'), ?, ?)
|
|
284
|
-
`
|
|
285
|
-
).run(translation.codeExampleId, translation.language, parseSuccess ? 1 : 0, errorMessage);
|
|
397
|
+
).run(translation.codeExampleId, translation.language, parseSuccess ? 1 : 0, errorMessage);
|
|
398
|
+
})();
|
|
286
399
|
return {
|
|
287
400
|
translation,
|
|
288
401
|
parseSuccess,
|
|
@@ -352,74 +465,70 @@ function getWordOrder(language) {
|
|
|
352
465
|
}
|
|
353
466
|
|
|
354
467
|
// src/api/llm.ts
|
|
468
|
+
init_cjs_shims();
|
|
469
|
+
var EXAMPLES_FROM = `
|
|
470
|
+
SELECT le.*, ce.engine AS engine
|
|
471
|
+
FROM llm_examples le
|
|
472
|
+
JOIN code_examples ce ON ce.id = le.code_example_id`;
|
|
355
473
|
async function getLLMExamples(prompt, language = "en", limit = 5, options) {
|
|
356
474
|
const db = getDatabase({ ...options, readonly: true });
|
|
475
|
+
const runs = exampleCondition("ce.engine", options?.engine);
|
|
357
476
|
const keywords = extractKeywords(prompt);
|
|
358
477
|
if (keywords.length === 0) {
|
|
359
478
|
const rows2 = db.prepare(
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
ORDER BY quality_score DESC, usage_count DESC
|
|
479
|
+
`${EXAMPLES_FROM}
|
|
480
|
+
WHERE le.language = ? AND ${runs.sql}
|
|
481
|
+
ORDER BY le.quality_score DESC, le.usage_count DESC
|
|
364
482
|
LIMIT ?
|
|
365
483
|
`
|
|
366
|
-
).all(language, limit);
|
|
367
|
-
trackUsage(
|
|
368
|
-
db,
|
|
369
|
-
rows2.map((r) => r.id)
|
|
370
|
-
);
|
|
484
|
+
).all(language, ...runs.params, limit);
|
|
371
485
|
return rows2.map(mapRowToLLMExample);
|
|
372
486
|
}
|
|
373
|
-
const likeClauses = keywords.map(() => "(prompt LIKE ? OR completion LIKE ?)").join(" OR ");
|
|
487
|
+
const likeClauses = keywords.map(() => "(le.prompt LIKE ? OR le.completion LIKE ?)").join(" OR ");
|
|
374
488
|
const params = keywords.flatMap((k) => [`%${k}%`, `%${k}%`]);
|
|
375
489
|
const rows = db.prepare(
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
ORDER BY quality_score DESC
|
|
490
|
+
`${EXAMPLES_FROM}
|
|
491
|
+
WHERE le.language = ? AND ${runs.sql} AND (${likeClauses})
|
|
492
|
+
ORDER BY le.quality_score DESC
|
|
380
493
|
LIMIT ?
|
|
381
494
|
`
|
|
382
|
-
).all(language, ...params, limit);
|
|
383
|
-
trackUsage(
|
|
384
|
-
db,
|
|
385
|
-
rows.map((r) => r.id)
|
|
386
|
-
);
|
|
495
|
+
).all(language, ...runs.params, ...params, limit);
|
|
387
496
|
return rows.map(mapRowToLLMExample);
|
|
388
497
|
}
|
|
389
498
|
async function getExamplesByCommand(command, language = "en", limit = 5, options) {
|
|
390
499
|
const db = getDatabase({ ...options, readonly: true });
|
|
500
|
+
const runs = exampleCondition("ce.engine", options?.engine);
|
|
391
501
|
const rows = db.prepare(
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
ORDER BY quality_score DESC
|
|
502
|
+
`${EXAMPLES_FROM}
|
|
503
|
+
WHERE le.language = ? AND ${runs.sql} AND le.completion LIKE ?
|
|
504
|
+
ORDER BY le.quality_score DESC
|
|
396
505
|
LIMIT ?
|
|
397
506
|
`
|
|
398
|
-
).all(language, `%${command}%`, limit);
|
|
507
|
+
).all(language, ...runs.params, `%${command}%`, limit);
|
|
399
508
|
return rows.map(mapRowToLLMExample);
|
|
400
509
|
}
|
|
401
510
|
async function getHighQualityExamples(language = "en", minQuality = 0.8, limit = 10, options) {
|
|
402
511
|
const db = getDatabase({ ...options, readonly: true });
|
|
512
|
+
const runs = exampleCondition("ce.engine", options?.engine);
|
|
403
513
|
const rows = db.prepare(
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
ORDER BY quality_score DESC, usage_count DESC
|
|
514
|
+
`${EXAMPLES_FROM}
|
|
515
|
+
WHERE le.language = ? AND ${runs.sql} AND le.quality_score >= ?
|
|
516
|
+
ORDER BY le.quality_score DESC, le.usage_count DESC
|
|
408
517
|
LIMIT ?
|
|
409
518
|
`
|
|
410
|
-
).all(language, minQuality, limit);
|
|
519
|
+
).all(language, ...runs.params, minQuality, limit);
|
|
411
520
|
return rows.map(mapRowToLLMExample);
|
|
412
521
|
}
|
|
413
522
|
async function getMostUsedExamples(language = "en", limit = 10, options) {
|
|
414
523
|
const db = getDatabase({ ...options, readonly: true });
|
|
524
|
+
const runs = exampleCondition("ce.engine", options?.engine);
|
|
415
525
|
const rows = db.prepare(
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
ORDER BY usage_count DESC, quality_score DESC
|
|
526
|
+
`${EXAMPLES_FROM}
|
|
527
|
+
WHERE le.language = ? AND ${runs.sql}
|
|
528
|
+
ORDER BY le.usage_count DESC, le.quality_score DESC
|
|
420
529
|
LIMIT ?
|
|
421
530
|
`
|
|
422
|
-
).all(language, limit);
|
|
531
|
+
).all(language, ...runs.params, limit);
|
|
423
532
|
return rows.map(mapRowToLLMExample);
|
|
424
533
|
}
|
|
425
534
|
async function buildFewShotContext(prompt, language = "en", numExamples = 3, options) {
|
|
@@ -517,18 +626,6 @@ function extractKeywords(prompt) {
|
|
|
517
626
|
]);
|
|
518
627
|
return prompt.toLowerCase().split(/\W+/).filter((word) => word.length > 2 && !stopWords.has(word));
|
|
519
628
|
}
|
|
520
|
-
function trackUsage(db, ids) {
|
|
521
|
-
if (ids.length === 0) return;
|
|
522
|
-
try {
|
|
523
|
-
const stmt = db.prepare(`
|
|
524
|
-
UPDATE llm_examples SET usage_count = usage_count + 1 WHERE id = ?
|
|
525
|
-
`);
|
|
526
|
-
for (const id of ids) {
|
|
527
|
-
stmt.run(id);
|
|
528
|
-
}
|
|
529
|
-
} catch {
|
|
530
|
-
}
|
|
531
|
-
}
|
|
532
629
|
function mapRowToLLMExample(row) {
|
|
533
630
|
return {
|
|
534
631
|
id: row.id,
|
|
@@ -538,11 +635,13 @@ function mapRowToLLMExample(row) {
|
|
|
538
635
|
completion: row.completion,
|
|
539
636
|
qualityScore: row.quality_score,
|
|
540
637
|
usageCount: row.usage_count,
|
|
541
|
-
createdAt: new Date(row.created_at)
|
|
638
|
+
createdAt: new Date(row.created_at),
|
|
639
|
+
engine: row.engine ?? null
|
|
542
640
|
};
|
|
543
641
|
}
|
|
544
642
|
|
|
545
643
|
// src/api/roles.ts
|
|
644
|
+
init_cjs_shims();
|
|
546
645
|
async function getPatternRoles(patternId, options) {
|
|
547
646
|
const db = getDatabase({ ...options, readonly: true });
|
|
548
647
|
const rows = db.prepare(
|
|
@@ -559,7 +658,7 @@ async function getPatternsByRole(role, options) {
|
|
|
559
658
|
const db = getDatabase({ ...options, readonly: true });
|
|
560
659
|
const rows = db.prepare(
|
|
561
660
|
`
|
|
562
|
-
SELECT DISTINCT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.created_at
|
|
661
|
+
SELECT DISTINCT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.translatable, ce.created_at
|
|
563
662
|
FROM code_examples ce
|
|
564
663
|
INNER JOIN pattern_roles pr ON ce.id = pr.code_example_id
|
|
565
664
|
WHERE pr.role = ?
|
|
@@ -575,7 +674,7 @@ async function getPatternsByRoles(roles, matchMode = "any", options) {
|
|
|
575
674
|
const placeholders = roles.map(() => "?").join(", ");
|
|
576
675
|
const rows = db.prepare(
|
|
577
676
|
`
|
|
578
|
-
SELECT DISTINCT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.created_at
|
|
677
|
+
SELECT DISTINCT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.translatable, ce.created_at
|
|
579
678
|
FROM code_examples ce
|
|
580
679
|
INNER JOIN pattern_roles pr ON ce.id = pr.code_example_id
|
|
581
680
|
WHERE pr.role IN (${placeholders})
|
|
@@ -587,7 +686,7 @@ async function getPatternsByRoles(roles, matchMode = "any", options) {
|
|
|
587
686
|
const placeholders = roles.map(() => "?").join(", ");
|
|
588
687
|
const rows = db.prepare(
|
|
589
688
|
`
|
|
590
|
-
SELECT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.created_at
|
|
689
|
+
SELECT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.translatable, ce.created_at
|
|
591
690
|
FROM code_examples ce
|
|
592
691
|
WHERE (
|
|
593
692
|
SELECT COUNT(DISTINCT pr.role)
|
|
@@ -604,7 +703,7 @@ async function getPatternsByRoleValue(role, value, options) {
|
|
|
604
703
|
const db = getDatabase({ ...options, readonly: true });
|
|
605
704
|
const rows = db.prepare(
|
|
606
705
|
`
|
|
607
|
-
SELECT DISTINCT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.created_at
|
|
706
|
+
SELECT DISTINCT ce.id, ce.title, ce.raw_code, ce.description, ce.feature, ce.engine, ce.translatable, ce.created_at
|
|
608
707
|
FROM code_examples ce
|
|
609
708
|
INNER JOIN pattern_roles pr ON ce.id = pr.code_example_id
|
|
610
709
|
WHERE pr.role = ? AND pr.role_value LIKE ?
|
|
@@ -737,6 +836,7 @@ function mapRowToPattern2(row) {
|
|
|
737
836
|
tags: extractTags2(row.raw_code),
|
|
738
837
|
difficulty: inferDifficulty2(row.raw_code),
|
|
739
838
|
engine: row.engine || null,
|
|
839
|
+
translatable: row.translatable !== 0,
|
|
740
840
|
createdAt: new Date(row.created_at)
|
|
741
841
|
};
|
|
742
842
|
}
|