zig-pug 0.2.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.
Files changed (46) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +346 -0
  3. package/binding.c +375 -0
  4. package/binding.gyp +28 -0
  5. package/common.gypi +5 -0
  6. package/include/zigpug.h +135 -0
  7. package/index.js +205 -0
  8. package/package.json +87 -0
  9. package/vendor/mujs/COPYING +16 -0
  10. package/vendor/mujs/README +50 -0
  11. package/vendor/mujs/astnames.h +92 -0
  12. package/vendor/mujs/jsarray.c +832 -0
  13. package/vendor/mujs/jsboolean.c +38 -0
  14. package/vendor/mujs/jsbuiltin.c +249 -0
  15. package/vendor/mujs/jscompile.c +1428 -0
  16. package/vendor/mujs/jsdate.c +861 -0
  17. package/vendor/mujs/jsdtoa.c +749 -0
  18. package/vendor/mujs/jserror.c +139 -0
  19. package/vendor/mujs/jsfunction.c +231 -0
  20. package/vendor/mujs/jsgc.c +284 -0
  21. package/vendor/mujs/jsi.h +870 -0
  22. package/vendor/mujs/jsintern.c +137 -0
  23. package/vendor/mujs/jslex.c +878 -0
  24. package/vendor/mujs/jsmath.c +194 -0
  25. package/vendor/mujs/jsnumber.c +198 -0
  26. package/vendor/mujs/jsobject.c +560 -0
  27. package/vendor/mujs/json.c +422 -0
  28. package/vendor/mujs/jsparse.c +1065 -0
  29. package/vendor/mujs/jsproperty.c +341 -0
  30. package/vendor/mujs/jsregexp.c +232 -0
  31. package/vendor/mujs/jsrepr.c +285 -0
  32. package/vendor/mujs/jsrun.c +2096 -0
  33. package/vendor/mujs/jsstate.c +334 -0
  34. package/vendor/mujs/jsstring.c +852 -0
  35. package/vendor/mujs/jsvalue.c +708 -0
  36. package/vendor/mujs/libmujs.a +0 -0
  37. package/vendor/mujs/main.c +396 -0
  38. package/vendor/mujs/mujs.h +253 -0
  39. package/vendor/mujs/one.c +25 -0
  40. package/vendor/mujs/opnames.h +85 -0
  41. package/vendor/mujs/pp.c +980 -0
  42. package/vendor/mujs/regexp.c +1277 -0
  43. package/vendor/mujs/regexp.h +46 -0
  44. package/vendor/mujs/utf.c +305 -0
  45. package/vendor/mujs/utf.h +52 -0
  46. package/vendor/mujs/utfdata.h +2209 -0
package/binding.c ADDED
@@ -0,0 +1,375 @@
1
+ /*
2
+ * Node.js N-API binding for zig-pug
3
+ * This file creates a native Node.js addon that exposes zig-pug functionality
4
+ */
5
+
6
+ #include <node_api.h>
7
+ #include <string.h>
8
+ #include <stdlib.h>
9
+
10
+ // Forward declarations of zig-pug C API
11
+ // These are defined in src/lib.zig and exported via the C FFI
12
+ typedef struct ZigPugContext ZigPugContext;
13
+
14
+ extern ZigPugContext* zigpug_init(void);
15
+ extern void zigpug_free(ZigPugContext* ctx);
16
+ extern char* zigpug_compile(ZigPugContext* ctx, const char* pug_source);
17
+ extern int zigpug_set_string(ZigPugContext* ctx, const char* key, const char* value);
18
+ extern int zigpug_set_int(ZigPugContext* ctx, const char* key, long long value);
19
+ extern int zigpug_set_bool(ZigPugContext* ctx, const char* key, int value);
20
+ extern void zigpug_free_string(char* str);
21
+ extern const char* zigpug_version(void);
22
+
23
+ // Wrapper for ZigPugContext to store in JavaScript
24
+ typedef struct {
25
+ ZigPugContext* ctx;
26
+ } PugContextWrapper;
27
+
28
+ // Finalizer for context when garbage collected
29
+ static void context_finalizer(napi_env env, void* finalize_data, void* finalize_hint) {
30
+ (void)env;
31
+ (void)finalize_hint;
32
+
33
+ PugContextWrapper* wrapper = (PugContextWrapper*)finalize_data;
34
+ if (wrapper && wrapper->ctx) {
35
+ zigpug_free(wrapper->ctx);
36
+ }
37
+ free(wrapper);
38
+ }
39
+
40
+ // Create a new Pug context
41
+ // JavaScript: const ctx = zigpug.createContext()
42
+ static napi_value CreateContext(napi_env env, napi_callback_info info) {
43
+ (void)info;
44
+
45
+ napi_status status;
46
+ napi_value result;
47
+
48
+ // Initialize zig-pug context
49
+ ZigPugContext* ctx = zigpug_init();
50
+ if (!ctx) {
51
+ napi_throw_error(env, NULL, "Failed to initialize zig-pug context");
52
+ return NULL;
53
+ }
54
+
55
+ // Wrap in our structure
56
+ PugContextWrapper* wrapper = malloc(sizeof(PugContextWrapper));
57
+ if (!wrapper) {
58
+ zigpug_free(ctx);
59
+ napi_throw_error(env, NULL, "Out of memory");
60
+ return NULL;
61
+ }
62
+ wrapper->ctx = ctx;
63
+
64
+ // Create JavaScript external object
65
+ status = napi_create_external(env, wrapper, context_finalizer, NULL, &result);
66
+ if (status != napi_ok) {
67
+ zigpug_free(ctx);
68
+ free(wrapper);
69
+ napi_throw_error(env, NULL, "Failed to create external object");
70
+ return NULL;
71
+ }
72
+
73
+ return result;
74
+ }
75
+
76
+ // Set a string variable
77
+ // JavaScript: zigpug.setString(ctx, 'name', 'Alice')
78
+ static napi_value SetString(napi_env env, napi_callback_info info) {
79
+ napi_status status;
80
+ size_t argc = 3;
81
+ napi_value args[3];
82
+
83
+ status = napi_get_cb_info(env, info, &argc, args, NULL, NULL);
84
+ if (status != napi_ok || argc < 3) {
85
+ napi_throw_error(env, NULL, "Expected 3 arguments: context, key, value");
86
+ return NULL;
87
+ }
88
+
89
+ // Get context
90
+ PugContextWrapper* wrapper;
91
+ status = napi_get_value_external(env, args[0], (void**)&wrapper);
92
+ if (status != napi_ok || !wrapper || !wrapper->ctx) {
93
+ napi_throw_error(env, NULL, "Invalid context");
94
+ return NULL;
95
+ }
96
+
97
+ // Get key string
98
+ size_t key_len;
99
+ status = napi_get_value_string_utf8(env, args[1], NULL, 0, &key_len);
100
+ if (status != napi_ok) {
101
+ napi_throw_error(env, NULL, "Invalid key");
102
+ return NULL;
103
+ }
104
+
105
+ char* key = malloc(key_len + 1);
106
+ status = napi_get_value_string_utf8(env, args[1], key, key_len + 1, &key_len);
107
+ if (status != napi_ok) {
108
+ free(key);
109
+ napi_throw_error(env, NULL, "Failed to get key string");
110
+ return NULL;
111
+ }
112
+
113
+ // Get value string
114
+ size_t value_len;
115
+ status = napi_get_value_string_utf8(env, args[2], NULL, 0, &value_len);
116
+ if (status != napi_ok) {
117
+ free(key);
118
+ napi_throw_error(env, NULL, "Invalid value");
119
+ return NULL;
120
+ }
121
+
122
+ char* value = malloc(value_len + 1);
123
+ status = napi_get_value_string_utf8(env, args[2], value, value_len + 1, &value_len);
124
+ if (status != napi_ok) {
125
+ free(key);
126
+ free(value);
127
+ napi_throw_error(env, NULL, "Failed to get value string");
128
+ return NULL;
129
+ }
130
+
131
+ // Set in zig-pug
132
+ int result = zigpug_set_string(wrapper->ctx, key, value);
133
+
134
+ free(key);
135
+ free(value);
136
+
137
+ napi_value js_result;
138
+ status = napi_get_boolean(env, result != 0, &js_result);
139
+ return js_result;
140
+ }
141
+
142
+ // Set a number variable
143
+ // JavaScript: zigpug.setNumber(ctx, 'age', 25)
144
+ static napi_value SetNumber(napi_env env, napi_callback_info info) {
145
+ napi_status status;
146
+ size_t argc = 3;
147
+ napi_value args[3];
148
+
149
+ status = napi_get_cb_info(env, info, &argc, args, NULL, NULL);
150
+ if (status != napi_ok || argc < 3) {
151
+ napi_throw_error(env, NULL, "Expected 3 arguments: context, key, value");
152
+ return NULL;
153
+ }
154
+
155
+ // Get context
156
+ PugContextWrapper* wrapper;
157
+ status = napi_get_value_external(env, args[0], (void**)&wrapper);
158
+ if (status != napi_ok || !wrapper || !wrapper->ctx) {
159
+ napi_throw_error(env, NULL, "Invalid context");
160
+ return NULL;
161
+ }
162
+
163
+ // Get key string
164
+ size_t key_len;
165
+ status = napi_get_value_string_utf8(env, args[1], NULL, 0, &key_len);
166
+ if (status != napi_ok) {
167
+ napi_throw_error(env, NULL, "Invalid key");
168
+ return NULL;
169
+ }
170
+
171
+ char* key = malloc(key_len + 1);
172
+ status = napi_get_value_string_utf8(env, args[1], key, key_len + 1, &key_len);
173
+ if (status != napi_ok) {
174
+ free(key);
175
+ napi_throw_error(env, NULL, "Failed to get key string");
176
+ return NULL;
177
+ }
178
+
179
+ // Get number value
180
+ int64_t value;
181
+ status = napi_get_value_int64(env, args[2], &value);
182
+ if (status != napi_ok) {
183
+ free(key);
184
+ napi_throw_error(env, NULL, "Invalid number value");
185
+ return NULL;
186
+ }
187
+
188
+ // Set in zig-pug
189
+ int result = zigpug_set_int(wrapper->ctx, key, value);
190
+
191
+ free(key);
192
+
193
+ napi_value js_result;
194
+ status = napi_get_boolean(env, result != 0, &js_result);
195
+ return js_result;
196
+ }
197
+
198
+ // Set a boolean variable
199
+ // JavaScript: zigpug.setBool(ctx, 'active', true)
200
+ static napi_value SetBool(napi_env env, napi_callback_info info) {
201
+ napi_status status;
202
+ size_t argc = 3;
203
+ napi_value args[3];
204
+
205
+ status = napi_get_cb_info(env, info, &argc, args, NULL, NULL);
206
+ if (status != napi_ok || argc < 3) {
207
+ napi_throw_error(env, NULL, "Expected 3 arguments: context, key, value");
208
+ return NULL;
209
+ }
210
+
211
+ // Get context
212
+ PugContextWrapper* wrapper;
213
+ status = napi_get_value_external(env, args[0], (void**)&wrapper);
214
+ if (status != napi_ok || !wrapper || !wrapper->ctx) {
215
+ napi_throw_error(env, NULL, "Invalid context");
216
+ return NULL;
217
+ }
218
+
219
+ // Get key string
220
+ size_t key_len;
221
+ status = napi_get_value_string_utf8(env, args[1], NULL, 0, &key_len);
222
+ if (status != napi_ok) {
223
+ napi_throw_error(env, NULL, "Invalid key");
224
+ return NULL;
225
+ }
226
+
227
+ char* key = malloc(key_len + 1);
228
+ status = napi_get_value_string_utf8(env, args[1], key, key_len + 1, &key_len);
229
+ if (status != napi_ok) {
230
+ free(key);
231
+ napi_throw_error(env, NULL, "Failed to get key string");
232
+ return NULL;
233
+ }
234
+
235
+ // Get boolean value
236
+ bool value;
237
+ status = napi_get_value_bool(env, args[2], &value);
238
+ if (status != napi_ok) {
239
+ free(key);
240
+ napi_throw_error(env, NULL, "Invalid boolean value");
241
+ return NULL;
242
+ }
243
+
244
+ // Set in zig-pug
245
+ int result = zigpug_set_bool(wrapper->ctx, key, value ? 1 : 0);
246
+
247
+ free(key);
248
+
249
+ napi_value js_result;
250
+ status = napi_get_boolean(env, result != 0, &js_result);
251
+ return js_result;
252
+ }
253
+
254
+ // Compile a Pug template to HTML
255
+ // JavaScript: const html = zigpug.compile(ctx, template)
256
+ static napi_value Compile(napi_env env, napi_callback_info info) {
257
+ napi_status status;
258
+ size_t argc = 2;
259
+ napi_value args[2];
260
+
261
+ status = napi_get_cb_info(env, info, &argc, args, NULL, NULL);
262
+ if (status != napi_ok || argc < 2) {
263
+ napi_throw_error(env, NULL, "Expected 2 arguments: context, template");
264
+ return NULL;
265
+ }
266
+
267
+ // Get context
268
+ PugContextWrapper* wrapper;
269
+ status = napi_get_value_external(env, args[0], (void**)&wrapper);
270
+ if (status != napi_ok || !wrapper || !wrapper->ctx) {
271
+ napi_throw_error(env, NULL, "Invalid context");
272
+ return NULL;
273
+ }
274
+
275
+ // Get template string
276
+ size_t template_len;
277
+ status = napi_get_value_string_utf8(env, args[1], NULL, 0, &template_len);
278
+ if (status != napi_ok) {
279
+ napi_throw_error(env, NULL, "Invalid template");
280
+ return NULL;
281
+ }
282
+
283
+ char* template = malloc(template_len + 1);
284
+ status = napi_get_value_string_utf8(env, args[1], template, template_len + 1, &template_len);
285
+ if (status != napi_ok) {
286
+ free(template);
287
+ napi_throw_error(env, NULL, "Failed to get template string");
288
+ return NULL;
289
+ }
290
+
291
+ // Compile with zig-pug
292
+ char* html = zigpug_compile(wrapper->ctx, template);
293
+ free(template);
294
+
295
+ if (!html) {
296
+ napi_throw_error(env, NULL, "Failed to compile template");
297
+ return NULL;
298
+ }
299
+
300
+ // Create JavaScript string
301
+ napi_value result;
302
+ status = napi_create_string_utf8(env, html, NAPI_AUTO_LENGTH, &result);
303
+ zigpug_free_string(html);
304
+
305
+ if (status != napi_ok) {
306
+ napi_throw_error(env, NULL, "Failed to create result string");
307
+ return NULL;
308
+ }
309
+
310
+ return result;
311
+ }
312
+
313
+ // Get zig-pug version
314
+ // JavaScript: const version = zigpug.version()
315
+ static napi_value Version(napi_env env, napi_callback_info info) {
316
+ (void)info;
317
+
318
+ const char* version = zigpug_version();
319
+
320
+ napi_value result;
321
+ napi_status status = napi_create_string_utf8(env, version, NAPI_AUTO_LENGTH, &result);
322
+
323
+ if (status != napi_ok) {
324
+ napi_throw_error(env, NULL, "Failed to get version");
325
+ return NULL;
326
+ }
327
+
328
+ return result;
329
+ }
330
+
331
+ // Initialize the N-API module
332
+ static napi_value Init(napi_env env, napi_value exports) {
333
+ napi_status status;
334
+ napi_value fn;
335
+
336
+ // createContext
337
+ status = napi_create_function(env, NULL, 0, CreateContext, NULL, &fn);
338
+ if (status != napi_ok) return NULL;
339
+ status = napi_set_named_property(env, exports, "createContext", fn);
340
+ if (status != napi_ok) return NULL;
341
+
342
+ // setString
343
+ status = napi_create_function(env, NULL, 0, SetString, NULL, &fn);
344
+ if (status != napi_ok) return NULL;
345
+ status = napi_set_named_property(env, exports, "setString", fn);
346
+ if (status != napi_ok) return NULL;
347
+
348
+ // setNumber
349
+ status = napi_create_function(env, NULL, 0, SetNumber, NULL, &fn);
350
+ if (status != napi_ok) return NULL;
351
+ status = napi_set_named_property(env, exports, "setNumber", fn);
352
+ if (status != napi_ok) return NULL;
353
+
354
+ // setBool
355
+ status = napi_create_function(env, NULL, 0, SetBool, NULL, &fn);
356
+ if (status != napi_ok) return NULL;
357
+ status = napi_set_named_property(env, exports, "setBool", fn);
358
+ if (status != napi_ok) return NULL;
359
+
360
+ // compile
361
+ status = napi_create_function(env, NULL, 0, Compile, NULL, &fn);
362
+ if (status != napi_ok) return NULL;
363
+ status = napi_set_named_property(env, exports, "compile", fn);
364
+ if (status != napi_ok) return NULL;
365
+
366
+ // version
367
+ status = napi_create_function(env, NULL, 0, Version, NULL, &fn);
368
+ if (status != napi_ok) return NULL;
369
+ status = napi_set_named_property(env, exports, "version", fn);
370
+ if (status != napi_ok) return NULL;
371
+
372
+ return exports;
373
+ }
374
+
375
+ NAPI_MODULE(NODE_GYP_MODULE_NAME, Init)
package/binding.gyp ADDED
@@ -0,0 +1,28 @@
1
+ {
2
+ "targets": [
3
+ {
4
+ "target_name": "zigpug",
5
+ "sources": [
6
+ "binding.c"
7
+ ],
8
+ "include_dirs": [
9
+ "include",
10
+ "../vendor/mujs"
11
+ ],
12
+ "libraries": [
13
+ "-L<(module_root_dir)",
14
+ "-lzigpug",
15
+ "-lm"
16
+ ],
17
+ "cflags": [
18
+ "-std=c99"
19
+ ],
20
+ "defines": [
21
+ "NAPI_VERSION=8"
22
+ ],
23
+ "ldflags": [
24
+ "-Wl,-rpath,'$$ORIGIN'"
25
+ ]
26
+ }
27
+ ]
28
+ }
package/common.gypi ADDED
@@ -0,0 +1,5 @@
1
+ {
2
+ 'variables': {
3
+ 'android_ndk_path%': '/tmp',
4
+ }
5
+ }
@@ -0,0 +1,135 @@
1
+ /**
2
+ * zig-pug - Pug template engine written in Zig
3
+ * C API Header
4
+ *
5
+ * This header provides a C-compatible interface for using zig-pug
6
+ * from C, C++, Python (ctypes/cffi), Node.js (FFI), Rust (FFI), etc.
7
+ */
8
+
9
+ #ifndef ZIGPUG_H
10
+ #define ZIGPUG_H
11
+
12
+ #include <stdint.h>
13
+ #include <stdbool.h>
14
+
15
+ #ifdef __cplusplus
16
+ extern "C" {
17
+ #endif
18
+
19
+ /**
20
+ * Opaque context handle
21
+ * Represents a zig-pug compilation context with runtime state
22
+ */
23
+ typedef struct ZigPugContext ZigPugContext;
24
+
25
+ /**
26
+ * Initialize a new zig-pug context
27
+ *
28
+ * @return Context handle, or NULL on error
29
+ *
30
+ * Example:
31
+ * ZigPugContext* ctx = zigpug_init();
32
+ * if (!ctx) {
33
+ * fprintf(stderr, "Failed to initialize zig-pug\n");
34
+ * return 1;
35
+ * }
36
+ */
37
+ ZigPugContext* zigpug_init(void);
38
+
39
+ /**
40
+ * Free a zig-pug context
41
+ *
42
+ * @param ctx Context handle (can be NULL)
43
+ *
44
+ * Example:
45
+ * zigpug_free(ctx);
46
+ */
47
+ void zigpug_free(ZigPugContext* ctx);
48
+
49
+ /**
50
+ * Compile a Pug template string to HTML
51
+ *
52
+ * @param ctx Context handle
53
+ * @param pug_source Null-terminated Pug template string
54
+ * @return Null-terminated HTML string (must be freed with zigpug_free_string),
55
+ * or NULL on error
56
+ *
57
+ * Example:
58
+ * const char* pug = "div.container\n p Hello #{name}!";
59
+ * char* html = zigpug_compile(ctx, pug);
60
+ * if (html) {
61
+ * printf("%s\n", html);
62
+ * zigpug_free_string(html);
63
+ * }
64
+ */
65
+ char* zigpug_compile(ZigPugContext* ctx, const char* pug_source);
66
+
67
+ /**
68
+ * Set a string variable in the context
69
+ *
70
+ * @param ctx Context handle
71
+ * @param key Variable name (null-terminated)
72
+ * @param value String value (null-terminated)
73
+ * @return true on success, false on error
74
+ *
75
+ * Example:
76
+ * zigpug_set_string(ctx, "name", "John Doe");
77
+ * zigpug_set_string(ctx, "title", "Welcome Page");
78
+ */
79
+ bool zigpug_set_string(ZigPugContext* ctx, const char* key, const char* value);
80
+
81
+ /**
82
+ * Set an integer variable in the context
83
+ *
84
+ * @param ctx Context handle
85
+ * @param key Variable name (null-terminated)
86
+ * @param value Integer value
87
+ * @return true on success, false on error
88
+ *
89
+ * Example:
90
+ * zigpug_set_int(ctx, "count", 42);
91
+ * zigpug_set_int(ctx, "year", 2024);
92
+ */
93
+ bool zigpug_set_int(ZigPugContext* ctx, const char* key, int64_t value);
94
+
95
+ /**
96
+ * Set a boolean variable in the context
97
+ *
98
+ * @param ctx Context handle
99
+ * @param key Variable name (null-terminated)
100
+ * @param value Boolean value
101
+ * @return true on success, false on error
102
+ *
103
+ * Example:
104
+ * zigpug_set_bool(ctx, "loggedIn", true);
105
+ * zigpug_set_bool(ctx, "isAdmin", false);
106
+ */
107
+ bool zigpug_set_bool(ZigPugContext* ctx, const char* key, bool value);
108
+
109
+ /**
110
+ * Free a string returned by zig-pug
111
+ *
112
+ * @param str String to free (can be NULL)
113
+ *
114
+ * Example:
115
+ * char* html = zigpug_compile(ctx, pug_source);
116
+ * // ... use html ...
117
+ * zigpug_free_string(html);
118
+ */
119
+ void zigpug_free_string(char* str);
120
+
121
+ /**
122
+ * Get zig-pug version string
123
+ *
124
+ * @return Version string (do not free)
125
+ *
126
+ * Example:
127
+ * printf("zig-pug version: %s\n", zigpug_version());
128
+ */
129
+ const char* zigpug_version(void);
130
+
131
+ #ifdef __cplusplus
132
+ }
133
+ #endif
134
+
135
+ #endif /* ZIGPUG_H */