plusui-native-bindgen 0.1.7 → 0.1.9
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/package.json +7 -4
- package/src/advanced-bindgen.js +642 -449
- package/src/index.js +0 -153
- package/src/test-interface-regex.js +0 -44
- package/src/test-regex.js +0 -35
- package/src/typescript-first-bindgen.js +0 -743
package/src/index.js
DELETED
|
@@ -1,153 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
|
|
3
|
-
import { readFile, writeFile, readdir, mkdir } from 'fs/promises';
|
|
4
|
-
import { existsSync } from 'fs';
|
|
5
|
-
import { join, basename } from 'path';
|
|
6
|
-
|
|
7
|
-
const TS_TYPE_MAP = {
|
|
8
|
-
'string': 'std::string',
|
|
9
|
-
'number': 'double',
|
|
10
|
-
'boolean': 'bool',
|
|
11
|
-
'void': 'void',
|
|
12
|
-
'any': 'std::string',
|
|
13
|
-
'unknown': 'std::string',
|
|
14
|
-
'null': 'std::nullptr_t',
|
|
15
|
-
};
|
|
16
|
-
|
|
17
|
-
function parseType(tsType) {
|
|
18
|
-
const baseType = tsType.replace(/\[\]/g, '');
|
|
19
|
-
const isArray = tsType.endsWith('[]');
|
|
20
|
-
|
|
21
|
-
if (TS_TYPE_MAP[baseType]) {
|
|
22
|
-
const cppType = TS_TYPE_MAP[baseType];
|
|
23
|
-
return isArray ? `std::vector<${cppType}>` : cppType;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
return 'std::string';
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
function parseService(content, filename) {
|
|
30
|
-
const className = basename(filename, '.ts');
|
|
31
|
-
const methods = [];
|
|
32
|
-
const events = [];
|
|
33
|
-
|
|
34
|
-
const methodRegex = /(?:async\s+)?(\w+)\s*\([^)]*\)\s*(?::\s*(\w+))?/g;
|
|
35
|
-
let match;
|
|
36
|
-
|
|
37
|
-
while ((match = methodRegex.exec(content)) !== null) {
|
|
38
|
-
if (match[1] === 'constructor' || match[1] === 'on' || match[1] === 'emit') continue;
|
|
39
|
-
if (content.includes('@event')) {
|
|
40
|
-
events.push({ name: match[1], returnType: match[2] || 'void' });
|
|
41
|
-
} else {
|
|
42
|
-
methods.push({ name: match[1], returnType: match[2] || 'any' });
|
|
43
|
-
}
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
return { className, methods, events };
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
function generateCppBindings(services) {
|
|
50
|
-
let code = `// Auto-generated by plusui-bindgen
|
|
51
|
-
#ifndef PLUSUI_BINDINGS_H
|
|
52
|
-
#define PLUSUI_BINDINGS_H
|
|
53
|
-
|
|
54
|
-
#include <plusui/app.hpp>
|
|
55
|
-
#include <functional>
|
|
56
|
-
#include <string>
|
|
57
|
-
|
|
58
|
-
namespace plusui::bindings {
|
|
59
|
-
|
|
60
|
-
`;
|
|
61
|
-
|
|
62
|
-
for (const service of services) {
|
|
63
|
-
code += `// Service: ${service.className}\n`;
|
|
64
|
-
|
|
65
|
-
for (const method of service.methods) {
|
|
66
|
-
const returnType = parseType(method.returnType);
|
|
67
|
-
code += `inline ${returnType} ${service.className}_${method.name}(const std::string& args) {
|
|
68
|
-
// TODO: Implement ${service.className}.${method.name}
|
|
69
|
-
return ${returnType === 'void' ? '' : 'std::string()'};
|
|
70
|
-
}\n\n`;
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
code += `inline void register_${service.className}(WebView& wv) {\n`;
|
|
74
|
-
for (const method of service.methods) {
|
|
75
|
-
code += ` wv.expose("${service.className.toLowerCase()}_${method.name}", ${service.className}_${method.name});\n`;
|
|
76
|
-
}
|
|
77
|
-
code += `}\n\n`;
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
code += `} // namespace plusui::bindings
|
|
81
|
-
|
|
82
|
-
#endif
|
|
83
|
-
`;
|
|
84
|
-
return code;
|
|
85
|
-
}
|
|
86
|
-
|
|
87
|
-
function generateTsTypes(services) {
|
|
88
|
-
let code = `// Auto-generated by plusui-bindgen
|
|
89
|
-
`;
|
|
90
|
-
|
|
91
|
-
for (const service of services) {
|
|
92
|
-
code += `export class ${service.className}Service {\n`;
|
|
93
|
-
|
|
94
|
-
for (const method of service.methods) {
|
|
95
|
-
code += ` async ${method.name}(...args: unknown[]): Promise<unknown>;\n`;
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
code += `}\n\n`;
|
|
99
|
-
}
|
|
100
|
-
|
|
101
|
-
code += `export const services: {\n`;
|
|
102
|
-
for (const service of services) {
|
|
103
|
-
code += ` ${service.className.toLowerCase()}: ${service.className}Service;\n`;
|
|
104
|
-
}
|
|
105
|
-
code += `};\n`;
|
|
106
|
-
|
|
107
|
-
return code;
|
|
108
|
-
}
|
|
109
|
-
|
|
110
|
-
async function scanServices(dir) {
|
|
111
|
-
const services = [];
|
|
112
|
-
|
|
113
|
-
try {
|
|
114
|
-
const files = await readdir(dir);
|
|
115
|
-
|
|
116
|
-
for (const file of files) {
|
|
117
|
-
if (file.endsWith('.service.ts')) {
|
|
118
|
-
const content = await readFile(join(dir, file), 'utf-8');
|
|
119
|
-
services.push(parseService(content, file));
|
|
120
|
-
}
|
|
121
|
-
}
|
|
122
|
-
} catch (e) {
|
|
123
|
-
console.log('No services directory found');
|
|
124
|
-
}
|
|
125
|
-
|
|
126
|
-
return services;
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
async function generateBindings(servicesDir = './src/services', outputDir = './src') {
|
|
130
|
-
console.log('Scanning for services...');
|
|
131
|
-
const services = await scanServices(servicesDir);
|
|
132
|
-
|
|
133
|
-
if (services.length === 0) {
|
|
134
|
-
console.log('No .service.ts files found');
|
|
135
|
-
return;
|
|
136
|
-
}
|
|
137
|
-
|
|
138
|
-
console.log(`Found ${services.length} service(s)`);
|
|
139
|
-
|
|
140
|
-
const cppCode = generateCppBindings(services);
|
|
141
|
-
await writeFile(join(outputDir, 'bindings.gen.hpp'), cppCode);
|
|
142
|
-
console.log('Generated: bindings.gen.hpp');
|
|
143
|
-
|
|
144
|
-
const tsCode = generateTsTypes(services);
|
|
145
|
-
await writeFile(join(outputDir, 'bindings.gen.ts'), tsCode);
|
|
146
|
-
console.log('Generated: bindings.gen.ts');
|
|
147
|
-
}
|
|
148
|
-
|
|
149
|
-
const args = process.argv.slice(2);
|
|
150
|
-
const servicesDir = args[0] || './src/services';
|
|
151
|
-
const outputDir = args[1] || './src';
|
|
152
|
-
|
|
153
|
-
generateBindings(servicesDir, outputDir).catch(console.error);
|
|
@@ -1,44 +0,0 @@
|
|
|
1
|
-
// Test interface regex
|
|
2
|
-
|
|
3
|
-
console.log('Testing interface regex...\n');
|
|
4
|
-
|
|
5
|
-
const interfaceRegex = /export\s+interface\s+(\w+)\s*\{([^}]+(?:\{[^}]*\}[^}]*)*)\}/g;
|
|
6
|
-
|
|
7
|
-
const testContent = `
|
|
8
|
-
/**
|
|
9
|
-
* Application management API
|
|
10
|
-
*/
|
|
11
|
-
export interface AppAPI {
|
|
12
|
-
/**
|
|
13
|
-
* Get application information
|
|
14
|
-
*/
|
|
15
|
-
getInfo(): Promise<{ name: string; version: string }>;
|
|
16
|
-
|
|
17
|
-
/**
|
|
18
|
-
* Quit the application
|
|
19
|
-
*/
|
|
20
|
-
quit(): Promise<void>;
|
|
21
|
-
}
|
|
22
|
-
`;
|
|
23
|
-
|
|
24
|
-
console.log('Test content:');
|
|
25
|
-
console.log(testContent);
|
|
26
|
-
|
|
27
|
-
let match;
|
|
28
|
-
while ((match = interfaceRegex.exec(testContent)) !== null) {
|
|
29
|
-
const name = match[1];
|
|
30
|
-
const body = match[2];
|
|
31
|
-
|
|
32
|
-
console.log('\n=== Interface Found ===');
|
|
33
|
-
console.log('Name:', name);
|
|
34
|
-
console.log('\nBody captured:');
|
|
35
|
-
console.log('---START---');
|
|
36
|
-
console.log(body);
|
|
37
|
-
console.log('---END---');
|
|
38
|
-
console.log('\nBody length:', body.length);
|
|
39
|
-
|
|
40
|
-
// Now test if both methods are in the body
|
|
41
|
-
console.log('\nSearching for methods in body...');
|
|
42
|
-
console.log('Contains "getInfo":', body.includes('getInfo'));
|
|
43
|
-
console.log('Contains "quit":', body.includes('quit'));
|
|
44
|
-
}
|
package/src/test-regex.js
DELETED
|
@@ -1,35 +0,0 @@
|
|
|
1
|
-
// Test to demonstrate parser bugs
|
|
2
|
-
|
|
3
|
-
console.log('Testing method regex...\n');
|
|
4
|
-
|
|
5
|
-
const methodRegex = /(\w+)\s*\(([^)]*)\)\s*:\s*Promise<([^>]+)>|(\w+)\s*\(([^)]*)\)\s*:\s*([^;]+)/g;
|
|
6
|
-
|
|
7
|
-
const testBody = `
|
|
8
|
-
/**
|
|
9
|
-
* Get application information
|
|
10
|
-
*/
|
|
11
|
-
getInfo(): Promise<{ name: string; version: string }>;
|
|
12
|
-
|
|
13
|
-
/**
|
|
14
|
-
* Quit the application
|
|
15
|
-
*/
|
|
16
|
-
quit(): Promise<void>;
|
|
17
|
-
`;
|
|
18
|
-
|
|
19
|
-
console.log('Test body:');
|
|
20
|
-
console.log(testBody);
|
|
21
|
-
console.log('\nMatches found:');
|
|
22
|
-
|
|
23
|
-
let match;
|
|
24
|
-
let count = 0;
|
|
25
|
-
while ((match = methodRegex.exec(testBody)) !== null) {
|
|
26
|
-
count++;
|
|
27
|
-
console.log(`\nMatch ${count}:`);
|
|
28
|
-
console.log(' Full match:', match[0]);
|
|
29
|
-
console.log(' Method name:', match[1] || match[4]);
|
|
30
|
-
console.log(' Return type:', match[3] || match[6]);
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
console.log(`\nTotal matches: ${count}`);
|
|
34
|
-
console.log('Expected: 2 (getInfo and quit)');
|
|
35
|
-
console.log('Actual:', count);
|