[njs] HTTP: simplifed r.subrequest() code.
noreply at nginx.com
noreply at nginx.com
Tue Jul 2 02:36:03 UTC 2024
details: https://github.com/nginx/njs/commit/7dda4b2ff1fe605e8d7b2723a0b855d43fe101a8
branches: master
commit: 7dda4b2ff1fe605e8d7b2723a0b855d43fe101a8
user: Dmitry Volyntsev <xeioex at nginx.com>
date: Thu, 27 Jun 2024 23:47:11 -0700
description:
HTTP: simplifed r.subrequest() code.
Moving promise callbacks from ctx->promise_callbacks to
the arguments of ngx_js_event_t.
---
nginx/ngx_http_js_module.c | 246 +++++++++++++--------------------------------
1 file changed, 71 insertions(+), 175 deletions(-)
diff --git a/nginx/ngx_http_js_module.c b/nginx/ngx_http_js_module.c
index 260cd497..0c8a3b11 100644
--- a/nginx/ngx_http_js_module.c
+++ b/nginx/ngx_http_js_module.c
@@ -59,7 +59,6 @@ typedef struct {
njs_opaque_value_t request_body;
njs_opaque_value_t response_body;
ngx_str_t redirect_uri;
- ngx_array_t promise_callbacks;
ngx_int_t filter;
ngx_buf_t *buf;
@@ -216,9 +215,6 @@ static njs_int_t ngx_http_js_periodic_session_variables(njs_vm_t *vm,
njs_value_t *retval);
static njs_int_t ngx_http_js_ext_subrequest(njs_vm_t *vm, njs_value_t *args,
njs_uint_t nargs, njs_index_t unused, njs_value_t *retval);
-static ngx_int_t ngx_http_js_subrequest(ngx_http_request_t *r,
- njs_str_t *uri_arg, njs_str_t *args_arg, njs_function_t *callback,
- ngx_http_request_t **sr);
static ngx_int_t ngx_http_js_subrequest_done(ngx_http_request_t *r,
void *data, ngx_int_t rc);
static njs_int_t ngx_http_js_ext_get_parent(njs_vm_t *vm,
@@ -3049,74 +3045,23 @@ ngx_http_js_periodic_session_variables(njs_vm_t *vm, njs_object_prop_t *prop,
}
-static njs_int_t
-ngx_http_js_promise_trampoline(njs_vm_t *vm, njs_value_t *args,
- njs_uint_t nargs, njs_index_t unused, njs_value_t *retval)
-{
- ngx_uint_t i;
- njs_function_t *callback;
- ngx_http_js_cb_t *cb, *cbs;
- ngx_http_js_ctx_t *ctx;
- ngx_http_request_t *r;
-
- r = njs_vm_external(vm, ngx_http_js_request_proto_id,
- njs_arg(args, nargs, 1));
- ctx = ngx_http_get_module_ctx(r->parent, ngx_http_js_module);
-
- ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
- "js subrequest promise trampoline parent ctx: %p", ctx);
-
- if (ctx == NULL) {
- njs_vm_error(vm, "js subrequest: failed to get the parent context");
- return NJS_ERROR;
- }
-
- cbs = ctx->promise_callbacks.elts;
-
- if (cbs == NULL) {
- goto fail;
- }
-
- cb = NULL;
-
- for (i = 0; i < ctx->promise_callbacks.nelts; i++) {
- if (cbs[i].request == r) {
- cb = &cbs[i];
- cb->request = NULL;
- break;
- }
- }
-
- if (cb == NULL) {
- goto fail;
- }
-
- callback = njs_value_function(njs_value_arg(&cb->callbacks[0]));
-
- return njs_vm_call(vm, callback, njs_argument(args, 1), 1);
-
-fail:
-
- njs_vm_error(vm, "js subrequest: promise callback not found");
-
- return NJS_ERROR;
-}
-
-
static njs_int_t
ngx_http_js_ext_subrequest(njs_vm_t *vm, njs_value_t *args, njs_uint_t nargs,
njs_index_t unused, njs_value_t *retval)
{
- ngx_int_t rc, promise;
- njs_str_t uri_arg, args_arg, method_name, body_arg;
- ngx_uint_t i, method, methods_max, has_body, detached;
- njs_value_t *value, *arg, *options;
- njs_function_t *callback;
- ngx_http_js_cb_t *cb, *cbs;
- ngx_http_js_ctx_t *ctx;
- njs_opaque_value_t lvalue;
- ngx_http_request_t *r, *sr;
- ngx_http_request_body_t *rb;
+ ngx_int_t rc, flags;
+ njs_str_t uri_arg, args_arg, method_name, body_arg;
+ ngx_str_t uri, rargs;
+ ngx_uint_t method, methods_max, has_body, detached,
+ promise;
+ njs_value_t *value, *arg, *options;
+ ngx_js_event_t *event;
+ njs_function_t *callback;
+ ngx_http_js_ctx_t *ctx;
+ njs_opaque_value_t lvalue;
+ ngx_http_request_t *r, *sr;
+ ngx_http_request_body_t *rb;
+ ngx_http_post_subrequest_t *ps;
static const struct {
ngx_str_t name;
@@ -3178,7 +3123,6 @@ ngx_http_js_ext_subrequest(njs_vm_t *vm, njs_value_t *args, njs_uint_t nargs,
args_arg.length = 0;
args_arg.start = NULL;
has_body = 0;
- promise = 0;
detached = 0;
arg = njs_arg(args, nargs, 2);
@@ -3267,21 +3211,71 @@ ngx_http_js_ext_subrequest(njs_vm_t *vm, njs_value_t *args, njs_uint_t nargs,
return NJS_ERROR;
}
- if (!detached && callback == NULL) {
- callback = njs_vm_function_alloc(vm, ngx_http_js_promise_trampoline, 0,
- 0);
- if (callback == NULL) {
- goto memory_error;
+ promise = 0;
+ flags = NGX_HTTP_SUBREQUEST_BACKGROUND;
+
+ njs_value_undefined_set(retval);
+
+ if (!detached) {
+ ps = ngx_palloc(r->pool, sizeof(ngx_http_post_subrequest_t));
+ if (ps == NULL) {
+ njs_vm_memory_error(ctx->vm);
+ return NJS_ERROR;
+ }
+
+ promise = !!(callback == NULL);
+
+ event = njs_mp_zalloc(njs_vm_memory_pool(ctx->vm),
+ sizeof(ngx_js_event_t)
+ + promise * (sizeof(njs_opaque_value_t) * 2));
+ if (njs_slow_path(event == NULL)) {
+ njs_vm_memory_error(ctx->vm);
+ return NJS_ERROR;
}
- promise = 1;
+ event->vm = ctx->vm;
+ event->fd = ctx->event_id++;
+
+ if (promise) {
+ event->args = (njs_value_t *) &event[1];
+ rc = njs_vm_promise_create(ctx->vm, retval,
+ njs_value_arg(event->args));
+ if (rc != NJS_OK) {
+ return NJS_ERROR;
+ }
+
+ callback = njs_value_function(njs_value_arg(event->args));
+ }
+
+ event->function = callback;
+
+ ps->handler = ngx_http_js_subrequest_done;
+ ps->data = event;
+
+ flags |= NGX_HTTP_SUBREQUEST_IN_MEMORY;
+
+ } else {
+ ps = NULL;
+ event = NULL;
}
- rc = ngx_http_js_subrequest(r, &uri_arg, &args_arg, callback, &sr);
- if (rc != NGX_OK) {
+ uri.len = uri_arg.length;
+ uri.data = uri_arg.start;
+
+ rargs.len = args_arg.length;
+ rargs.data = args_arg.start;
+
+ if (ngx_http_subrequest(r, &uri, rargs.len ? &rargs : NULL, &sr, ps, flags)
+ != NGX_OK)
+ {
+ njs_vm_error(ctx->vm, "subrequest creation failed");
return NJS_ERROR;
}
+ if (event != NULL) {
+ ngx_js_add_event(ctx, event);
+ }
+
if (method != methods_max) {
sr->method = methods[method].value;
sr->method_name = methods[method].name;
@@ -3325,41 +3319,6 @@ ngx_http_js_ext_subrequest(njs_vm_t *vm, njs_value_t *args, njs_uint_t nargs,
sr->headers_in.chunked = 0;
}
- if (promise) {
- cbs = ctx->promise_callbacks.elts;
-
- if (cbs == NULL) {
- if (ngx_array_init(&ctx->promise_callbacks, r->pool, 4,
- sizeof(ngx_http_js_cb_t)) != NGX_OK)
- {
- goto memory_error;
- }
- }
-
- cb = NULL;
-
- for (i = 0; i < ctx->promise_callbacks.nelts; i++) {
- if (cbs[i].request == NULL) {
- cb = &cbs[i];
- break;
- }
- }
-
- if (i == ctx->promise_callbacks.nelts) {
- cb = ngx_array_push(&ctx->promise_callbacks);
- if (cb == NULL) {
- goto memory_error;
- }
- }
-
- cb->request = sr;
-
- return njs_vm_promise_create(vm, retval,
- njs_value_arg(&cb->callbacks));
- }
-
- njs_value_undefined_set(retval);
-
return NJS_OK;
memory_error:
@@ -3370,69 +3329,6 @@ memory_error:
}
-static ngx_int_t
-ngx_http_js_subrequest(ngx_http_request_t *r, njs_str_t *uri_arg,
- njs_str_t *args_arg, njs_function_t *callback, ngx_http_request_t **sr)
-{
- ngx_int_t flags;
- ngx_str_t uri, args;
- ngx_js_event_t *event;
- ngx_http_js_ctx_t *ctx;
- ngx_http_post_subrequest_t *ps;
-
- ctx = ngx_http_get_module_ctx(r, ngx_http_js_module);
-
- flags = NGX_HTTP_SUBREQUEST_BACKGROUND;
-
- if (callback != NULL) {
- ps = ngx_palloc(r->pool, sizeof(ngx_http_post_subrequest_t));
- if (ps == NULL) {
- njs_vm_error(ctx->vm, "internal error");
- return NJS_ERROR;
- }
-
- event = njs_mp_zalloc(njs_vm_memory_pool(ctx->vm),
- sizeof(ngx_js_event_t));
- if (njs_slow_path(event == NULL)) {
- njs_vm_memory_error(ctx->vm);
- return NJS_ERROR;
- }
-
- event->vm = ctx->vm;
- event->function = callback;
- event->fd = ctx->event_id++;
-
- ps->handler = ngx_http_js_subrequest_done;
- ps->data = event;
-
- flags |= NGX_HTTP_SUBREQUEST_IN_MEMORY;
-
- } else {
- ps = NULL;
- event = NULL;
- }
-
- uri.len = uri_arg->length;
- uri.data = uri_arg->start;
-
- args.len = args_arg->length;
- args.data = args_arg->start;
-
- if (ngx_http_subrequest(r, &uri, args.len ? &args : NULL, sr, ps, flags)
- != NGX_OK)
- {
- njs_vm_error(ctx->vm, "subrequest creation failed");
- return NJS_ERROR;
- }
-
- if (event != NULL) {
- ngx_js_add_event(ctx, event);
- }
-
- return NJS_OK;
-}
-
-
static ngx_int_t
ngx_http_js_subrequest_done(ngx_http_request_t *r, void *data, ngx_int_t rc)
{
More information about the nginx-devel
mailing list