Hello,
I've made a few helper methods for a common case of creating fixed size
objects/arrays.
They handle freeing the arguments in case any of the other value constructors
fails, which is somewhat inconvenient.
Use case:
...
return qjs_make_object(ctx,
"some_array", qjs_make_array(ctx,
JS_NewString(ctx, "bla bla"),
JS_NewString(ctx, "ble ble"),
JS_UNINITIALIZED,
)),
"success", JS_NewBool(ctx, 1),
"some_string", JS_NewString(ctx, "bla bla"),
"some_value", JS_DupValue(ctx, val),
NULL
);
In case anything fails, everything will be correctly freed.
---------
JSValue qjs_make_array(JSContext* ctx, ...)
{
JSValue obj;
va_list ap;
uint32_t i = 0;
obj = JS_NewArray(ctx);
va_start(ap, ctx);
while (true) {
JSValue el = va_arg(ap, JSValue);
if (JS_IsUninitialized(el)) {
if (JS_IsException(obj))
return JS_EXCEPTION;
if (JS_SetPropertyStr(ctx, obj, "length",
JS_NewInt32(ctx, i)) < 0) {
JS_FreeValue(ctx, obj);
obj = JS_EXCEPTION;
}
return obj;
}
if (JS_IsException(obj)) {
JS_FreeValue(ctx, el);
} else if (JS_IsException(el) || JS_SetPropertyUint32(ctx, obj,
i++, el) < 0) {
JS_FreeValue(ctx, obj);
JS_FreeValue(ctx, el);
obj = JS_EXCEPTION;
}
}
va_end(ap);
return obj;
}
JSValue qjs_make_object(JSContext* ctx, ...)
{
JSValue obj;
va_list ap;
obj = JS_NewObject(ctx);
va_start(ap, ctx);
while (true) {
const char* name = va_arg(ap, const char*);
if (name == NULL)
return obj;
JSValue val = va_arg(ap, JSValue);
if (JS_IsException(obj)) {
JS_FreeValue(ctx, val);
} else if (JS_IsException(val) || JS_SetPropertyStr(ctx, obj,
name, val)) {
JS_FreeValue(ctx, obj);
JS_FreeValue(ctx, val);
obj = JS_EXCEPTION;
}
}
va_end(ap);
return obj;
}
regards,
Ondrej