@pawel-up/jexl
Version:
Javascript Expression Language: Powerful context-based expression parser and evaluator
187 lines • 7.34 kB
JavaScript
function getTypeStringFromSchema(schema) {
if (schema.type) {
if (Array.isArray(schema.type)) {
return schema.type.join(' | ');
}
return schema.type;
}
if (schema.enum) {
return schema.enum.map((v) => (typeof v === 'string' ? `"${v}"` : String(v))).join(' | ');
}
if (schema.anyOf) {
return schema.anyOf
.map((s) => (typeof s === 'object' && s !== null && !Array.isArray(s) ? getTypeStringFromSchema(s) : 'unknown'))
.join(' | ');
}
if (schema.oneOf) {
return schema.oneOf
.map((s) => (typeof s === 'object' && s !== null && !Array.isArray(s) ? getTypeStringFromSchema(s) : 'unknown'))
.join(' | ');
}
return 'unknown';
}
export function createVSCodeCompletionItems(library) {
return Object.values(library.functions).map((func) => ({
label: func.name,
kind: 3,
detail: func.description,
documentation: {
kind: 'markdown',
value: createVSCodeFunctionDocumentation(func),
},
insertText: func.name,
}));
}
function createVSCodeFunctionDocumentation(func) {
const params = func.parameters.map((p) => `${p.name}: ${getTypeStringFromSchema(p.schema)}`).join(', ');
const returnType = getTypeStringFromSchema(func.returns);
const lines = [`**${func.name}**(${params}) → ${returnType}`, '', func.description, ''];
if (func.examples && func.examples.length > 0) {
lines.push('**Examples:**');
func.examples.forEach((example) => {
lines.push(`\`\`\`typescript\n${example}\n\`\`\``);
});
}
return lines.join('\n');
}
export function createMonacoCompletionItems(library) {
return Object.values(library.functions).map((func) => ({
label: func.name,
kind: 1,
detail: func.description,
documentation: {
value: createMonacoFunctionDocumentation(func),
},
insertText: func.name,
}));
}
function createMonacoFunctionDocumentation(func) {
const params = func.parameters.map((p) => `${p.name}: ${getTypeStringFromSchema(p.schema)}`).join(', ');
const returnType = getTypeStringFromSchema(func.returns);
const lines = [`**${func.name}**(${params}) → ${returnType}`, '', func.description, ''];
if (func.examples && func.examples.length > 0) {
lines.push('**Examples:**');
func.examples.forEach((example) => {
lines.push(`\`${example}\``);
});
}
return lines.join('\n');
}
export function createCodeMirrorCompletionOptions(library) {
return Object.values(library.functions).map((func) => ({
label: func.name,
type: 'function',
info: func.description,
detail: createCodeMirrorFunctionDetail(func),
apply: func.name,
}));
}
function createCodeMirrorFunctionDetail(func) {
const params = func.parameters.map((p) => p.name).join(', ');
return `${func.name}(${params}) → ${func.returns.type}`;
}
export function createLSPCompletionItems(library) {
return Object.values(library.functions).map((func) => ({
label: func.name,
kind: 3,
detail: func.description,
documentation: {
kind: 'markdown',
value: createLSPFunctionDocumentation(func),
},
}));
}
function createLSPFunctionDocumentation(func) {
const params = func.parameters.map((p) => `${p.name}: ${getTypeStringFromSchema(p.schema)}`).join(', ');
const returnType = getTypeStringFromSchema(func.returns);
const lines = [`**${func.name}**(${params}) → ${returnType}`, '', func.description, ''];
if (func.examples && func.examples.length > 0) {
lines.push('**Examples:**');
func.examples.forEach((example) => {
lines.push(`\`${example}\``);
});
}
return lines.join('\n');
}
export function createFunctionCallSchema(func) {
return {
type: 'object',
properties: {
function: { const: func.name },
arguments: {
type: 'array',
items: func.parameters.map((param) => ({
...param.schema,
})),
minItems: func.parameters.filter((p) => p.required).length,
maxItems: func.parameters.some((p) => p.variadic) ? undefined : func.parameters.length,
},
},
required: ['function', 'arguments'],
};
}
export function createLibraryValidationSchemas(library) {
return Object.fromEntries(Object.entries(library.functions).map(([name, func]) => [name, createFunctionCallSchema(func)]));
}
export function generateFunctionTable(library) {
const functions = Object.values(library.functions);
const lines = ['| Function | Arguments | Description |', '|----------|-----------|-------------|'];
functions.forEach((func) => {
const args = func.parameters.map((p) => `${p.name}: ${getTypeStringFromSchema(p.schema)}`).join(', ');
const description = func.description.replace(/\|/g, '\\|');
lines.push(`| \`${func.name}\` | \`(${args})\` | ${description} |`);
});
return lines.join('\n');
}
export function generateFunctionCards(library) {
const functions = Object.values(library.functions);
const cards = functions.map((func) => {
const params = func.parameters.map((p) => `${p.name}: ${getTypeStringFromSchema(p.schema)}`).join(', ');
const examples = func.examples ? func.examples.map((ex) => ` ${ex}`).join('\n') : 'No examples available';
return [
`## ${func.name}`,
'',
`**Signature:** \`${func.name}(${params}) → ${func.returns.type}\``,
'',
`**Description:** ${func.description}`,
'',
'**Examples:**',
'```typescript',
examples,
'```',
'',
].join('\n');
});
return cards.join('\n---\n\n');
}
export function registerFunctions(jexl, library, functionModule) {
Object.entries(library.functions).forEach(([name, schema]) => {
const func = functionModule[name];
if (func) {
jexl.addFunction(name, func);
const funcWithMetadata = func;
Object.defineProperty(funcWithMetadata, '_schema', { value: schema, enumerable: false });
Object.defineProperty(funcWithMetadata, '_category', { value: schema.category, enumerable: false });
Object.defineProperty(funcWithMetadata, '_parameters', { value: schema.parameters, enumerable: false });
Object.defineProperty(funcWithMetadata, '_returns', { value: schema.returns, enumerable: false });
}
});
}
export function getFunctionMetadata(func) {
return func._schema;
}
export function listFunctionsByCategory(jexl) {
const categorized = {};
if (jexl._functions) {
Object.entries(jexl._functions).forEach(([name, func]) => {
const funcWithMetadata = func;
const category = funcWithMetadata._category || 'uncategorised';
if (!categorized[category]) {
categorized[category] = [];
}
categorized[category].push(name);
});
}
return categorized;
}
//# sourceMappingURL=integrations.js.map