changeset 1903:4b41550ebdb3

Tests: removed njs tests. The tests are now hosted in the njs repository.
author Sergey Kandaurov <pluknet@nginx.com>
date Mon, 05 Jun 2023 16:59:38 +0400
parents c560f5da581e
children c04134b0290b
files h2_request_body_js.t js.t js_args.t js_async.t js_body_filter.t js_body_filter_if.t js_buffer.t js_dump.t js_fetch.t js_fetch_https.t js_fetch_objects.t js_fetch_resolver.t js_fetch_timeout.t js_fetch_verify.t js_header_filter.t js_header_filter_if.t js_headers.t js_import.t js_import2.t js_internal_redirect.t js_modules.t js_ngx.t js_object.t js_paths.t js_preload_object.t js_promise.t js_request_body.t js_return.t js_subrequests.t js_var.t js_var2.t js_variables.t stream_js.t stream_js_buffer.t stream_js_exit.t stream_js_fetch.t stream_js_fetch_https.t stream_js_fetch_init.t stream_js_import.t stream_js_import2.t stream_js_ngx.t stream_js_object.t stream_js_preload_object.t stream_js_send.t stream_js_var.t stream_js_var2.t stream_js_variables.t
diffstat 47 files changed, 0 insertions(+), 9234 deletions(-) [+]
line wrap: on
line diff
deleted file mode 100644
--- a/h2_request_body_js.t
+++ /dev/null
@@ -1,87 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Sergey Kandaurov
-# (C) Nginx, Inc.
-
-# Tests for HTTP/2 request body with njs subrequest in the body handler.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::HTTP2;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http http_v2/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080 http2;
-        server_name  localhost;
-
-        lingering_close off;
-
-        location / {
-            js_content test.sr_body;
-            add_header X-Body $request_body;
-        }
-
-        location /sr { }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-function body_fwd_cb(r) {
-    r.parent.return(r.status, r.responseText);
-}
-
-function sr_body(r) {
-    r.subrequest('/sr', body_fwd_cb);
-}
-
-export default {sr_body};
-
-EOF
-
-$t->write_file('sr', 'SEE-THIS');
-$t->try_run('no njs available')->plan(3);
-
-###############################################################################
-
-my $s = Test::Nginx::HTTP2->new();
-my $sid = $s->new_stream({ body => 'TEST' });
-my $frames = $s->read(all => [{ sid => $sid, fin => 1 }]);
-
-my ($frame) = grep { $_->{type} eq "HEADERS" } @$frames;
-is($frame->{headers}->{':status'}, 200, 'status');
-is($frame->{headers}->{'x-body'}, 'TEST', 'request body');
-
-($frame) = grep { $_->{type} eq "DATA" } @$frames;
-is($frame->{data}, 'SEE-THIS', 'response body');
-
-###############################################################################
deleted file mode 100644
--- a/js.t
+++ /dev/null
@@ -1,391 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Roman Arutyunyan
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_set $test_method   test.method;
-    js_set $test_version  test.version;
-    js_set $test_addr     test.addr;
-    js_set $test_uri      test.uri;
-    js_set $test_var      test.variable;
-    js_set $test_type     test.type;
-    js_set $test_global   test.global_obj;
-    js_set $test_log      test.log;
-    js_set $test_internal test.sub_internal;
-    js_set $test_except   test.except;
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /method {
-            return 200 $test_method;
-        }
-
-        location /version {
-            return 200 $test_version;
-        }
-
-        location /addr {
-            return 200 $test_addr;
-        }
-
-        location /uri {
-            return 200 $test_uri;
-        }
-
-        location /var {
-            return 200 $test_var;
-        }
-
-        location /global {
-            return 200 $test_global;
-        }
-
-        location /body {
-            js_content test.request_body;
-        }
-
-        location /in_file {
-            client_body_in_file_only on;
-            js_content test.request_body;
-        }
-
-        location /status {
-            js_content test.status;
-        }
-
-        location /request_body {
-            js_content test.request_body;
-        }
-
-        location /request_body_cache {
-            js_content test.request_body_cache;
-        }
-
-        location /send {
-            js_content test.send;
-        }
-
-        location /return_method {
-            js_content test.return_method;
-        }
-
-        location /type {
-            js_content test.type;
-        }
-
-        location /log {
-            return 200 $test_log;
-        }
-
-        location /internal {
-            js_content test.internal;
-        }
-
-        location /sub_internal {
-            internal;
-            return 200 $test_internal;
-        }
-
-        location /except {
-            return 200 $test_except;
-        }
-
-        location /content_except {
-            js_content test.content_except;
-        }
-
-        location /content_empty {
-            js_content test.content_empty;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    var global = ['n', 'j', 's'].join("");
-
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function method(r) {
-        return 'method=' + r.method;
-    }
-
-    function version(r) {
-        return 'version=' + r.httpVersion;
-    }
-
-    function addr(r) {
-        return 'addr=' + r.remoteAddress;
-    }
-
-    function uri(r) {
-        return 'uri=' + r.uri;
-    }
-
-    function variable(r) {
-        return 'variable=' + r.variables.remote_addr;
-    }
-
-    function global_obj(r) {
-        return 'global=' + global;
-    }
-
-    function status(r) {
-        r.status = 204;
-        r.sendHeader();
-        r.finish();
-    }
-
-    function request_body(r) {
-        try {
-            var body = r.requestText;
-            r.return(200, body);
-
-        } catch (e) {
-            r.return(500, e.message);
-        }
-    }
-
-    function request_body_cache(r) {
-        function t(v) {return Buffer.isBuffer(v) ? 'buffer' : (typeof v);}
-        r.return(200,
-      `requestText:\${t(r.requestText)} requestBuffer:\${t(r.requestBuffer)}`);
-    }
-
-    function send(r) {
-        var a, s;
-        r.status = 200;
-        r.sendHeader();
-        for (a in r.args) {
-            if (a.substr(0, 3) == 'foo') {
-                s = r.args[a];
-                r.send('n=' + a + ', v=' + s.substr(0, 2) + ' ');
-            }
-        }
-        r.finish();
-    }
-
-    function return_method(r) {
-        r.return(Number(r.args.c), r.args.t);
-    }
-
-    function type(r) {
-        var p = r.args.path.split('.').reduce((a, v) => a[v], r);
-
-        var typ = Buffer.isBuffer(p) ? 'buffer' : (typeof p);
-        r.return(200, `type: \${typ}`);
-    }
-
-    function log(r) {
-        r.log('SEE-LOG');
-    }
-
-    async function internal(r) {
-        let reply = await r.subrequest('/sub_internal');
-
-        r.return(200, `parent: \${r.internal} sub: \${reply.responseText}`);
-    }
-
-    function sub_internal(r) {
-        return r.internal;
-    }
-
-    function except(r) {
-        var fs = require('fs');
-        fs.readFileSync();
-    }
-
-
-    function content_except(r) {
-        JSON.parse({}.a.a);
-    }
-
-    function content_empty(r) {
-    }
-
-    export default {njs:test_njs, method, version, addr, uri,
-                    variable, global_obj, status, request_body, internal,
-                    request_body_cache, send, return_method, sub_internal,
-                    type, log, except, content_except, content_empty};
-
-EOF
-
-$t->try_run('no njs available')->plan(27);
-
-###############################################################################
-
-like(http_get('/method'), qr/method=GET/, 'r.method');
-like(http_get('/version'), qr/version=1.0/, 'r.httpVersion');
-like(http_get('/addr'), qr/addr=127.0.0.1/, 'r.remoteAddress');
-like(http_get('/uri'), qr/uri=\/uri/, 'r.uri');
-
-like(http_get('/status'), qr/204 No Content/, 'r.status');
-
-like(http_post('/body'), qr/REQ-BODY/, 'request body');
-like(http_post('/in_file'), qr/request body is in a file/,
-	'request body in file');
-like(http_post_big('/body'), qr/200.*^(1234567890){1024}$/ms,
-	'request body big');
-
-like(http_get('/send?foo=12345&n=11&foo-2=bar&ndd=&foo-3=z'),
-	qr/n=foo, v=12 n=foo-2, v=ba n=foo-3, v=z/, 'r.send');
-
-like(http_get('/return_method?c=200'), qr/200 OK.*\x0d\x0a?\x0d\x0a?$/s,
-	'return code');
-like(http_get('/return_method?c=200&t=SEE-THIS'), qr/200 OK.*^SEE-THIS$/ms,
-	'return text');
-like(http_get('/return_method?c=301&t=path'), qr/ 301 .*Location: path/s,
-	'return redirect');
-like(http_get('/return_method?c=404'), qr/404 Not.*html/s, 'return error page');
-like(http_get('/return_method?c=inv'), qr/ 500 /, 'return invalid');
-
-like(http_get('/type?path=variables.host'), qr/200 OK.*type: string$/s,
-	'variables type');
-like(http_get('/type?path=rawVariables.host'), qr/200 OK.*type: buffer$/s,
-	'rawVariables type');
-
-like(http_post('/type?path=requestText'), qr/200 OK.*type: string$/s,
-	'requestText type');
-like(http_post('/type?path=requestBuffer'), qr/200 OK.*type: buffer$/s,
-	'requestBuffer type');
-like(http_post('/request_body_cache'),
-	qr/requestText:string requestBuffer:buffer$/s, 'request body cache');
-
-like(http_get('/var'), qr/variable=127.0.0.1/, 'r.variables');
-like(http_get('/global'), qr/global=njs/, 'global code');
-like(http_get('/log'), qr/200 OK/, 'r.log');
-
-TODO: {
-local $TODO = 'not yet' unless has_version('0.7.7');
-
-like(http_get('/internal'), qr/parent: false sub: true/, 'r.internal');
-
-}
-
-http_get('/except');
-http_get('/content_except');
-
-like(http_get('/content_empty'), qr/500 Internal Server Error/,
-	'empty handler');
-
-$t->stop();
-
-ok(index($t->read_file('error.log'), 'SEE-LOG') > 0, 'log js');
-ok(index($t->read_file('error.log'), 'at fs.readFileSync') > 0,
-	'js_set backtrace');
-ok(index($t->read_file('error.log'), 'at JSON.parse') > 0,
-	'js_content backtrace');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub http_get_hdr {
-	my ($url, %extra) = @_;
-	return http(<<EOF, %extra);
-GET $url HTTP/1.0
-FoO: 12345
-
-EOF
-}
-
-sub http_get_ihdr {
-	my ($url, %extra) = @_;
-	return http(<<EOF, %extra);
-GET $url HTTP/1.0
-foo: 12345
-Host: localhost
-foo2: bar
-X-xxx: more
-foo-3: z
-
-EOF
-}
-
-sub http_post {
-	my ($url, %extra) = @_;
-
-	my $p = "POST $url HTTP/1.0" . CRLF .
-		"Host: localhost" . CRLF .
-		"Content-Length: 8" . CRLF .
-		CRLF .
-		"REQ-BODY";
-
-	return http($p, %extra);
-}
-
-sub http_post_big {
-	my ($url, %extra) = @_;
-
-	my $p = "POST $url HTTP/1.0" . CRLF .
-		"Host: localhost" . CRLF .
-		"Content-Length: 10240" . CRLF .
-		CRLF .
-		("1234567890" x 1024);
-
-	return http($p, %extra);
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_args.t
+++ /dev/null
@@ -1,167 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, arguments tests.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-eval { require JSON::PP; };
-plan(skip_all => "JSON::PP not installed") if $@;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    js_set $test_iter     test.iter;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /iter {
-            return 200 $test_iter;
-        }
-
-        location /keys {
-            js_content test.keys;
-        }
-
-        location /object {
-            js_content test.object;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function iter(r) {
-        var s = '', a;
-        for (a in r.args) {
-            if (a.substr(0, 3) == 'foo') {
-                s += r.args[a];
-            }
-        }
-
-        return s;
-    }
-
-    function keys(r) {
-        r.return(200, Object.keys(r.args).sort());
-    }
-
-    function object(r) {
-        r.return(200, JSON.stringify(r.args));
-    }
-
-    export default {njs: test_njs, iter, keys, object};
-
-EOF
-
-$t->try_run('no njs')->plan(15);
-
-###############################################################################
-
-sub recode {
-	my $json;
-	eval { $json = JSON::PP::decode_json(shift) };
-
-	if ($@) {
-		return "<failed to parse JSON>";
-	}
-
-	JSON::PP->new()->canonical()->encode($json);
-}
-
-sub get_json {
-	http_get(shift) =~ /\x0d\x0a?\x0d\x0a?(.*)/ms;
-	recode($1);
-}
-
-###############################################################################
-
-local $TODO = 'not yet' unless has_version('0.7.6');
-
-like(http_get('/iter?foo=12345&foo2=bar&nn=22&foo-3=z'), qr/12345barz/,
-	'r.args iteration');
-like(http_get('/iter?foo=123&foo2=&foo3&foo4=456'), qr/123456/,
-	'r.args iteration 2');
-like(http_get('/iter?foo=123&foo2=&foo3'), qr/123/, 'r.args iteration 3');
-like(http_get('/iter?foo=123&foo2='), qr/123/, 'r.args iteration 4');
-like(http_get('/iter?foo=1&foo=2'), qr/1,2/m, 'r.args iteration 5');
-
-like(http_get('/keys?b=1&c=2&a=5'), qr/a,b,c/m, 'r.args sorted keys');
-like(http_get('/keys?b=1&b=2'), qr/b/m, 'r.args duplicate keys');
-like(http_get('/keys?b=1&a&c='), qr/a,b,c/m, 'r.args empty value');
-
-is(get_json('/object'), '{}', 'empty object');
-is(get_json('/object?a=1&b=2&c=3'), '{"a":"1","b":"2","c":"3"}',
-	'ordinary object');
-is(get_json('/object?a=1&A=2'), '{"A":"2","a":"1"}',
-	'case sensitive object');
-is(get_json('/object?a=1&A=2&a=3'), '{"A":"2","a":["1","3"]}',
-	'duplicate keys object');
-is(get_json('/object?%61=1&a=2'), '{"a":["1","2"]}',
-	'keys percent-encoded object');
-is(get_json('/object?a=%62%63&b=%63%64'), '{"a":"bc","b":"cd"}',
-	'values percent-encoded object');
-is(get_json('/object?a=%6&b=%&c=%%&d=%zz'),
-	'{"a":"%6","b":"%","c":"%%","d":"%zz"}',
-	'values percent-encoded broken object');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_async.t
+++ /dev/null
@@ -1,249 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Async tests for http njs module.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_set $test_async      test.set_timeout;
-    js_set $context_var     test.context_var;
-    js_set $test_set_rv_var test.set_rv_var;
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /async_var {
-            return 200 $test_async;
-        }
-
-        location /shared_ctx {
-            add_header H $context_var;
-            js_content test.shared_ctx;
-        }
-
-        location /set_timeout {
-            js_content test.set_timeout;
-        }
-
-        location /set_timeout_many {
-            js_content test.set_timeout_many;
-        }
-
-        location /set_timeout_data {
-            postpone_output 0;
-            js_content test.set_timeout_data;
-        }
-
-        location /limit_rate {
-            postpone_output 0;
-            sendfile_max_chunk 5;
-            js_content test.limit_rate;
-        }
-
-        location /async_content {
-            js_content test.async_content;
-        }
-
-        location /set_rv_var {
-            return 200 $test_set_rv_var;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function set_timeout(r) {
-        var timerId = setTimeout(timeout_cb_r, 5, r, 0);
-        clearTimeout(timerId);
-        setTimeout(timeout_cb_r, 5, r, 0)
-    }
-
-    function set_timeout_data(r) {
-        setTimeout(timeout_cb_data, 5, r, 0);
-    }
-
-    function set_timeout_many(r) {
-        for (var i = 0; i < 5; i++) {
-            setTimeout(timeout_cb_empty, 5, r, i);
-        }
-
-        setTimeout(timeout_cb_reply, 10, r);
-    }
-
-    function timeout_cb_r(r, cnt) {
-        if (cnt == 10) {
-            r.status = 200;
-            r.headersOut['Content-Type'] = 'foo';
-            r.sendHeader();
-            r.finish();
-
-        } else {
-            setTimeout(timeout_cb_r, 5, r, ++cnt);
-        }
-    }
-
-    function timeout_cb_empty(r, arg) {
-        r.log("timeout_cb_empty" + arg);
-    }
-
-    function timeout_cb_reply(r) {
-        r.status = 200;
-        r.headersOut['Content-Type'] = 'reply';
-        r.sendHeader();
-        r.finish();
-    }
-
-    function timeout_cb_data(r, counter) {
-        if (counter == 0) {
-            r.log("timeout_cb_data: init");
-            r.status = 200;
-            r.sendHeader();
-            setTimeout(timeout_cb_data, 5, r, ++counter);
-
-        } else if (counter == 10) {
-            r.log("timeout_cb_data: finish");
-            r.finish();
-
-        } else {
-            r.send("" + counter);
-            setTimeout(timeout_cb_data, 5, r, ++counter);
-        }
-    }
-
-    var js_;
-    function context_var() {
-        return js_;
-    }
-
-    function shared_ctx(r) {
-        js_ = r.variables.arg_a;
-
-        r.status = 200;
-        r.sendHeader();
-        r.finish();
-    }
-
-    function limit_rate_cb(r) {
-        r.finish();
-    }
-
-    function limit_rate(r) {
-        r.status = 200;
-        r.sendHeader();
-        r.send("AAAAA".repeat(10))
-        setTimeout(limit_rate_cb, 1000, r);
-    }
-
-    function pr(x) {
-        return new Promise(resolve => {resolve(x)}).then(v => v).then(v => v);
-    }
-
-    async function async_content(r) {
-        const a1 = await pr('A');
-        const a2 = await pr('B');
-
-        r.return(200, `retval: \${a1 + a2}`);
-    }
-
-    async function set_rv_var(r) {
-        const a1 = await pr(10);
-        const a2 = await pr(20);
-
-        r.setReturnValue(`retval: \${a1 + a2}`);
-    }
-
-    export default {njs:test_njs, set_timeout, set_timeout_data,
-                    set_timeout_many, context_var, shared_ctx, limit_rate,
-                    async_content, set_rv_var};
-
-EOF
-
-$t->try_run('no njs available')->plan(9);
-
-###############################################################################
-
-like(http_get('/set_timeout'), qr/Content-Type: foo/, 'setTimeout');
-like(http_get('/set_timeout_many'), qr/Content-Type: reply/, 'setTimeout many');
-like(http_get('/set_timeout_data'), qr/123456789/, 'setTimeout data');
-like(http_get('/shared_ctx?a=xxx'), qr/H: xxx/, 'shared context');
-like(http_get('/limit_rate'), qr/A{50}/, 'limit_rate');
-
-TODO: {
-local $TODO = 'not yet' unless has_version('0.7.0');
-
-like(http_get('/async_content'), qr/retval: AB/, 'async content');
-like(http_get('/set_rv_var'), qr/retval: 30/, 'set return value variable');
-
-}
-
-http_get('/async_var');
-
-$t->stop();
-
-ok(index($t->read_file('error.log'), 'pending events') > 0,
-   'pending js events');
-ok(index($t->read_file('error.log'), 'async operation inside') > 0,
-   'async op in var handler');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_body_filter.t
+++ /dev/null
@@ -1,168 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, body filter.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http proxy/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /append {
-            js_body_filter test.append;
-            proxy_pass http://127.0.0.1:8081/source;
-        }
-
-        location /buffer_type {
-            js_body_filter test.buffer_type buffer_type=buffer;
-            proxy_pass http://127.0.0.1:8081/source;
-        }
-
-        location /forward {
-            js_body_filter test.forward buffer_type=string;
-            proxy_pass http://127.0.0.1:8081/source;
-        }
-
-        location /filter {
-            proxy_buffering off;
-            js_body_filter test.filter;
-            proxy_pass http://127.0.0.1:8081/source;
-        }
-
-        location /prepend {
-            js_body_filter test.prepend;
-            proxy_pass http://127.0.0.1:8081/source;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location /source {
-            postpone_output 1;
-            js_content test.source;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function append(r, data, flags) {
-        r.sendBuffer(data, {last:false});
-
-        if (flags.last) {
-            r.sendBuffer("XXX", flags);
-        }
-    }
-
-    var collect = Buffer.from([]);
-    function buffer_type(r, data, flags) {
-        collect = Buffer.concat([collect, data]);
-
-        if (flags.last) {
-            r.sendBuffer(collect, flags);
-        }
-    }
-
-    function chain(chunks, i) {
-        if (i < chunks.length) {
-            chunks.r.send(chunks[i++]);
-            setTimeout(chunks.chain, chunks.delay, chunks, i);
-
-        } else {
-            chunks.r.finish();
-        }
-    }
-
-    function source(r) {
-        var chunks = ['AAA', 'BB', 'C', 'DDDD'];
-        chunks.delay = 5;
-        chunks.r = r;
-        chunks.chain = chain;
-
-        r.status = 200;
-        r.sendHeader();
-        chain(chunks, 0);
-    }
-
-    function filter(r, data, flags) {
-        if (flags.last || data.length >= Number(r.args.len)) {
-            r.sendBuffer(`\${data}|`, flags);
-
-            if (r.args.dup && !flags.last) {
-                r.sendBuffer(data, flags);
-            }
-        }
-    }
-
-    function forward(r, data, flags) {
-        r.sendBuffer(data, flags);
-    }
-
-    function prepend(r, data, flags) {
-        r.sendBuffer("XXX");
-        r.sendBuffer(data, flags);
-        r.done();
-    }
-
-    export default {njs: test_njs, append, buffer_type, filter, forward,
-                    prepend, source};
-
-EOF
-
-$t->try_run('no njs body filter')->plan(6);
-
-###############################################################################
-
-like(http_get('/append'), qr/AAABBCDDDDXXX/, 'append');
-like(http_get('/buffer_type'), qr/AAABBCDDDD/, 'buffer type');
-like(http_get('/forward'), qr/AAABBCDDDD/, 'forward');
-like(http_get('/filter?len=3'), qr/AAA|DDDD|/, 'filter 3');
-like(http_get('/filter?len=2&dup=1'), qr/AAA|AAABB|BBDDDD|DDDD/,
-	'filter 2 dup');
-like(http_get('/prepend'), qr/XXXAAABBCDDDD/, 'prepend');
-
-###############################################################################
deleted file mode 100644
--- a/js_body_filter_if.t
+++ /dev/null
@@ -1,127 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, body filter, if context.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http proxy rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /filter {
-            if ($arg_name ~ "prepend") {
-                js_body_filter test.prepend;
-            }
-
-            if ($arg_name ~ "append") {
-                js_body_filter test.append;
-            }
-
-            js_body_filter test.should_not_be_called;
-
-            proxy_pass http://127.0.0.1:8081/source;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location /source {
-            postpone_output 1;
-            js_content test.source;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function append(r, data, flags) {
-        r.sendBuffer(data, {last:false});
-
-        if (flags.last) {
-            r.sendBuffer("XXX", flags);
-        }
-    }
-
-    function chain(chunks, i) {
-        if (i < chunks.length) {
-            chunks.r.send(chunks[i++]);
-            setTimeout(chunks.chain, chunks.delay, chunks, i);
-
-        } else {
-            chunks.r.finish();
-        }
-    }
-
-    function source(r) {
-        var chunks = ['AAA', 'BB', 'C', 'DDDD'];
-        chunks.delay = 5;
-        chunks.r = r;
-        chunks.chain = chain;
-
-        r.status = 200;
-        r.sendHeader();
-        chain(chunks, 0);
-    }
-
-    function prepend(r, data, flags) {
-        r.sendBuffer("XXX");
-        r.sendBuffer(data, flags);
-        r.done();
-    }
-
-    export default {njs: test_njs, append, prepend, source};
-
-EOF
-
-$t->try_run('no njs body filter')->plan(2);
-
-###############################################################################
-
-like(http_get('/filter?name=append'), qr/AAABBCDDDDXXX/, 'append');
-like(http_get('/filter?name=prepend'), qr/XXXAAABBCDDDD/, 'prepend');
-
-###############################################################################
deleted file mode 100644
--- a/js_buffer.t
+++ /dev/null
@@ -1,184 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, buffer properties.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-eval { require JSON::PP; };
-plan(skip_all => "JSON::PP not installed") if $@;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite proxy/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /return {
-            js_content test.return;
-        }
-
-        location /req_body {
-            js_content test.req_body;
-        }
-
-        location /res_body {
-            js_content test.res_body;
-        }
-
-        location /res_text {
-            js_content test.res_text;
-        }
-
-        location /binary_var {
-            js_content test.binary_var;
-        }
-
-        location /p/ {
-            proxy_pass http://127.0.0.1:8081/;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location /sub1 {
-            return 200 '{"a": {"b": 1}}';
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function test_return(r) {
-        var body = Buffer.from("body: ");
-        body = Buffer.concat([body, Buffer.from(r.args.text)]);
-        r.return(200, body);
-    }
-
-    function req_body(r) {
-        var body = r.requestBuffer;
-        var view = new DataView(body.buffer);
-        view.setInt8(2, 'c'.charCodeAt(0));
-        r.return(200, JSON.parse(body).c.b);
-    }
-
-    function type(v) {return Buffer.isBuffer(v) ? 'buffer' : (typeof v);}
-
-    function res_body(r) {
-        r.subrequest('/p/sub1')
-        .then(reply => {
-            var body = reply.responseBuffer;
-            var view = new DataView(body.buffer);
-            view.setInt8(2, 'c'.charCodeAt(0));
-            body = JSON.parse(body);
-            body.type = type(reply.responseBuffer);
-            r.return(200, JSON.stringify(body));
-        })
-    }
-
-    function res_text(r) {
-        r.subrequest('/p/sub1')
-        .then(reply => {
-            var body = JSON.parse(reply.responseText);
-            body.type = type(reply.responseText);
-            r.return(200, JSON.stringify(body));
-        })
-    }
-
-    function binary_var(r) {
-        var test = r.rawVariables.binary_remote_addr
-                   .equals(Buffer.from([127,0,0,1]));
-        r.return(200, test);
-    }
-
-    export default {njs: test_njs, return: test_return, req_body, res_body,
-                    res_text, binary_var};
-
-EOF
-
-$t->try_run('no njs buffer')->plan(5);
-
-###############################################################################
-
-like(http_get('/return?text=FOO'), qr/200 OK.*body: FOO$/s,
-	'return buffer');
-like(http_post('/req_body'), qr/200 OK.*BAR$/s, 'request buffer');
-is(get_json('/res_body'), '{"c":{"b":1},"type":"buffer"}', 'response buffer');
-is(get_json('/res_text'), '{"a":{"b":1},"type":"string"}', 'response text');
-like(http_get('/binary_var'), qr/200 OK.*true$/s,
-	'binary var');
-
-###############################################################################
-
-sub recode {
-	my $json;
-	eval { $json = JSON::PP::decode_json(shift) };
-
-	if ($@) {
-		return "<failed to parse JSON>";
-	}
-
-	JSON::PP->new()->canonical()->encode($json);
-}
-
-sub get_json {
-	http_get(shift) =~ /\x0d\x0a?\x0d\x0a?(.*)/ms;
-	recode($1);
-}
-
-sub http_post {
-	my ($url, %extra) = @_;
-
-	my $p = "POST $url HTTP/1.0" . CRLF .
-		"Host: localhost" . CRLF .
-		"Content-Length: 17" . CRLF .
-		CRLF .
-		"{\"a\":{\"b\":\"BAR\"}}";
-
-	return http($p, %extra);
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_dump.t
+++ /dev/null
@@ -1,110 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, request object dump.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /dump {
-            js_content test.dump;
-        }
-
-        location /stringify {
-            js_content test.stringify;
-        }
-
-        location /stringify_subrequest {
-            js_content test.stringify_subrequest;
-        }
-
-        location /js_sub {
-            return 201 '{$request_method}';
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function dump(r) {
-        r.headersOut.baz = 'bar';
-        r.return(200, njs.dump(r));
-    }
-
-    function stringify(r) {
-        r.headersOut.baz = 'bar';
-        var obj = JSON.parse(JSON.stringify(r));
-        r.return(200, JSON.stringify(obj));
-    }
-
-    function stringify_subrequest(r) {
-        r.subrequest('/js_sub', reply => {
-            r.return(200, JSON.stringify(reply))
-        });
-    }
-
-    export default {dump, stringify, stringify_subrequest};
-
-EOF
-
-$t->try_run('no njs dump')->plan(3);
-
-###############################################################################
-
-like(http(
-	'GET /dump?v=1&t=x HTTP/1.0' . CRLF
-	. 'Foo: bar' . CRLF
-	. 'Foo2: bar2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/method:'GET'/, 'njs.dump(r)');
-
-like(http(
-	'GET /stringify?v=1&t=x HTTP/1.0' . CRLF
-	. 'Foo: bar' . CRLF
-	. 'Foo2: bar2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/headersOut":\{"baz":"bar"}/, 'JSON.stringify(r)');
-
-like(http(
-	'GET /stringify_subrequest HTTP/1.0' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/"status":201/, 'JSON.stringify(reply)');
-
-###############################################################################
deleted file mode 100644
--- a/js_fetch.t
+++ /dev/null
@@ -1,694 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, fetch method.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-eval { require JSON::PP; };
-plan(skip_all => "JSON::PP not installed") if $@;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /broken {
-            js_content test.broken;
-        }
-
-        location /broken_response {
-            js_content test.broken_response;
-        }
-
-        location /body {
-            js_content test.body;
-        }
-
-        location /body_special {
-            js_content test.body_special;
-        }
-
-        location /chain {
-            js_content test.chain;
-        }
-
-        location /chunked_ok {
-            js_content test.chunked_ok;
-        }
-
-        location /chunked_fail {
-            js_content test.chunked_fail;
-        }
-
-        location /header {
-            js_content test.header;
-        }
-
-        location /header_iter {
-            js_content test.header_iter;
-        }
-
-        location /multi {
-            js_content test.multi;
-        }
-
-        location /property {
-            js_content test.property;
-        }
-
-        location /loc {
-            js_content test.loc;
-        }
-
-        location /json { }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location /loc {
-            js_content test.loc;
-        }
-    }
-}
-
-EOF
-
-my $p0 = port(8080);
-my $p1 = port(8081);
-my $p2 = port(8082);
-
-$t->write_file('json', '{"a":[1,2], "b":{"c":"FIELD"}}');
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function body(r) {
-        var loc = r.args.loc;
-        var getter = r.args.getter;
-
-        function query(obj) {
-            var path = r.args.path;
-            var retval = (getter == 'arrayBuffer') ? Buffer.from(obj).toString()
-                                                   : obj;
-
-            if (path) {
-                retval = path.split('.').reduce((a, v) => a[v], obj);
-            }
-
-            return JSON.stringify(retval);
-        }
-
-        ngx.fetch(`http://127.0.0.1:$p0/\${loc}`)
-        .then(reply => reply[getter]())
-        .then(data => r.return(200, query(data)))
-        .catch(e => r.return(501, e.message))
-    }
-
-    function property(r) {
-        var opts = {headers:{}};
-
-        if (r.args.code) {
-            opts.headers.code = r.args.code;
-        }
-
-        var p = ngx.fetch('http://127.0.0.1:$p0/loc', opts)
-
-        if (r.args.readBody) {
-            p = p.then(rep =>
-                 rep.text().then(body => {rep.text = body; return rep;}))
-        }
-
-        p.then(reply => r.return(200, reply[r.args.pr]))
-        .catch(e => r.return(501, e.message))
-    }
-
-    function process_errors(r, tests) {
-        var results = [];
-
-        tests.forEach(args => {
-            ngx.fetch.apply(r, args)
-            .then(reply => {
-                r.return(400, '["unexpected then"]');
-            })
-            .catch(e => {
-                results.push(e.message);
-
-                if (results.length == tests.length) {
-                    results.sort();
-                    r.return(200, JSON.stringify(results));
-                }
-            })
-        })
-    }
-
-    function broken(r) {
-        var tests = [
-            ['http://127.0.0.1:1/loc'],
-            ['http://127.0.0.1:80800/loc'],
-            [Symbol.toStringTag],
-        ];
-
-        return process_errors(r, tests);
-    }
-
-    function broken_response(r) {
-        var tests = [
-            ['http://127.0.0.1:$p2/status_line'],
-            ['http://127.0.0.1:$p2/length'],
-            ['http://127.0.0.1:$p2/header'],
-            ['http://127.0.0.1:$p2/headers'],
-            ['http://127.0.0.1:$p2/content_length'],
-        ];
-
-        return process_errors(r, tests);
-    }
-
-    function chain(r) {
-        var results = [];
-        var reqs = [
-             ['http://127.0.0.1:$p0/loc'],
-             ['http://127.0.0.1:$p1/loc'],
-           ];
-
-           function next(reply) {
-              if (reqs.length == 0) {
-                 r.return(200, "SUCCESS");
-                 return;
-              }
-
-              ngx.fetch.apply(r, reqs.pop())
-              .then(next)
-              .catch(e => r.return(400, e.message))
-           }
-
-           next();
-    }
-
-    function chunked_ok(r) {
-        var results = [];
-        var tests = [
-            ['http://127.0.0.1:$p2/big/ok', {max_response_body_size:128000}],
-            ['http://127.0.0.1:$p2/chunked/ok'],
-            ['http://127.0.0.1:$p2/chunked/big'],
-        ];
-
-        function collect(v) {
-            results.push(v);
-
-            if (results.length == tests.length) {
-                r.return(200);
-            }
-        }
-
-        tests.forEach(args => {
-            ngx.fetch.apply(r, args)
-            .then(reply => reply.text())
-            .then(body => collect(body.length))
-        })
-    }
-
-    function chunked_fail(r) {
-        var results = [];
-        var tests = [
-            ['http://127.0.0.1:$p2/big', {max_response_body_size:128000}],
-            ['http://127.0.0.1:$p2/chunked'],
-            ['http://127.0.0.1:$p2/chunked/big', {max_response_body_size:128}],
-        ];
-
-        function collect(v) {
-            results.push(v);
-
-            if (results.length == tests.length) {
-                r.return(200);
-            }
-        }
-
-        tests.forEach(args => {
-            ngx.fetch.apply(r, args)
-            .then(reply => reply.text())
-            .catch(e => collect(e.message))
-        })
-    }
-
-    function header(r) {
-        var url = `http://127.0.0.1:$p2/\${r.args.loc}`;
-        var method = r.args.method ? r.args.method : 'get';
-
-        var p = ngx.fetch(url)
-
-        if (r.args.readBody) {
-            p = p.then(rep =>
-                 rep.text().then(body => {rep.text = body; return rep;}))
-        }
-
-        p.then(reply => {
-            var h = reply.headers[method](r.args.h);
-            r.return(200, njs.dump(h));
-        })
-        .catch(e => r.return(501, e.message))
-    }
-
-    async function body_special(r) {
-        let opts = {};
-
-        if (r.args.method) {
-            opts.method = r.args.method;
-        }
-
-        let reply = await ngx.fetch(`http://127.0.0.1:$p2/\${r.args.loc}`,
-                                    opts);
-        let body = await reply.text();
-
-        r.return(200, body != '' ? body : '<empty>');
-    }
-
-    async function header_iter(r) {
-        let url = `http://127.0.0.1:$p2/\${r.args.loc}`;
-
-        let response = await ngx.fetch(url);
-
-        let headers = response.headers;
-        let out = [];
-        for (let key in response.headers) {
-            if (key != 'Connection') {
-                out.push(`\${key}:\${headers.get(key)}`);
-            }
-        }
-
-        r.return(200, njs.dump(out));
-    }
-
-    function multi(r) {
-        var results = [];
-        var tests = [
-             [
-              'http://127.0.0.1:$p0/loc',
-               { headers: {Code: 201}},
-             ],
-             [
-              'http://127.0.0.1:$p0/loc',
-               { method:'POST', headers: {Code: 401}, body: 'OK'},
-             ],
-             [
-              'http://127.0.0.1:$p1/loc',
-               { method:'PATCH',
-                 headers: {bar:'xxx'}},
-             ],
-           ];
-
-        function cmp(a,b) {
-            if (a.b > b.b) {return 1;}
-            if (a.b < b.b) {return -1;}
-            return 0
-        }
-
-        tests.forEach(args => {
-            ngx.fetch.apply(r, args)
-            .then(rep =>
-                 rep.text().then(body => {rep.text = body; return rep;}))
-            .then(rep => {
-                results.push({b:rep.text,
-                              c:rep.status,
-                              u:rep.url});
-
-                if (results.length == tests.length) {
-                    results.sort(cmp);
-                    r.return(200, JSON.stringify(results));
-                }
-            })
-            .catch(e => {
-                r.return(400, `["\${e.message}"]`);
-                throw e;
-            })
-        })
-
-        if (r.args.throw) {
-            throw 'Oops';
-        }
-    }
-
-    function str(v) { return v ? v : ''};
-
-    function loc(r) {
-        var v = r.variables;
-        var body = str(r.requestText);
-        var bar = str(r.headersIn.bar);
-        var c = r.headersIn.code ? Number(r.headersIn.code) : 200;
-        r.return(c, `\${v.request_method}:\${bar}:\${body}`);
-    }
-
-     export default {njs: test_njs, body, broken, broken_response, body_special,
-                     chain, chunked_ok, chunked_fail, header, header_iter,
-                     multi, loc, property};
-EOF
-
-$t->try_run('no njs.fetch')->plan(34);
-
-$t->run_daemon(\&http_daemon, port(8082));
-$t->waitforsocket('127.0.0.1:' . port(8082));
-
-###############################################################################
-
-like(http_get('/body?getter=arrayBuffer&loc=loc'), qr/200 OK.*"GET::"$/s,
-	'fetch body arrayBuffer');
-like(http_get('/body?getter=text&loc=loc'), qr/200 OK.*"GET::"$/s,
-	'fetch body text');
-like(http_get('/body?getter=json&loc=json&path=b.c'),
-	qr/200 OK.*"FIELD"$/s, 'fetch body json');
-like(http_get('/body?getter=json&loc=loc'), qr/501/s,
-	'fetch body json invalid');
-like(http_get('/body_special?loc=parted'), qr/200 OK.*X{32000}$/s,
-	'fetch body parted');
-like(http_get('/property?pr=bodyUsed'), qr/false$/s,
-	'fetch bodyUsed false');
-like(http_get('/property?pr=bodyUsed&readBody=1'), qr/true$/s,
-	'fetch bodyUsed true');
-like(http_get('/property?pr=ok'), qr/200 OK.*true$/s,
-	'fetch ok true');
-like(http_get('/property?pr=ok&code=401'), qr/200 OK.*false$/s,
-	'fetch ok false');
-like(http_get('/property?pr=redirected'), qr/200 OK.*false$/s,
-	'fetch redirected false');
-like(http_get('/property?pr=statusText'), qr/200 OK.*OK$/s,
-	'fetch statusText OK');
-like(http_get('/property?pr=statusText&code=403'), qr/200 OK.*Forbidden$/s,
-	'fetch statusText Forbidden');
-like(http_get('/property?pr=type'), qr/200 OK.*basic$/s,
-	'fetch type');
-like(http_get('/header?loc=duplicate_header&h=BAR'), qr/200 OK.*c$/s,
-	'fetch header');
-like(http_get('/header?loc=duplicate_header&h=BARR'), qr/200 OK.*null$/s,
-	'fetch no header');
-like(http_get('/header?loc=duplicate_header&h=foo'), qr/200 OK.*a, ?b$/s,
-	'fetch header duplicate');
-like(http_get('/header?loc=duplicate_header&h=BAR&method=getAll'),
-	qr/200 OK.*\['c']$/s, 'fetch getAll header');
-like(http_get('/header?loc=duplicate_header&h=BARR&method=getAll'),
-	qr/200 OK.*\[]$/s, 'fetch getAll no header');
-like(http_get('/header?loc=duplicate_header&h=FOO&method=getAll'),
-	qr/200 OK.*\['a','b']$/s, 'fetch getAll duplicate');
-like(http_get('/header?loc=duplicate_header&h=bar&method=has'),
-	qr/200 OK.*true$/s, 'fetch header has');
-like(http_get('/header?loc=duplicate_header&h=buz&method=has'),
-	qr/200 OK.*false$/s, 'fetch header does not have');
-like(http_get('/header?loc=chunked/big&h=BAR&readBody=1'), qr/200 OK.*xxx$/s,
-	'fetch chunked header');
-is(get_json('/multi'),
-	'[{"b":"GET::","c":201,"u":"http://127.0.0.1:'.$p0.'/loc"},' .
-	'{"b":"PATCH:xxx:","c":200,"u":"http://127.0.0.1:'.$p1.'/loc"},' .
-	'{"b":"POST::OK","c":401,"u":"http://127.0.0.1:'.$p0.'/loc"}]',
-	'fetch multi');
-like(http_get('/multi?throw=1'), qr/500/s, 'fetch destructor');
-like(http_get('/broken'), qr/200/s, 'fetch broken');
-like(http_get('/broken_response'), qr/200/s, 'fetch broken response');
-like(http_get('/chunked_ok'), qr/200/s, 'fetch chunked ok');
-like(http_get('/chunked_fail'), qr/200/s, 'fetch chunked fail');
-like(http_get('/chain'), qr/200 OK.*SUCCESS$/s, 'fetch chain');
-
-TODO: {
-todo_skip 'leaves coredump', 1 unless $ENV{TEST_NGINX_UNSAFE}
-	or has_version('0.7.4');
-
-like(http_get('/header_iter?loc=duplicate_header_large'),
-	qr/\['A:a','B:a','C:a','D:a','E:a','F:a','G:a','H:a','Moo:a, ?b']$/s,
-	'fetch header duplicate large');
-
-}
-
-TODO: {
-local $TODO = 'not yet' unless has_version('0.7.7');
-
-like(http_get('/body_special?loc=no_content_length'),
-	qr/200 OK.*CONTENT-BODY$/s, 'fetch body without content-length');
-like(http_get('/body_special?loc=no_content_length/parted'),
-	qr/200 OK.*X{32000}$/s, 'fetch body without content-length parted');
-
-}
-
-TODO: {
-local $TODO = 'not yet' unless has_version('0.7.8');
-
-like(http_get('/body_special?loc=head&method=HEAD'),
-	qr/200 OK.*<empty>$/s, 'fetch head method');
-like(http_get('/body_special?loc=length&method=head'),
-	qr/200 OK.*<empty>$/s, 'fetch head method lower case');
-
-}
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub recode {
-	my $json;
-	eval { $json = JSON::PP::decode_json(shift) };
-
-	if ($@) {
-		return "<failed to parse JSON>";
-	}
-
-	JSON::PP->new()->canonical()->encode($json);
-}
-
-sub get_json {
-	http_get(shift) =~ /\x0d\x0a?\x0d\x0a?(.*)/ms;
-	recode($1);
-}
-
-###############################################################################
-
-sub http_daemon {
-	my $port = shift;
-
-	my $server = IO::Socket::INET->new(
-		Proto => 'tcp',
-		LocalAddr => '127.0.0.1:' . $port,
-		Listen => 5,
-		Reuse => 1
-	) or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	while (my $client = $server->accept()) {
-		$client->autoflush(1);
-
-		my $headers = '';
-		my $uri = '';
-
-		while (<$client>) {
-			$headers .= $_;
-			last if (/^\x0d?\x0a?$/);
-		}
-
-		$uri = $1 if $headers =~ /^\S+\s+([^ ]+)\s+HTTP/i;
-
-		if ($uri eq '/status_line') {
-			print $client
-				"HTTP/1.1 2A";
-
-		} elsif ($uri eq '/content_length') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Content-Length: " . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-		} elsif ($uri eq '/header') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"@#" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-		} elsif ($uri eq '/duplicate_header') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Foo: a" . CRLF .
-				"bar: c" . CRLF .
-				"Foo: b" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-		} elsif ($uri eq '/duplicate_header_large') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"A: a" . CRLF .
-				"B: a" . CRLF .
-				"C: a" . CRLF .
-				"D: a" . CRLF .
-				"E: a" . CRLF .
-				"F: a" . CRLF .
-				"G: a" . CRLF .
-				"H: a" . CRLF .
-				"Moo: a" . CRLF .
-				"Moo: b" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-		} elsif ($uri eq '/headers') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Connection: close" . CRLF;
-
-		} elsif ($uri eq '/length') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Content-Length: 100" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF .
-				"unfinished" . CRLF;
-
-		} elsif ($uri eq '/head') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Content-Length: 100" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-		} elsif ($uri eq '/parted') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Content-Length: 32000" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-			for (1 .. 4) {
-				select undef, undef, undef, 0.01;
-				print $client "X" x 8000;
-			}
-
-		} elsif ($uri eq '/no_content_length') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF .
-				"CONTENT-BODY";
-
-		} elsif ($uri eq '/no_content_length/parted') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-			for (1 .. 4) {
-				select undef, undef, undef, 0.01;
-				print $client "X" x 8000;
-			}
-
-		} elsif ($uri eq '/big') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Content-Length: 100100" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-			for (1 .. 1000) {
-				print $client ("X" x 98) . CRLF;
-			}
-			print $client "unfinished" . CRLF;
-
-		} elsif ($uri eq '/big/ok') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Content-Length: 100010" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-			for (1 .. 1000) {
-				print $client ("X" x 98) . CRLF;
-			}
-			print $client "finished" . CRLF;
-
-		} elsif ($uri eq '/chunked') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Transfer-Encoding: chunked" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF .
-				"ff" . CRLF .
-				"unfinished" . CRLF;
-
-		} elsif ($uri eq '/chunked/ok') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Transfer-Encoding: chunked" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF .
-				"a" . CRLF .
-				"finished" . CRLF .
-				CRLF . "0" . CRLF . CRLF;
-		} elsif ($uri eq '/chunked/big') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Transfer-Encoding: chunked" . CRLF .
-				"Bar: xxx" . CRLF .
-				"Connection: close" . CRLF .
-				CRLF;
-
-			for (1 .. 100) {
-				print $client "ff" . CRLF . ("X" x 255) . CRLF;
-			}
-
-		    print $client  "0" . CRLF . CRLF;
-		}
-	}
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_fetch_https.t
+++ /dev/null
@@ -1,304 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Antoine Bonavita
-# (C) Nginx, Inc.
-
-# Tests for http njs module, fetch method, https support.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http http_ssl rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        resolver   127.0.0.1:%%PORT_8981_UDP%%;
-        resolver_timeout 1s;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /https {
-            js_content test.https;
-        }
-
-        location /https.myca {
-            js_content test.https;
-
-            js_fetch_ciphers HIGH:!aNull:!MD5;
-            js_fetch_protocols TLSv1.1 TLSv1.2;
-            js_fetch_trusted_certificate myca.crt;
-        }
-
-        location /https.myca.short {
-            js_content test.https;
-
-            js_fetch_verify_depth 0;
-            js_fetch_trusted_certificate myca.crt;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081 ssl default;
-        server_name  default.example.com;
-
-        ssl_certificate default.example.com.chained.crt;
-        ssl_certificate_key default.example.com.key;
-
-        location /loc {
-            return 200 "You are at default.example.com.";
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081 ssl;
-        server_name  1.example.com;
-
-        ssl_certificate 1.example.com.chained.crt;
-        ssl_certificate_key 1.example.com.key;
-
-        location /loc {
-            return 200 "You are at 1.example.com.";
-        }
-    }
-}
-
-EOF
-
-my $p1 = port(8081);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function https(r) {
-        var url = `https://\${r.args.domain}:$p1/loc`;
-        var opt = {};
-
-        if (r.args.verify != null && r.args.verify == "false") {
-            opt.verify = false;
-        }
-
-        ngx.fetch(url, opt)
-        .then(reply => reply.text())
-        .then(body => r.return(200, body))
-        .catch(e => r.return(501, e.message))
-    }
-
-    export default {njs: test_njs, https};
-EOF
-
-my $d = $t->testdir();
-
-$t->write_file('openssl.conf', <<EOF);
-[ req ]
-default_bits = 2048
-encrypt_key = no
-distinguished_name = req_distinguished_name
-[ req_distinguished_name ]
-EOF
-
-$t->write_file('myca.conf', <<EOF);
-[ ca ]
-default_ca = myca
-
-[ myca ]
-new_certs_dir = $d
-database = $d/certindex
-default_md = sha256
-policy = myca_policy
-serial = $d/certserial
-default_days = 1
-x509_extensions = myca_extensions
-
-[ myca_policy ]
-commonName = supplied
-
-[ myca_extensions ]
-basicConstraints = critical,CA:TRUE
-EOF
-
-system('openssl req -x509 -new '
-	. "-config $d/openssl.conf -subj /CN=myca/ "
-	. "-out $d/myca.crt -keyout $d/myca.key "
-	. ">>$d/openssl.out 2>&1") == 0
-	or die "Can't create self-signed certificate for CA: $!\n";
-
-foreach my $name ('intermediate', 'default.example.com', '1.example.com') {
-	system("openssl req -new "
-		. "-config $d/openssl.conf -subj /CN=$name/ "
-		. "-out $d/$name.csr -keyout $d/$name.key "
-		. ">>$d/openssl.out 2>&1") == 0
-		or die "Can't create certificate signing req for $name: $!\n";
-}
-
-$t->write_file('certserial', '1000');
-$t->write_file('certindex', '');
-
-system("openssl ca -batch -config $d/myca.conf "
-	. "-keyfile $d/myca.key -cert $d/myca.crt "
-	. "-subj /CN=intermediate/ -in $d/intermediate.csr "
-	. "-out $d/intermediate.crt "
-	. ">>$d/openssl.out 2>&1") == 0
-	or die "Can't sign certificate for intermediate: $!\n";
-
-foreach my $name ('default.example.com', '1.example.com') {
-	system("openssl ca -batch -config $d/myca.conf "
-		. "-keyfile $d/intermediate.key -cert $d/intermediate.crt "
-		. "-subj /CN=$name/ -in $d/$name.csr -out $d/$name.crt "
-		. ">>$d/openssl.out 2>&1") == 0
-		or die "Can't sign certificate for $name $!\n";
-	$t->write_file("$name.chained.crt", $t->read_file("$name.crt")
-		. $t->read_file('intermediate.crt'));
-}
-
-$t->try_run('no njs.fetch')->plan(7);
-
-$t->run_daemon(\&dns_daemon, port(8981), $t);
-$t->waitforfile($t->testdir . '/' . port(8981));
-
-###############################################################################
-
-local $TODO = 'not yet' unless has_version('0.7.0');
-
-like(http_get('/https?domain=default.example.com&verify=false'),
-	qr/You are at default.example.com.$/s, 'fetch https');
-like(http_get('/https?domain=127.0.0.1&verify=false'),
-	qr/You are at default.example.com.$/s, 'fetch https by IP');
-like(http_get('/https?domain=1.example.com&verify=false'),
-	qr/You are at 1.example.com.$/s, 'fetch tls extension');
-like(http_get('/https.myca?domain=default.example.com'),
-	qr/You are at default.example.com.$/s, 'fetch https trusted certificate');
-like(http_get('/https.myca?domain=localhost'),
-	qr/connect failed/s, 'fetch https wrong CN certificate');
-like(http_get('/https?domain=default.example.com'),
-	qr/connect failed/s, 'fetch https non trusted CA');
-like(http_get('/https.myca.short?domain=default.example.com'),
-	qr/connect failed/s, 'fetch https CA too far');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub reply_handler {
-	my ($recv_data, $port, %extra) = @_;
-
-	my (@name, @rdata);
-
-	use constant NOERROR	=> 0;
-	use constant A		=> 1;
-	use constant IN		=> 1;
-
-	# default values
-
-	my ($hdr, $rcode, $ttl) = (0x8180, NOERROR, 3600);
-
-	# decode name
-
-	my ($len, $offset) = (undef, 12);
-	while (1) {
-		$len = unpack("\@$offset C", $recv_data);
-		last if $len == 0;
-		$offset++;
-		push @name, unpack("\@$offset A$len", $recv_data);
-		$offset += $len;
-	}
-
-	$offset -= 1;
-	my ($id, $type, $class) = unpack("n x$offset n2", $recv_data);
-
-	my $name = join('.', @name);
-
-	if ($type == A) {
-		push @rdata, rd_addr($ttl, '127.0.0.1');
-	}
-
-	$len = @name;
-	pack("n6 (C/a*)$len x n2", $id, $hdr | $rcode, 1, scalar @rdata,
-		0, 0, @name, $type, $class) . join('', @rdata);
-}
-
-sub rd_addr {
-	my ($ttl, $addr) = @_;
-
-	my $code = 'split(/\./, $addr)';
-
-	return pack 'n3N', 0xc00c, A, IN, $ttl if $addr eq '';
-
-	pack 'n3N nC4', 0xc00c, A, IN, $ttl, eval "scalar $code", eval($code);
-}
-
-sub dns_daemon {
-	my ($port, $t) = @_;
-
-	my ($data, $recv_data);
-	my $socket = IO::Socket::INET->new(
-		LocalAddr    => '127.0.0.1',
-		LocalPort    => $port,
-		Proto        => 'udp',
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	# signal we are ready
-
-	open my $fh, '>', $t->testdir() . '/' . $port;
-	close $fh;
-
-	while (1) {
-		$socket->recv($recv_data, 65536);
-		$data = reply_handler($recv_data, $port);
-		$socket->send($data);
-	}
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_fetch_objects.t
+++ /dev/null
@@ -1,520 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, fetch objects.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /headers {
-            js_content test.headers;
-        }
-
-        location /request {
-            js_content test.request;
-        }
-
-        location /response {
-            js_content test.response;
-        }
-
-        location /fetch {
-            js_content test.fetch;
-        }
-
-        location /fetch_multi_header {
-            js_content test.fetch_multi_header;
-        }
-
-        location /method {
-            return 200 $request_method;
-        }
-
-        location /header {
-            return 200 $http_a;
-        }
-
-        location /body {
-            js_content test.body;
-        }
-    }
-}
-
-EOF
-
-my $p0 = port(8080);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function header(r) {
-        r.return(200, r.headersIn.a);
-    }
-
-    function body(r) {
-        r.return(201, r.requestText);
-    }
-
-    async function run(r, tests) {
-        var fails = [];
-        for (var i = 0; i < tests.length; i++) {
-            var v, t = tests[i];
-
-            try {
-                v = await t[1]();
-
-            } catch (e) {
-                v = e.message;
-            }
-
-            if (v != t[2]) {
-                fails.push(`\${t[0]}: got "\${v}" expected: "\${t[2]}"\n`);
-            }
-        }
-
-        r.return(fails.length ? 400 : 200, fails);
-    }
-
-    async function headers(r) {
-        const tests = [
-            ['empty', () => {
-                var h = new Headers();
-                return h.get('a');
-             }, null],
-            ['normal', () => {
-                var h = new Headers({a: 'X', b: 'Z'});
-                return `\${h.get('a')} \${h.get('B')}`;
-             }, 'X Z'],
-            ['trim value', () => {
-                var h = new Headers({a: '  X   '});
-                return h.get('a');
-             }, 'X'],
-            ['invalid header name', () => {
-                const valid = "!#\$\%&'*+-.^_`|~0123456789";
-
-                for (var i = 0; i < 128; i++) {
-                    var c = String.fromCodePoint(i);
-
-                    if (valid.indexOf(c) != -1 || /[a-zA-Z]+/.test(c)) {
-                        continue;
-                    }
-
-                    try {
-                        new Headers([[c, 'a']]);
-                        throw new Error(
-                                   `header with "\${c}" (\${i}) should throw`);
-
-                    } catch (e) {
-                        if (e.message != 'invalid header name') {
-                            throw e;
-                        }
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-            ['invalid header value', () => {
-                var h = new Headers({A: 'aa\x00a'});
-             }, 'invalid header value'],
-            ['combine', () => {
-                var h = new Headers({a: 'X', A: 'Z'});
-                return h.get('a');
-             }, 'X, Z'],
-            ['combine2', () => {
-                var h = new Headers([['A', 'x'], ['a', 'z']]);
-                return h.get('a');
-             }, 'x, z'],
-            ['combine3', () => {
-                var h = new Headers();
-                h.append('a', 'A');
-                h.append('a', 'B');
-                h.append('a', 'C');
-                h.append('a', 'D');
-                h.append('a', 'E');
-                h.append('a', 'F');
-                return h.get('a');
-             }, 'A, B, C, D, E, F'],
-            ['getAll', () => {
-                var h = new Headers({a: 'X', A: 'Z'});
-                return njs.dump(h.getAll('a'));
-             }, "['X','Z']"],
-            ['inherit', () => {
-                var h = new Headers({a: 'X', b: 'Y'});
-                var h2 = new Headers(h);
-                h2.append('c', 'Z');
-                return h2.has('a') && h2.has('B') && h2.has('c');
-             }, true],
-            ['delete', () => {
-                var h = new Headers({a: 'X', b: 'Z'});
-                h.delete('b');
-                return h.get('a') && !h.get('b');
-             }, true],
-            ['forEach', () => {
-                var r = [];
-                var h = new Headers({a: '0', b: '1', c: '2'});
-                h.delete('b');
-                h.append('z', '3');
-                h.append('a', '4');
-                h.append('q', '5');
-                h.forEach((v, k) => { r.push(`\${v}:\${k}`)})
-                return r.join('|');
-             }, 'a:0, 4|c:2|q:5|z:3'],
-            ['set', () => {
-                var h = new Headers([['A', 'x'], ['a', 'y'], ['a', 'z']]);
-                h.set('a', '#');
-                return h.get('a');
-             }, '#'],
-        ];
-
-        run(r, tests);
-    }
-
-    async function request(r) {
-        const tests = [
-            ['empty', () => {
-                try {
-                    new Request();
-                    throw new Error(`Request() should throw`);
-
-                } catch (e) {
-                    if (e.message != '1st argument is required') {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-            ['normal', () => {
-                var r = new Request("http://nginx.org",
-                                    {headers: {a: 'X', b: 'Y'}});
-                return `\${r.url}: \${r.method} \${r.headers.a}`;
-             }, 'http://nginx.org: GET X'],
-            ['url trim', () => {
-                var r = new Request("\\x00\\x01\\x02\\x03\\x05\\x06\\x07\\x08"
-                                    + "\\x09\\x0a\\x0b\\x0c\\x0d\\x0e\\x0f"
-                                    + "\\x10\\x11\\x12\\x13\\x14\\x15\\x16"
-                                    + "\\x17\\x18\\x19\\x1a\\x1b\\x1c\\x1d"
-                                    + "\\x1e\\x1f\\x20http://nginx.org\\x00"
-                                    + "\\x01\\x02\\x03\\x05\\x06\\x07\\x08"
-                                    + "\\x09\\x0a\\x0b\\x0c\\x0d\\x0e\\x0f"
-                                    + "\\x10\\x11\\x12\\x13\\x14\\x15\\x16"
-                                    + "\\x17\\x18\\x19\\x1a\\x1b\\x1c\\x1d"
-                                    + "\\x1e\\x1f\\x20");
-                return r.url;
-             }, 'http://nginx.org'],
-            ['read only', () => {
-                var r = new Request("http://nginx.org");
-
-                const props = ['bodyUsed', 'cache', 'credentials', 'headers',
-                               'method', 'mode', 'url'];
-                try {
-                    props.forEach(prop => {
-                        r[prop] = 1;
-                        throw new Error(
-                                    `setting read-only \${prop} should throw`);
-                    })
-
-                } catch (e) {
-                    if (!e.message.startsWith('Cannot assign to read-only p')) {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-            ['cache', () => {
-                const props = ['default', 'no-cache', 'no-store', 'reload',
-                               'force-cache', 'only-if-cached', '#'];
-                try {
-                    props.forEach(cv => {
-                        var r = new Request("http://nginx.org", {cache: cv});
-                        if (r.cache != cv) {
-                            throw new Error(`r.cache != \${cv}`);
-                        }
-                    })
-
-                } catch (e) {
-                    if (!e.message.startsWith('unknown cache type: #')) {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-            ['credentials', () => {
-                const props = ['omit', 'include', 'same-origin', '#'];
-                try {
-                    props.forEach(cr => {
-                        var r = new Request("http://nginx.org",
-                                            {credentials: cr});
-                        if (r.credentials != cr) {
-                            throw new Error(`r.credentials != \${cr}`);
-                        }
-                    })
-
-                } catch (e) {
-                    if (!e.message.startsWith('unknown credentials type: #')) {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-            ['method', () => {
-                const methods = ['get', 'hEad', 'Post', 'OPTIONS', 'PUT',
-                                 'DELETE', 'CONNECT'];
-                try {
-                    methods.forEach(m => {
-                        var r = new Request("http://nginx.org", {method: m});
-                        if (r.method != m.toUpperCase()) {
-                            throw new Error(`r.method != \${m}`);
-                        }
-                    })
-
-                } catch (e) {
-                    if (!e.message.startsWith('forbidden method: CONNECT')) {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-            ['mode', () => {
-                const props = ['same-origin', 'cors', 'no-cors', 'navigate',
-                               'websocket', '#'];
-                try {
-                    props.forEach(m => {
-                        var r = new Request("http://nginx.org", {mode: m});
-                        if (r.mode != m) {
-                            throw new Error(`r.mode != \${m}`);
-                        }
-                    })
-
-                } catch (e) {
-                    if (!e.message.startsWith('unknown mode type: #')) {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-            ['inherit', () => {
-                var r = new Request("http://nginx.org",
-                                    {headers: {a: 'X', b: 'Y'}});
-                var r2 = new Request(r);
-                r2.headers.append('a', 'Z')
-                return `\${r2.url}: \${r2.headers.get('a')}`;
-             }, 'http://nginx.org: X, Z'],
-            ['inherit2', () => {
-                var r = new Request("http://nginx.org",
-                                    {headers: {a: 'X', b: 'Y'}});
-                var r2 = new Request(r);
-                r2.headers.append('a', 'Z')
-                return `\${r.url}: \${r.headers.get('a')}`;
-             }, 'http://nginx.org: X'],
-            ['inherit3', () => {
-                var h = new Headers();
-                h.append('a', 'X');
-                h.append('a', 'Z');
-                var r = new Request("http://nginx.org", {headers: h});
-                return `\${r.url}: \${r.headers.get('a')}`;
-             }, 'http://nginx.org: X, Z'],
-            ['content type', async () => {
-                var r = new Request("http://nginx.org",
-                                    {body: 'ABC', method: 'POST'});
-                var body = await r.text();
-                return `\${body}: \${r.headers.get('Content-Type')}`;
-             }, 'ABC: text/plain;charset=UTF-8'],
-            ['GET body', () => {
-                try {
-                    var r = new Request("http://nginx.org", {body: 'ABC'});
-
-                } catch (e) {
-                    if (!e.message.startsWith('Request body incompatible w')) {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-        ];
-
-        run(r, tests);
-    }
-
-    async function response(r) {
-        const tests = [
-            ['empty', async () => {
-                var r = new Response();
-                var body = await r.text();
-                return `\${r.url}: \${r.status} \${body} \${r.headers.get('a')}`;
-             }, ': 200  null'],
-            ['normal', async () => {
-                var r = new Response("ABC", {headers: {a: 'X', b: 'Y'}});
-                var body = await r.text();
-                return `\${r.url}: \${r.status} \${body} \${r.headers.get('a')}`;
-             }, ': 200 ABC X'],
-            ['headers', async () => {
-                var r = new Response(null,
-                                    {headers: new Headers({a: 'X', b: 'Y'})});
-                var body = await r.text();
-                return `\${r.url}: \${body} \${r.headers.get('b')}`;
-             }, ':  Y'],
-            ['json', async () => {
-                var r = new Response('{"a": {"b": 42}}');
-                var json = await r.json();
-                return json.a.b;
-             }, 42],
-            ['statusText', () => {
-                const statuses = ['status text', 'aa\\u0000a'];
-                try {
-                    statuses.forEach(s => {
-                        var r = new Response(null, {statusText: s});
-                        if (r.statusText != s) {
-                            throw new Error(`r.statusText != \${s}`);
-                        }
-                    })
-
-                } catch (e) {
-                    if (!e.message.startsWith('invalid Response statusText')) {
-                        throw e;
-                    }
-                }
-
-                return 'OK';
-
-             }, 'OK'],
-        ];
-
-        run(r, tests);
-    }
-
-    async function fetch(r) {
-        const tests = [
-            ['method', async () => {
-                var req = new Request("http://127.0.0.1:$p0/method",
-                                      {method: 'PUT'});
-                var r = await ngx.fetch(req);
-                var body = await r.text();
-                return `\${r.url}: \${r.status} \${body} \${r.headers.get('a')}`;
-             }, 'http://127.0.0.1:$p0/method: 200 PUT null'],
-            ['request body', async () => {
-                var req = new Request("http://127.0.0.1:$p0/body",
-                                      {body: 'foo'});
-                var r = await ngx.fetch(req);
-                var body = await r.text();
-                return `\${r.url}: \${r.status} \${body}`;
-             }, 'http://127.0.0.1:$p0/body: 201 foo'],
-        ];
-
-        run(r, tests);
-    }
-
-    async function fetch_multi_header(r) {
-        const tests = [
-            ['request multi header', async () => {
-                var h = new Headers({a: 'X'});
-                h.append('a', 'Z');
-                var req = new Request("http://127.0.0.1:$p0/header",
-                                      {headers: h});
-                var r = await ngx.fetch(req);
-                var body = await r.text();
-                return `\${r.url}: \${r.status} \${body}`;
-             }, 'http://127.0.0.1:$p0/header: 200 X, Z'],
-        ];
-
-        run(r, tests);
-    }
-
-     export default {njs: test_njs, body, headers, request, response, fetch,
-                     fetch_multi_header};
-EOF
-
-$t->try_run('no njs')->plan(5);
-
-###############################################################################
-
-local $TODO = 'not yet' unless has_version('0.7.10');
-
-like(http_get('/headers'), qr/200 OK/s, 'headers tests');
-like(http_get('/request'), qr/200 OK/s, 'request tests');
-like(http_get('/response'), qr/200 OK/s, 'response tests');
-like(http_get('/fetch'), qr/200 OK/s, 'fetch tests');
-
-TODO: {
-local $TODO = 'not yet' unless $t->has_version('1.23.0');
-
-like(http_get('/fetch_multi_header'), qr/200 OK/s,
-	'fetch multi header tests');
-
-}
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_fetch_resolver.t
+++ /dev/null
@@ -1,231 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, fetch method, dns support.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use IO::Select;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-plan(skip_all => '127.0.0.2 local address required')
-	unless defined IO::Socket::INET->new( LocalAddr => '127.0.0.2' );
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /dns {
-            js_content test.dns;
-
-            resolver   127.0.0.1:%%PORT_8981_UDP%%;
-            resolver_timeout 1s;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  aaa;
-
-        location /loc {
-            js_content test.loc;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  many;
-
-        location /loc {
-            js_content test.loc;
-        }
-    }
-}
-
-EOF
-
-my $p0 = port(8080);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function dns(r) {
-        var url = `http://\${r.args.domain}:$p0/loc`;
-
-        ngx.fetch(url)
-        .then(reply => reply.text())
-        .then(body => r.return(200, body))
-        .catch(e => r.return(501, e.message))
-    }
-
-    function str(v) { return v ? v : ''};
-
-    function loc(r) {
-        var v = r.variables;
-        var body = str(r.requestText);
-        var foo = str(r.headersIn.foo);
-        var bar = str(r.headersIn.bar);
-        var c = r.headersIn.code ? Number(r.headersIn.code) : 200;
-        r.return(c, `\${v.host}:\${v.request_method}:\${foo}:\${bar}:\${body}`);
-    }
-
-     export default {njs: test_njs, dns, loc};
-EOF
-
-$t->try_run('no njs.fetch')->plan(3);
-
-$t->run_daemon(\&dns_daemon, port(8981), $t);
-$t->waitforfile($t->testdir . '/' . port(8981));
-
-###############################################################################
-
-like(http_get('/dns?domain=aaa'), qr/aaa:GET:::$/s, 'fetch dns aaa');
-like(http_get('/dns?domain=many'), qr/many:GET:::$/s, 'fetch dns many');
-like(http_get('/dns?domain=unknown'), qr/"unknown" could not be resolved/s,
-	'fetch dns unknown');
-
-###############################################################################
-
-sub reply_handler {
-	my ($recv_data, $port, %extra) = @_;
-
-	my (@name, @rdata);
-
-	use constant NOERROR	=> 0;
-	use constant FORMERR	=> 1;
-	use constant SERVFAIL	=> 2;
-	use constant NXDOMAIN	=> 3;
-
-	use constant A		=> 1;
-
-	use constant IN		=> 1;
-
-	# default values
-
-	my ($hdr, $rcode, $ttl) = (0x8180, NOERROR, 3600);
-
-	# decode name
-
-	my ($len, $offset) = (undef, 12);
-	while (1) {
-		$len = unpack("\@$offset C", $recv_data);
-		last if $len == 0;
-		$offset++;
-		push @name, unpack("\@$offset A$len", $recv_data);
-		$offset += $len;
-	}
-
-	$offset -= 1;
-	my ($id, $type, $class) = unpack("n x$offset n2", $recv_data);
-
-	my $name = join('.', @name);
-
-	if ($name eq 'aaa' && $type == A) {
-		push @rdata, rd_addr($ttl, '127.0.0.1');
-
-	} elsif ($name eq 'many' && $type == A) {
-		push @rdata, rd_addr($ttl, '127.0.0.2');
-		push @rdata, rd_addr($ttl, '127.0.0.1');
-	}
-
-	$len = @name;
-	pack("n6 (C/a*)$len x n2", $id, $hdr | $rcode, 1, scalar @rdata,
-		0, 0, @name, $type, $class) . join('', @rdata);
-}
-
-sub rd_addr {
-	my ($ttl, $addr) = @_;
-
-	my $code = 'split(/\./, $addr)';
-
-	return pack 'n3N', 0xc00c, A, IN, $ttl if $addr eq '';
-
-	pack 'n3N nC4', 0xc00c, A, IN, $ttl, eval "scalar $code", eval($code);
-}
-
-sub dns_daemon {
-	my ($port, $t, %extra) = @_;
-
-	my ($data, $recv_data);
-	my $socket = IO::Socket::INET->new(
-		LocalAddr => '127.0.0.1',
-		LocalPort => $port,
-		Proto => 'udp',
-	)
-		or die "Can't create listening socket: $!\n";
-
-	my $sel = IO::Select->new($socket);
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	# signal we are ready
-
-	open my $fh, '>', $t->testdir() . '/' . $port;
-	close $fh;
-
-	while (my @ready = $sel->can_read) {
-		foreach my $fh (@ready) {
-			if ($socket == $fh) {
-				$fh->recv($recv_data, 65536);
-				$data = reply_handler($recv_data, $port);
-				$fh->send($data);
-
-			} else {
-				$fh->recv($recv_data, 65536);
-				unless (length $recv_data) {
-					$sel->remove($fh);
-					$fh->close;
-					next;
-				}
-
-again:
-				my $len = unpack("n", $recv_data);
-				$data = substr $recv_data, 2, $len;
-				$data = reply_handler($data, $port, tcp => 1);
-				$data = pack("n", length $data) . $data;
-				$fh->send($data);
-				$recv_data = substr $recv_data, 2 + $len;
-				goto again if length $recv_data;
-			}
-		}
-	}
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_fetch_timeout.t
+++ /dev/null
@@ -1,119 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, fetch method timeout.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /normal_timeout {
-            js_content test.timeout_test;
-        }
-
-        location /short_timeout {
-            js_fetch_timeout 200ms;
-            js_content test.timeout_test;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location /normal_reply {
-            js_content test.normal_reply;
-        }
-
-        location /delayed_reply {
-            js_content test.delayed_reply;
-        }
-    }
-}
-
-EOF
-
-my $p1 = port(8081);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    async function timeout_test(r) {
-        let rs = await Promise.allSettled([
-            'http://127.0.0.1:$p1/normal_reply',
-            'http://127.0.0.1:$p1/delayed_reply',
-        ].map(v => ngx.fetch(v)));
-
-        let bs = rs.map(v => ({s: v.status, v: v.value ? v.value.headers.X
-                                                       : v.reason}));
-
-        r.return(200, njs.dump(bs));
-    }
-
-    function normal_reply(r) {
-        r.headersOut.X = 'N';
-        r.return(200);
-    }
-
-    function delayed_reply(r) {
-        r.headersOut.X = 'D';
-        setTimeout((r) => { r.return(200); }, 250, r, 0);
-    }
-
-     export default {njs: test_njs, timeout_test, normal_reply, delayed_reply};
-EOF
-
-$t->try_run('no js_fetch_timeout')->plan(2);
-
-###############################################################################
-
-like(http_get('/normal_timeout'),
-	qr/\[\{s:'fulfilled',v:'N'},\{s:'fulfilled',v:'D'}]$/s,
-	'normal timeout');
-like(http_get('/short_timeout'),
-	qr/\[\{s:'fulfilled',v:'N'},\{s:'rejected',v:Error: read timed out}]$/s,
-	'short timeout');
-
-###############################################################################
deleted file mode 100644
--- a/js_fetch_verify.t
+++ /dev/null
@@ -1,192 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Sergey Kandaurov
-# (C) Nginx, Inc.
-
-# Tests for http njs module, fetch method, backend certificate verification.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http http_ssl/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        resolver   127.0.0.1:%%PORT_8981_UDP%%;
-        resolver_timeout 1s;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /https {
-            js_content test.https;
-        }
-
-        location /https.verify_off {
-            js_content test.https;
-            js_fetch_verify off;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081 ssl;
-        server_name  localhost;
-
-        ssl_certificate localhost.crt;
-        ssl_certificate_key localhost.key;
-    }
-}
-
-EOF
-
-my $p1 = port(8081);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function https(r) {
-        ngx.fetch(`https://example.com:$p1/loc`)
-        .then(reply => reply.text())
-        .then(body => r.return(200, body))
-        .catch(e => r.return(501, e.message));
-    }
-
-    export default {njs: test_njs, https};
-EOF
-
-$t->write_file('openssl.conf', <<EOF);
-[ req ]
-default_bits = 2048
-encrypt_key = no
-distinguished_name = req_distinguished_name
-[ req_distinguished_name ]
-EOF
-
-my $d = $t->testdir();
-
-foreach my $name ('localhost') {
-	system('openssl req -x509 -new '
-		. "-config $d/openssl.conf -subj /CN=$name/ "
-		. "-out $d/$name.crt -keyout $d/$name.key "
-		. ">>$d/openssl.out 2>&1") == 0
-		or die "Can't create certificate for $name: $!\n";
-}
-
-$t->try_run('no js_fetch_verify')->plan(2);
-
-$t->run_daemon(\&dns_daemon, port(8981), $t);
-$t->waitforfile($t->testdir . '/' . port(8981));
-
-###############################################################################
-
-like(http_get('/https'), qr/connect failed/, 'fetch verify error');
-like(http_get('/https.verify_off'), qr/200 OK/, 'fetch verify off');
-
-###############################################################################
-
-sub reply_handler {
-	my ($recv_data, $port, %extra) = @_;
-
-	my (@name, @rdata);
-
-	use constant NOERROR	=> 0;
-	use constant A		=> 1;
-	use constant IN		=> 1;
-
-	# default values
-
-	my ($hdr, $rcode, $ttl) = (0x8180, NOERROR, 3600);
-
-	# decode name
-
-	my ($len, $offset) = (undef, 12);
-	while (1) {
-		$len = unpack("\@$offset C", $recv_data);
-		last if $len == 0;
-		$offset++;
-		push @name, unpack("\@$offset A$len", $recv_data);
-		$offset += $len;
-	}
-
-	$offset -= 1;
-	my ($id, $type, $class) = unpack("n x$offset n2", $recv_data);
-
-	my $name = join('.', @name);
-
-	if ($type == A) {
-		push @rdata, rd_addr($ttl, '127.0.0.1');
-	}
-
-	$len = @name;
-	pack("n6 (C/a*)$len x n2", $id, $hdr | $rcode, 1, scalar @rdata,
-		0, 0, @name, $type, $class) . join('', @rdata);
-}
-
-sub rd_addr {
-	my ($ttl, $addr) = @_;
-
-	my $code = 'split(/\./, $addr)';
-
-	return pack 'n3N', 0xc00c, A, IN, $ttl if $addr eq '';
-
-	pack 'n3N nC4', 0xc00c, A, IN, $ttl, eval "scalar $code", eval($code);
-}
-
-sub dns_daemon {
-	my ($port, $t) = @_;
-
-	my ($data, $recv_data);
-	my $socket = IO::Socket::INET->new(
-		LocalAddr    => '127.0.0.1',
-		LocalPort    => $port,
-		Proto        => 'udp',
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	# signal we are ready
-
-	open my $fh, '>', $t->testdir() . '/' . $port;
-	close $fh;
-
-	while (1) {
-		$socket->recv($recv_data, 65536);
-		$data = reply_handler($recv_data, $port);
-		$socket->send($data);
-	}
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_header_filter.t
+++ /dev/null
@@ -1,93 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, header filter.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http proxy rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /filter/ {
-            js_header_filter test.filter;
-            proxy_pass http://127.0.0.1:8081/;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location / {
-            add_header Set-Cookie "BB";
-            add_header Set-Cookie "CCCC";
-
-            return 200;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function filter(r) {
-        var cookies = r.headersOut['Set-Cookie'];
-        var len = r.args.len ? Number(r.args.len) : 0;
-        r.headersOut['Set-Cookie'] = cookies.filter(v=>v.length > len);
-    }
-
-    export default {njs: test_njs, filter};
-
-EOF
-
-$t->try_run('no njs header filter')->plan(2);
-
-###############################################################################
-
-like(http_get('/filter/?len=1'), qr/Set-Cookie: BB.*Set-Cookie: CCCC.*/ms,
-	'all');;
-unlike(http_get('/filter/?len=3'), qr/Set-Cookie: BB/,
-	'filter');
-
-###############################################################################
deleted file mode 100644
--- a/js_header_filter_if.t
+++ /dev/null
@@ -1,95 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, header filter, if context.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http proxy rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location / {
-            if ($arg_name ~ "add") {
-                js_header_filter test.add;
-            }
-
-            js_header_filter test.add2;
-
-            proxy_pass http://127.0.0.1:8081/;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location / {
-            return 200;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function add(r) {
-        r.headersOut['Foo'] = 'bar';
-    }
-
-    function add2(r) {
-        r.headersOut['Bar'] = 'xxx';
-    }
-
-    export default {njs: test_njs, add, add2};
-
-EOF
-
-$t->try_run('no njs header filter')->plan(2);
-
-###############################################################################
-
-like(http_get('/?name=add'), qr/Foo: bar/, 'header filter if');
-like(http_get('/'), qr/Bar: xxx/, 'header filter');
-
-###############################################################################
deleted file mode 100644
--- a/js_headers.t
+++ /dev/null
@@ -1,568 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, working with headers.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http charset/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_set $test_foo_in   test.foo_in;
-    js_set $test_ifoo_in  test.ifoo_in;
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /content_length {
-            js_content test.content_length;
-        }
-
-        location /content_length_arr {
-            js_content test.content_length_arr;
-        }
-
-        location /content_length_keys {
-            js_content test.content_length_keys;
-        }
-
-        location /content_type {
-            charset windows-1251;
-
-            default_type text/plain;
-            js_content test.content_type;
-        }
-
-        location /content_type_arr {
-            charset windows-1251;
-
-            default_type text/plain;
-            js_content test.content_type_arr;
-        }
-
-        location /content_encoding {
-            js_content test.content_encoding;
-        }
-
-        location /content_encoding_arr {
-            js_content test.content_encoding_arr;
-        }
-
-        location /headers_list {
-            js_content test.headers_list;
-        }
-
-        location /foo_in {
-            return 200 $test_foo_in;
-        }
-
-        location /ifoo_in {
-            return 200 $test_ifoo_in;
-        }
-
-        location /hdr_in {
-            js_content test.hdr_in;
-        }
-
-        location /raw_hdr_in {
-            js_content test.raw_hdr_in;
-        }
-
-        location /hdr_out {
-            js_content test.hdr_out;
-        }
-
-        location /raw_hdr_out {
-            js_content test.raw_hdr_out;
-        }
-
-        location /hdr_out_array {
-            js_content test.hdr_out_array;
-        }
-
-        location /hdr_out_set_cookie {
-            js_content test.hdr_out_set_cookie;
-        }
-
-        location /hdr_out_single {
-            js_content test.hdr_out_single;
-        }
-
-        location /ihdr_out {
-            js_content test.ihdr_out;
-        }
-
-        location /hdr_sorted_keys {
-            js_content test.hdr_sorted_keys;
-        }
-
-        location /hdr_out_special_set {
-            js_content test.hdr_out_special_set;
-        }
-
-        location /copy_subrequest_hdrs {
-            js_content test.copy_subrequest_hdrs;
-        }
-
-        location = /subrequest {
-            internal;
-
-            js_content test.subrequest;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function content_length(r) {
-        if (njs.version_number >= 0x000705) {
-            var clength = r.headersOut['Content-Length'];
-            if (clength !== undefined) {
-                r.return(500, `Content-Length "\${clength}" is not empty`);
-                return;
-            }
-        }
-
-        delete r.headersOut['Content-Length'];
-        r.headersOut['Content-Length'] = '';
-        r.headersOut['Content-Length'] = 3;
-        delete r.headersOut['Content-Length'];
-        r.headersOut['Content-Length'] = 3;
-        r.sendHeader();
-        r.send('XXX');
-        r.finish();
-    }
-
-    function content_length_arr(r) {
-        r.headersOut['Content-Length'] = [5];
-        r.headersOut['Content-Length'] = [];
-        r.headersOut['Content-Length'] = [4,3];
-        r.sendHeader();
-        r.send('XXX');
-        r.finish();
-    }
-
-    function content_length_keys(r) {
-        r.headersOut['Content-Length'] = 3;
-        var in_keys = Object.keys(r.headersOut).some(v=>v=='Content-Length');
-        r.return(200, `B:\${in_keys}`);
-    }
-
-    function content_type(r) {
-        if (njs.version_number >= 0x000705) {
-            var ctype = r.headersOut['Content-Type'];
-            if (ctype !== undefined) {
-                r.return(500, `Content-Type "\${ctype}" is not empty`);
-                return;
-            }
-        }
-
-        delete r.headersOut['Content-Type'];
-        r.headersOut['Content-Type'] = 'text/xml';
-        r.headersOut['Content-Type'] = '';
-        r.headersOut['Content-Type'] = 'text/xml; charset=';
-        delete r.headersOut['Content-Type'];
-        r.headersOut['Content-Type'] = 'text/xml; charset=utf-8';
-        r.headersOut['Content-Type'] = 'text/xml; charset="utf-8"';
-        var in_keys = Object.keys(r.headersOut).some(v=>v=='Content-Type');
-        r.return(200, `B:\${in_keys}`);
-    }
-
-    function content_type_arr(r) {
-        r.headersOut['Content-Type'] = ['text/html'];
-        r.headersOut['Content-Type'] = [];
-        r.headersOut['Content-Type'] = [ 'text/xml', 'text/html'];
-        r.return(200);
-    }
-
-    function content_encoding(r) {
-        if (njs.version_number >= 0x000705) {
-            var ce = r.headersOut['Content-Encoding'];
-            if (ce !== undefined) {
-                r.return(500, `Content-Encoding "\${ce}" is not empty`);
-                return;
-            }
-        }
-
-        delete r.headersOut['Content-Encoding'];
-        r.headersOut['Content-Encoding'] = '';
-        r.headersOut['Content-Encoding'] = 'test';
-        delete r.headersOut['Content-Encoding'];
-        r.headersOut['Content-Encoding'] = 'gzip';
-        r.return(200);
-    }
-
-    function content_encoding_arr(r) {
-        r.headersOut['Content-Encoding'] = 'test';
-        r.headersOut['Content-Encoding'] = [];
-        r.headersOut['Content-Encoding'] = ['test', 'gzip'];
-        r.return(200);
-    }
-
-    function headers_list(r) {
-        for (var h in {a:1, b:2, c:3}) {
-            r.headersOut[h] = h;
-        }
-
-        delete r.headersOut.b;
-        r.headersOut.d = 'd';
-
-        var out = "";
-        for (var h in r.headersOut) {
-            out += h + ":";
-        }
-
-        r.return(200, out);
-    }
-
-    function hdr_in(r) {
-        var s = '', h;
-        for (h in r.headersIn) {
-            s += `\${h.toLowerCase()}: \${r.headersIn[h]}\n`;
-        }
-
-        r.return(200, s);
-    }
-
-    function raw_hdr_in(r) {
-        var filtered = r.rawHeadersIn
-                       .filter(v=>v[0].toLowerCase() == r.args.filter);
-        r.return(200, 'raw:' + filtered.map(v=>v[1]).join('|'));
-    }
-
-    function hdr_sorted_keys(r) {
-        var s = '';
-        var hdr = r.args.in ? r.headersIn : r.headersOut;
-
-        if (!r.args.in) {
-            r.headersOut.b = 'b';
-            r.headersOut.c = 'c';
-            r.headersOut.a = 'a';
-        }
-
-        r.return(200, Object.keys(hdr).sort());
-    }
-
-    function foo_in(r) {
-        return 'hdr=' + r.headersIn.foo;
-    }
-
-    function ifoo_in(r) {
-        var s = '', h;
-        for (h in r.headersIn) {
-            if (h.substr(0, 3) == 'foo') {
-                s += r.headersIn[h];
-            }
-        }
-        return s;
-    }
-
-    function hdr_out(r) {
-        r.status = 200;
-        r.headersOut['Foo'] = r.args.foo;
-
-        if (r.args.bar) {
-            r.headersOut['Bar'] =
-                r.headersOut[(r.args.bar == 'empty' ? 'Baz' :'Foo')]
-        }
-
-        r.sendHeader();
-        r.finish();
-    }
-
-    function raw_hdr_out(r) {
-        r.headersOut.a = ['foo', 'bar'];
-        r.headersOut.b = 'b';
-
-        var filtered = r.rawHeadersOut
-                       .filter(v=>v[0].toLowerCase() == r.args.filter);
-        r.return(200, 'raw:' + filtered.map(v=>v[1]).join('|'));
-    }
-
-    function hdr_out_array(r) {
-        if (!r.args.hidden) {
-            r.headersOut['Foo'] = [r.args.foo];
-            r.headersOut['Foo'] = [];
-            r.headersOut['Foo'] = ['bar', r.args.foo];
-        }
-
-        if (r.args.scalar_set) {
-            r.headersOut['Foo'] = 'xxx';
-        }
-
-        r.return(200, `B:\${njs.dump(r.headersOut.foo)}`);
-    }
-
-    function hdr_out_single(r) {
-        r.headersOut.ETag = ['a', 'b'];
-        r.return(200, `B:\${njs.dump(r.headersOut.etag)}`);
-    }
-
-    function hdr_out_set_cookie(r) {
-        r.headersOut['Set-Cookie'] = [];
-        r.headersOut['Set-Cookie'] = ['a', 'b'];
-        delete r.headersOut['Set-Cookie'];
-        r.headersOut['Set-Cookie'] = 'e';
-        r.headersOut['Set-Cookie'] = ['c', '', null, 'd', 'f'];
-
-        r.return(200, `B:\${njs.dump(r.headersOut['Set-Cookie'])}`);
-    }
-
-    function ihdr_out(r) {
-        r.status = 200;
-        r.headersOut['a'] = r.args.a;
-        r.headersOut['b'] = r.args.b;
-
-        var s = '', h;
-        for (h in r.headersOut) {
-            s += r.headersOut[h];
-        }
-
-        r.sendHeader();
-        r.send(s);
-        r.finish();
-    }
-
-    function hdr_out_special_set(r) {
-        r.headersOut['Foo'] = "xxx";
-        r.headersOut['Content-Encoding'] = 'abc';
-
-        let ce = r.headersOut['Content-Encoding'];
-        r.return(200, `CE: \${ce}`);
-    }
-
-    async function copy_subrequest_hdrs(r) {
-        let resp = await r.subrequest("/subrequest");
-
-        for (const h in resp.headersOut) {
-            r.headersOut[h] = resp.headersOut[h];
-        }
-
-        r.return(200, resp.responseText);
-    }
-
-    function subrequest(r) {
-        r.headersOut['A'] = 'a';
-        r.headersOut['Content-Encoding'] = 'ce';
-        r.headersOut['B'] = 'b';
-        r.headersOut['C'] = 'c';
-        r.headersOut['D'] = 'd';
-        r.headersOut['Set-Cookie'] = ['A', 'BB'];
-        r.headersOut['Content-Length'] = 3;
-        r.headersOut['Content-Type'] = 'ct';
-        r.sendHeader();
-        r.send('XXX');
-        r.finish();
-    }
-
-    export default {njs:test_njs, content_length, content_length_arr,
-                    content_length_keys, content_type, content_type_arr,
-                    content_encoding, content_encoding_arr, headers_list,
-                    hdr_in, raw_hdr_in, hdr_sorted_keys, foo_in, ifoo_in,
-                    hdr_out, raw_hdr_out, hdr_out_array, hdr_out_single,
-                    hdr_out_set_cookie, ihdr_out, hdr_out_special_set,
-                    copy_subrequest_hdrs, subrequest};
-
-
-EOF
-
-$t->try_run('no njs')->plan(42);
-
-###############################################################################
-
-like(http_get('/content_length'), qr/Content-Length: 3/,
-	'set Content-Length');
-like(http_get('/content_type'), qr/Content-Type: text\/xml; charset="utf-8"\r/,
-	'set Content-Type');
-unlike(http_get('/content_type'), qr/Content-Type: text\/plain/,
-	'set Content-Type 2');
-like(http_get('/content_encoding'), qr/Content-Encoding: gzip/,
-	'set Content-Encoding');
-like(http_get('/headers_list'), qr/a:c:d/, 'headers list');
-
-like(http_get('/ihdr_out?a=12&b=34'), qr/^1234$/m, 'r.headersOut iteration');
-like(http_get('/ihdr_out'), qr/\x0d\x0a?\x0d\x0a?$/m, 'r.send zero');
-like(http_get('/hdr_out?foo=12345'), qr/Foo: 12345/, 'r.headersOut');
-like(http_get('/hdr_out?foo=123&bar=copy'), qr/Bar: 123/, 'r.headersOut get');
-unlike(http_get('/hdr_out?bar=empty'), qr/Bar:/, 'r.headersOut empty');
-unlike(http_get('/hdr_out?foo='), qr/Foo:/, 'r.headersOut no value');
-unlike(http_get('/hdr_out?foo'), qr/Foo:/, 'r.headersOut no value 2');
-
-like(http_get('/content_length_keys'), qr/B:true/, 'Content-Length in keys');
-like(http_get('/content_length_arr'), qr/Content-Length: 3/,
-	'set Content-Length arr');
-
-like(http_get('/content_type'), qr/B:true/, 'Content-Type in keys');
-like(http_get('/content_type_arr'), qr/Content-Type: text\/html/,
-	'set Content-Type arr');
-like(http_get('/content_encoding_arr'), qr/Content-Encoding: gzip/,
-	'set Content-Encoding arr');
-
-like(http_get('/hdr_out_array?foo=12345'), qr/Foo: bar\r\nFoo: 12345/,
-	'r.headersOut arr');
-like(http_get('/hdr_out_array'), qr/Foo: bar/,
-	'r.headersOut arr last is empty');
-like(http_get('/hdr_out_array?foo=abc'), qr/B:bar,\s?abc/,
-	'r.headersOut get');
-like(http_get('/hdr_out_array'), qr/B:bar/, 'r.headersOut get2');
-like(http_get('/hdr_out_array?hidden=1'), qr/B:undefined/,
-	'r.headersOut get3');
-like(http_get('/hdr_out_array?scalar_set=1'), qr/B:xxx/,
-	'r.headersOut scalar set');
-like(http_get('/hdr_out_single'), qr/ETag: a\r\nETag: b/,
-	'r.headersOut single');
-like(http_get('/hdr_out_single'), qr/B:a/,
-	'r.headersOut single get');
-like(http_get('/hdr_out_set_cookie'), qr/Set-Cookie: c\r\nSet-Cookie: d/,
-	'set_cookie');
-like(http_get('/hdr_out_set_cookie'), qr/B:\['c','d','f']/,
-	'set_cookie2');
-unlike(http_get('/hdr_out_set_cookie'), qr/Set-Cookie: [abe]/,
-	'set_cookie3');
-
-like(http(
-	'GET /hdr_in HTTP/1.0' . CRLF
-	. 'Cookie: foo' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/cookie: foo/, 'r.headersIn cookie');
-
-like(http(
-	'GET /hdr_in HTTP/1.0' . CRLF
-	. 'X-Forwarded-For: foo' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/x-forwarded-for: foo/, 'r.headersIn xff');
-
-like(http(
-	'GET /hdr_in HTTP/1.0' . CRLF
-	. 'Cookie: foo1' . CRLF
-	. 'Cookie: foo2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/cookie: foo1;\s?foo2/, 'r.headersIn cookie2');
-
-like(http(
-	'GET /hdr_in HTTP/1.0' . CRLF
-	. 'X-Forwarded-For: foo1' . CRLF
-	. 'X-Forwarded-For: foo2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/x-forwarded-for: foo1,\s?foo2/, 'r.headersIn xff2');
-
-like(http(
-	'GET /hdr_in HTTP/1.0' . CRLF
-	. 'ETag: bar1' . CRLF
-	. 'ETag: bar2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/etag: bar1(?!,\s?bar2)/, 'r.headersIn duplicate single');
-
-like(http(
-	'GET /hdr_in HTTP/1.0' . CRLF
-	. 'Content-Type: bar1' . CRLF
-	. 'Content-Type: bar2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/content-type: bar1(?!,\s?bar2)/, 'r.headersIn duplicate single 2');
-
-like(http(
-	'GET /hdr_in HTTP/1.0' . CRLF
-	. 'Foo: bar1' . CRLF
-	. 'Foo: bar2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/foo: bar1,\s?bar2/, 'r.headersIn duplicate generic');
-
-like(http(
-	'GET /raw_hdr_in?filter=foo HTTP/1.0' . CRLF
-	. 'foo: bar1' . CRLF
-	. 'Foo: bar2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/raw: bar1|bar2/, 'r.rawHeadersIn');
-
-like(http_get('/raw_hdr_out?filter=a'), qr/raw: foo|bar/, 'r.rawHeadersOut');
-
-like(http(
-	'GET /hdr_sorted_keys?in=1 HTTP/1.0' . CRLF
-	. 'Cookie: foo1' . CRLF
-	. 'Accept: */*' . CRLF
-	. 'Cookie: foo2' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/Accept,Cookie,Host/, 'r.headersIn sorted keys');
-
-like(http(
-	'GET /hdr_sorted_keys HTTP/1.0' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/a,b,c/, 'r.headersOut sorted keys');
-
-TODO: {
-local $TODO = 'not yet' unless has_version('0.7.6');
-
-like(http_get('/hdr_out_special_set'), qr/CE: abc/,
-	'r.headerOut special set');
-
-like(http_get('/copy_subrequest_hdrs'),
-	qr/A: a.*B: b.*C: c.*D: d.*Set-Cookie: A.*Set-Cookie: BB/s,
-	'subrequest copy');
-
-like(http_get('/copy_subrequest_hdrs'),
-	qr/Content-Type: ct.*Content-Encoding: ce.*Content-Length: 3/s,
-	'subrequest copy special');
-
-}
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_import.t
+++ /dev/null
@@ -1,108 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (c) Nginx, Inc.
-
-# Tests for http njs module, js_import directive.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_set $test foo.bar.p;
-
-    js_import lib.js;
-    js_import fun.js;
-    js_import foo from ./main.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content foo.version;
-        }
-
-        location /test_foo {
-            js_content foo.test;
-        }
-
-        location /test_lib {
-            js_content lib.test;
-        }
-
-        location /test_fun {
-            js_content fun;
-        }
-
-        location /test_var {
-            return 200 $test;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('lib.js', <<EOF);
-    function test(r) {
-        r.return(200, "LIB-TEST");
-    }
-
-    export default {test};
-
-EOF
-
-$t->write_file('fun.js', <<EOF);
-    export default function (r) {r.return(200, "FUN-TEST")};
-
-EOF
-
-$t->write_file('main.js', <<EOF);
-    function version(r) {
-        r.return(200, njs.version);
-    }
-
-    function test(r) {
-        r.return(200, "MAIN-TEST");
-    }
-
-    export default {version, test, bar: {p(r) {return "P-TEST"}}};
-
-EOF
-
-$t->try_run('no njs available')->plan(4);
-
-###############################################################################
-
-like(http_get('/test_foo'), qr/MAIN-TEST/s, 'foo.test');
-like(http_get('/test_lib'), qr/LIB-TEST/s, 'lib.test');
-like(http_get('/test_fun'), qr/FUN-TEST/s, 'fun');
-like(http_get('/test_var'), qr/P-TEST/s, 'foo.bar.p');
-
-###############################################################################
deleted file mode 100644
--- a/js_import2.t
+++ /dev/null
@@ -1,127 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (c) Nginx, Inc.
-
-# Tests for http njs module, js_import directive in server | location contexts.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http proxy rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        js_set $test foo.bar.p;
-
-        js_import foo from main.js;
-
-        location /njs {
-            js_content foo.version;
-        }
-
-        location /test_foo {
-            js_content foo.test;
-        }
-
-        location /test_lib {
-            js_import lib.js;
-            js_content lib.test;
-        }
-
-        location /test_fun {
-            js_import fun.js;
-            js_content fun;
-        }
-
-        location /test_var {
-            return 200 $test;
-        }
-
-        location /proxy {
-            proxy_pass http://127.0.0.1:8081/;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location /test_fun {
-            js_import fun.js;
-            js_content fun;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('lib.js', <<EOF);
-    function test(r) {
-        r.return(200, "LIB-TEST");
-    }
-
-    function p(r) {
-        return "LIB-P";
-    }
-
-    export default {test, p};
-
-EOF
-
-$t->write_file('fun.js', <<EOF);
-    export default function (r) {r.return(200, "FUN-TEST")};
-
-EOF
-
-$t->write_file('main.js', <<EOF);
-    function version(r) {
-        r.return(200, njs.version);
-    }
-
-    function test(r) {
-        r.return(200, "MAIN-TEST");
-    }
-
-    export default {version, test, bar: {p(r) {return "P-TEST"}}};
-
-EOF
-
-$t->try_run('no njs available')->plan(5);
-
-###############################################################################
-
-like(http_get('/test_foo'), qr/MAIN-TEST/s, 'foo.test');
-like(http_get('/test_lib'), qr/LIB-TEST/s, 'lib.test');
-like(http_get('/test_fun'), qr/FUN-TEST/s, 'fun');
-like(http_get('/proxy/test_fun'), qr/FUN-TEST/s, 'proxy fun');
-like(http_get('/test_var'), qr/P-TEST/s, 'foo.bar.p');
-
-###############################################################################
deleted file mode 100644
--- a/js_internal_redirect.t
+++ /dev/null
@@ -1,130 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, internalRedirect method.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /test {
-            js_content test.redirect;
-        }
-
-        location /redirect {
-            internal;
-            return 200 redirect$arg_b;
-        }
-
-        location @named {
-            return 200 named;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function redirect(r) {
-        if (r.variables.arg_dest == 'named') {
-            r.internalRedirect('\@named');
-
-        } else if (r.variables.arg_unsafe) {
-            r.internalRedirect('/red\0rect');
-
-        } else if (r.variables.arg_quoted) {
-            r.internalRedirect('/red%69rect');
-
-        } else {
-            if (r.variables.arg_a) {
-                r.internalRedirect('/redirect?b=' + r.variables.arg_a);
-
-            } else {
-                r.internalRedirect('/redirect');
-            }
-        }
-    }
-
-    export default {njs:test_njs, redirect};
-
-EOF
-
-$t->try_run('no njs available')->plan(5);
-
-###############################################################################
-
-like(http_get('/test'), qr/redirect/s, 'redirect');
-like(http_get('/test?a=A'), qr/redirectA/s, 'redirect with args');
-like(http_get('/test?dest=named'), qr/named/s, 'redirect to named location');
-
-TODO: {
-local $TODO = 'not yet' unless has_version('0.7.4');
-
-like(http_get('/test?unsafe=1'), qr/500 Internal Server/s,
-	'unsafe redirect');
-like(http_get('/test?quoted=1'), qr/200 .*redirect/s,
-	'quoted redirect');
-}
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_modules.t
+++ /dev/null
@@ -1,84 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, ES6 import, export.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /test {
-            js_content test.test;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    import m from 'module.js';
-
-    function test(r) {
-        r.return(200, m[r.args.fun](r.args.a, r.args.b));
-    }
-
-    export default {test};
-
-EOF
-
-$t->write_file('module.js', <<EOF);
-    function sum(a, b) {
-        return Number(a) + Number(b);
-    }
-
-    function prod(a, b) {
-        return Number(a) * Number(b);
-    }
-
-    export default {sum, prod};
-
-EOF
-
-
-$t->try_run('no njs modules')->plan(2);
-
-###############################################################################
-
-like(http_get('/test?fun=sum&a=3&b=4'), qr/7/s, 'test sum');
-like(http_get('/test?fun=prod&a=3&b=4'), qr/12/s, 'test prod');
-
-###############################################################################
deleted file mode 100644
--- a/js_ngx.t
+++ /dev/null
@@ -1,94 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, ngx object.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /log {
-            js_content test.log;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function level(r) {
-        switch (r.args.level) {
-        case 'INFO': return ngx.INFO;
-        case 'WARN': return ngx.WARN;
-        case 'ERR': return ngx.ERR;
-        default:
-            throw Error(`Unknown log level:"\${r.args.level}"`);
-        }
-    }
-
-    function log(r) {
-        ngx.log(level(r), `ngx.log:\${r.args.text}`);
-        r.return(200);
-    }
-
-    export default {njs: test_njs, log};
-
-EOF
-
-$t->try_run('no njs ngx')->plan(3);
-
-###############################################################################
-
-http_get('/log?level=INFO&text=FOO');
-http_get('/log?level=WARN&text=BAR');
-http_get('/log?level=ERR&text=BAZ');
-
-$t->stop();
-
-like($t->read_file('error.log'), qr/\[info\].*ngx.log:FOO/, 'ngx.log info');
-like($t->read_file('error.log'), qr/\[warn\].*ngx.log:BAR/, 'ngx.log warn');
-like($t->read_file('error.log'), qr/\[error\].*ngx.log:BAZ/, 'ngx.log err');
-
-###############################################################################
deleted file mode 100644
--- a/js_object.t
+++ /dev/null
@@ -1,137 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, request object.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /to_string {
-            js_content test.to_string;
-        }
-
-        location /define_prop {
-            js_content test.define_prop;
-        }
-
-        location /in_operator {
-            js_content test.in_operator;
-        }
-
-        location /redefine_bind {
-            js_content test.redefine_bind;
-        }
-
-        location /redefine_proxy {
-            js_content test.redefine_proxy;
-        }
-
-        location /redefine_proto {
-            js_content test.redefine_proto;
-        }
-
-        location /get_own_prop_descs {
-            js_content test.get_own_prop_descs;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function to_string(r) {
-        r.return(200, r.toString());
-    }
-
-    function define_prop(r) {
-        Object.defineProperty(r.headersOut, 'Foo', {value:'bar'});
-        r.return(200);
-    }
-
-    function in_operator(r) {
-        r.return(200, ['Foo', 'Bar'].map(v=>v in r.headersIn)
-                      .toString() === 'true,false');
-    }
-
-    function redefine_bind(r) {
-        r.return = r.return.bind(r, 200);
-        r.return('redefine_bind');
-    }
-
-    function redefine_proxy(r) {
-        r.return_orig = r.return;
-        r.return = function (body) { this.return_orig(200, body);}
-        r.return('redefine_proxy');
-    }
-
-    function redefine_proto(r) {
-        r[0] = 'a';
-        r[1] = 'b';
-        r.length = 2;
-        Object.setPrototypeOf(r, Array.prototype);
-        r.return(200, r.join('|'));
-    }
-
-    function get_own_prop_descs(r) {
-        r.return(200,
-                 Object.getOwnPropertyDescriptors(r)['log'].value === r.log);
-    }
-
-    export default {to_string, define_prop, in_operator, redefine_bind,
-                    redefine_proxy, redefine_proto, get_own_prop_descs};
-
-EOF
-
-$t->try_run('no njs request object')->plan(7);
-
-###############################################################################
-
-like(http_get('/to_string'), qr/\[object Request\]/, 'toString');
-like(http_get('/define_prop'), qr/Foo: bar/, 'define_prop');
-like(http(
-	'GET /in_operator HTTP/1.0' . CRLF
-	. 'Foo: foo' . CRLF
-	. 'Host: localhost' . CRLF . CRLF
-), qr/true/, 'in_operator');
-like(http_get('/redefine_bind'), qr/redefine_bind/, 'redefine_bind');
-like(http_get('/redefine_proxy'), qr/redefine_proxy/, 'redefine_proxy');
-like(http_get('/redefine_proto'), qr/a|b/, 'redefine_proto');
-like(http_get('/get_own_prop_descs'), qr/true/, 'get_own_prop_descs');
-
-###############################################################################
deleted file mode 100644
--- a/js_paths.t
+++ /dev/null
@@ -1,110 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, js_path directive.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_path "%%TESTDIR%%/lib1";
-    js_path "lib2";
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /test {
-            js_content test.test;
-        }
-
-        location /test2 {
-            js_content test.test2;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    import m1 from 'module1.js';
-    import m2 from 'module2.js';
-    import m3 from 'lib1/module1.js';
-
-    function test(r) {
-        r.return(200, m1[r.args.fun](r.args.a, r.args.b));
-    }
-
-    function test2(r) {
-        r.return(200, m2.sum(r.args.a, r.args.b));
-    }
-
-    function test3(r) {
-        r.return(200, m3.sum(r.args.a, r.args.b));
-    }
-
-    export default {test, test2};
-
-EOF
-
-my $d = $t->testdir();
-
-mkdir("$d/lib1");
-mkdir("$d/lib2");
-
-$t->write_file('lib1/module1.js', <<EOF);
-    function sum(a, b) { return Number(a) + Number(b); }
-    function prod(a, b) { return Number(a) * Number(b); }
-
-    export default {sum, prod};
-
-EOF
-
-$t->write_file('lib2/module2.js', <<EOF);
-    function sum(a, b) { return a + b; }
-
-    export default {sum};
-
-EOF
-
-
-$t->try_run('no njs available')->plan(4);
-
-###############################################################################
-
-like(http_get('/test?fun=sum&a=3&b=4'), qr/7/s, 'test sum');
-like(http_get('/test?fun=prod&a=3&b=4'), qr/12/s, 'test prod');
-like(http_get('/test2?a=3&b=4'), qr/34/s, 'test2');
-like(http_get('/test2?a=A&b=B'), qr/AB/s, 'test2 relative');
-
-###############################################################################
deleted file mode 100644
--- a/js_preload_object.t
+++ /dev/null
@@ -1,181 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Vadim Zhestikov
-# (C) Nginx, Inc.
-
-# Tests for http njs module, js_preload_object directive.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_preload_object g1 from g.json;
-    js_preload_object ga from ga.json;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        js_import lib.js;
-        js_preload_object lx from l.json;
-
-        location /test {
-            js_content lib.test;
-        }
-
-        location /test_query {
-            js_import lib1.js;
-            js_content lib1.query;
-        }
-
-        location /test_query_preloaded {
-            js_import lib1.js;
-            js_preload_object l.json;
-            js_content lib1.query;
-        }
-
-        location /test_var {
-            js_set $test_var lib.test_var;
-            return 200 $test_var;
-        }
-
-        location /test_mutate {
-            js_content lib.mutate;
-        }
-
-        location /test_no_suffix {
-            js_preload_object gg from no_suffix;
-            js_content lib.suffix;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('lib.js', <<EOF);
-    function test(r) {
-        r.return(200, ga + ' ' + g1.c.prop[0].a + ' ' + lx);
-    }
-
-    function test_var(r) {
-        return g1.b[2];
-    }
-
-    function mutate(r) {
-        var res = "OK";
-
-        try {
-            switch (r.args.method) {
-            case 'set_obj':
-                g1.c.prop[0].a = 5;
-                break;
-            case 'set_arr':
-                g1.c.prop[0] = 5;
-                break;
-            case 'add_obj':
-                g1.c.prop[0].xxx = 5;
-                break;
-            case 'add_arr':
-                g1.c.prop[10] = 5;
-                break;
-            case 'del_obj':
-                delete g1.c.prop[0].a;
-                break;
-            case 'del_arr':
-                delete g1.c.prop[0];
-                break;
-            }
-
-        } catch (e) {
-            res = e.message;
-        }
-
-        r.return(200, res);
-    }
-
-    function suffix(r) {
-        r.return(200, gg);
-    }
-
-    export default {test, test_var, mutate, suffix};
-
-EOF
-
-$t->write_file('lib1.js', <<EOF);
-    function query(r) {
-        var res = 'ok';
-
-        try {
-            res = r.args.path.split('.').reduce((a, v) => a[v], globalThis);
-
-        } catch (e) {
-            res = e.message;
-        }
-
-        r.return(200, njs.dump(res));
-    }
-
-    export default {query};
-
-EOF
-
-$t->write_file('g.json',
-	'{"a":1, "b":[1,2,"element",4,5], "c":{"prop":[{"a":2}]}}');
-$t->write_file('ga.json', '"ga loaded"');
-$t->write_file('l.json', '"l loaded"');
-$t->write_file('no_suffix', '"no_suffix loaded"');
-
-$t->try_run('no js_preload_object available')->plan(12);
-
-###############################################################################
-
-like(http_get('/test'), qr/ga loaded 2 l loaded/s, 'direct query');
-like(http_get('/test_query?path=l'), qr/undefined/s, 'unreferenced');
-like(http_get('/test_query_preloaded?path=l'), qr/l loaded/s,
-	'reference preload');
-like(http_get('/test_query?path=g1.b.1'), qr/2/s, 'complex query');
-like(http_get('/test_var'), qr/element/s, 'var reference');
-
-like(http_get('/test_mutate?method=set_obj'), qr/Cannot assign to read-only/s,
-	'preload_object props are const (object)');
-like(http_get('/test_mutate?method=set_arr'), qr/Cannot assign to read-only/s,
-	'preload_object props are const (array)');
-like(http_get('/test_mutate?method=add_obj'), qr/Cannot add property "xxx"/s,
-	'preload_object props are not extensible (object)');
-like(http_get('/test_mutate?method=add_arr'), qr/Cannot add property "10"/s,
-	'preload_object props are not extensible (array)');
-like(http_get('/test_mutate?method=del_obj'), qr/Cannot delete property "a"/s,
-	'preload_object props are not deletable (object)');
-like(http_get('/test_mutate?method=del_arr'), qr/Cannot delete property "0"/s,
-	'preload_object props are not deletable (array)');
-
-like(http_get('/test_no_suffix'), qr/no_suffix loaded/s,
-	'load without suffix');
-
-###############################################################################
deleted file mode 100644
--- a/js_promise.t
+++ /dev/null
@@ -1,201 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Nginx, Inc.
-
-# Promise tests for http njs module.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /promise {
-            js_content test.promise;
-        }
-
-        location /promise_throw {
-            js_content test.promise_throw;
-        }
-
-        location /promise_pure {
-            js_content test.promise_pure;
-        }
-
-        location /timeout {
-            js_content test.timeout;
-        }
-
-        location /sub_token {
-            js_content test.sub_token;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    var global_token = '';
-
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function promise(r) {
-        promisified_subrequest(r, '/sub_token', 'code=200&token=a')
-        .then(reply => {
-            var data = JSON.parse(reply.responseText);
-
-            if (data['token'] !== "a") {
-                throw new Error('token is not "a"');
-            }
-
-            return data['token'];
-        })
-        .then(token => {
-            promisified_subrequest(r, '/sub_token', 'code=200&token=b')
-            .then(reply => {
-                var data = JSON.parse(reply.responseText);
-
-                r.return(200, '{"token": "' + data['token'] + '"}');
-            })
-            .catch(() => {
-                throw new Error("failed promise() test");
-            });
-        })
-        .catch(() => {
-            r.return(500);
-        });
-    }
-
-    function promise_throw(r) {
-        promisified_subrequest(r, '/sub_token', 'code=200&token=x')
-        .then(reply => {
-            var data = JSON.parse(reply.responseText);
-
-            if (data['token'] !== "a") {
-                throw data['token'];
-            }
-
-            return data['token'];
-        })
-        .then(() => {
-            r.return(500);
-        })
-        .catch(token => {
-            r.return(200, '{"token": "' + token + '"}');
-        });
-    }
-
-    function promise_pure(r) {
-        var count = 0;
-
-        Promise.resolve(true)
-        .then(() => count++)
-        .then(() => not_exist_ref)
-        .finally(() => count++)
-        .catch(() => {
-            r.return((count != 2) ? 500 : 200);
-        });
-    }
-
-    function timeout(r) {
-        promisified_subrequest(r, '/sub_token', 'code=200&token=R')
-        .then(reply => JSON.parse(reply.responseText))
-        .then(data => {
-            setTimeout(timeout_cb, 50, r, '/sub_token', 'code=200&token=T');
-            return data;
-        })
-        .then(data => {
-            setTimeout(timeout_cb, 1, r, '/sub_token', 'code=200&token='
-                                                        + data['token']);
-        })
-        .catch(() => {
-            r.return(500);
-        });
-    }
-
-    function timeout_cb(r, url, args) {
-        promisified_subrequest(r, url, args)
-        .then(reply => {
-            if (global_token == '') {
-                var data = JSON.parse(reply.responseText);
-
-                global_token = data['token'];
-
-                r.return(200, '{"token": "' + data['token'] + '"}');
-            }
-        })
-        .catch(() => {
-            r.return(500);
-        });
-    }
-
-    function promisified_subrequest(r, uri, args) {
-        return new Promise((resolve, reject) => {
-            r.subrequest(uri, args, (reply) => {
-                if (reply.status < 400) {
-                    resolve(reply);
-                } else {
-                    reject(reply);
-                }
-            });
-        })
-    }
-
-    function sub_token(r) {
-        var code = r.variables.arg_code;
-        var token = r.variables.arg_token;
-
-        r.return(parseInt(code), '{"token": "'+ token +'"}');
-    }
-
-    export default {njs:test_njs, promise, promise_throw, promise_pure,
-                    timeout, sub_token};
-
-EOF
-
-$t->try_run('no njs available')->plan(4);
-
-###############################################################################
-
-like(http_get('/promise'), qr/{"token": "b"}/, "Promise");
-like(http_get('/promise_throw'), qr/{"token": "x"}/, "Promise throw and catch");
-like(http_get('/timeout'), qr/{"token": "R"}/, "Promise with timeout");
-like(http_get('/promise_pure'), qr/200 OK/, "events handling");
-
-###############################################################################
deleted file mode 100644
--- a/js_request_body.t
+++ /dev/null
@@ -1,110 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, r.requestText method.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /body {
-            js_content test.body;
-        }
-
-        location /in_file {
-            client_body_in_file_only on;
-            js_content test.body;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function body(r) {
-        try {
-            var body = r.requestText;
-            r.return(200, body);
-
-        } catch (e) {
-            r.return(500, e.message);
-        }
-    }
-
-    export default {body};
-
-EOF
-
-$t->try_run('no njs request body')->plan(3);
-
-###############################################################################
-
-like(http_post('/body'), qr/REQ-BODY/, 'request body');
-like(http_post('/in_file'), qr/request body is in a file/,
-	'request body in file');
-like(http_post_big('/body'), qr/200.*^(1234567890){1024}$/ms,
-		'request body big');
-
-###############################################################################
-
-sub http_post {
-	my ($url, %extra) = @_;
-
-	my $p = "POST $url HTTP/1.0" . CRLF .
-		"Host: localhost" . CRLF .
-		"Content-Length: 8" . CRLF .
-		CRLF .
-		"REQ-BODY";
-
-	return http($p, %extra);
-}
-
-sub http_post_big {
-	my ($url, %extra) = @_;
-
-	my $p = "POST $url HTTP/1.0" . CRLF .
-		"Host: localhost" . CRLF .
-		"Content-Length: 10240" . CRLF .
-		CRLF .
-		("1234567890" x 1024);
-
-	return http($p, %extra);
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_return.t
+++ /dev/null
@@ -1,73 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Sergey Kandaurov
-# (C) Nginx, Inc.
-
-# Tests for http njs module, return method.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use Config;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location / {
-            js_content test.returnf;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function returnf(r) {
-        r.return(Number(r.args.c), r.args.t);
-    }
-
-    export default {returnf};
-
-EOF
-
-$t->try_run('no njs return')->plan(5);
-
-###############################################################################
-
-like(http_get('/?c=200'), qr/200 OK.*\x0d\x0a?\x0d\x0a?$/s, 'return code');
-like(http_get('/?c=200&t=SEE-THIS'), qr/200 OK.*^SEE-THIS$/ms, 'return text');
-like(http_get('/?c=301&t=path'), qr/ 301 .*Location: path/s, 'return redirect');
-like(http_get('/?c=404'), qr/404 Not.*html/s, 'return error page');
-like(http_get('/?c=inv'), qr/ 500 /, 'return invalid');
-
-###############################################################################
deleted file mode 100644
--- a/js_subrequests.t
+++ /dev/null
@@ -1,636 +0,0 @@
-#!/usr/bin/perl
-#
-# (C) Dmitry Volyntsev.
-# (C) Nginx, Inc.
-
-# Tests for subrequests in http njs module.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-use Socket qw/ CRLF /;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-eval { require JSON::PP; };
-plan(skip_all => "JSON::PP not installed") if $@;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite proxy cache/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    proxy_cache_path   %%TESTDIR%%/cache1
-                       keys_zone=ON:1m      use_temp_path=on;
-
-    js_import test.js;
-
-    js_set $async_var       test.async_var;
-    js_set $subrequest_var  test.subrequest_var;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /sr {
-            js_content test.sr;
-        }
-
-        location /sr_pr {
-            js_content test.sr_pr;
-        }
-
-        location /sr_args {
-            js_content test.sr_args;
-        }
-
-        location /sr_options_args {
-            js_content test.sr_options_args;
-        }
-
-        location /sr_options_args_pr {
-            js_content test.sr_options_args_pr;
-        }
-
-        location /sr_options_method {
-            js_content test.sr_options_method;
-        }
-
-        location /sr_options_method_pr {
-            js_content test.sr_options_method_pr;
-        }
-
-        location /sr_options_body {
-            js_content test.sr_options_body;
-        }
-
-        location /sr_options_method_head {
-            js_content test.sr_options_method_head;
-        }
-
-        location /sr_body {
-            js_content test.sr_body;
-        }
-
-        location /sr_body_pr {
-            js_content test.sr_body_pr;
-        }
-
-        location /sr_body_special {
-            js_content test.sr_body_special;
-        }
-
-        location /sr_in_variable_handler {
-            set $_ $async_var;
-            js_content test.sr_in_variable_handler;
-        }
-
-        location /sr_detached_in_variable_handler {
-            return 200 $subrequest_var;
-        }
-
-        location /sr_async_var {
-            set $_ $async_var;
-            error_page 404 /return;
-            return 404;
-        }
-
-        location /sr_error_page {
-            js_content test.sr_error_page;
-        }
-
-        location /sr_js_in_subrequest {
-            js_content test.sr_js_in_subrequest;
-        }
-
-        location /sr_js_in_subrequest_pr {
-            js_content test.sr_js_in_subrequest_pr;
-        }
-
-        location /sr_file {
-            js_content test.sr_file;
-        }
-
-        location /sr_cache {
-            js_content test.sr_cache;
-        }
-
-
-        location /sr_unavail {
-            js_content test.sr_unavail;
-        }
-
-        location /sr_unavail_pr {
-            js_content test.sr_unavail_pr;
-        }
-
-        location /sr_broken {
-            js_content test.sr_broken;
-        }
-
-        location /sr_too_large {
-            js_content test.sr_too_large;
-        }
-
-        location /sr_out_of_order {
-            js_content test.sr_out_of_order;
-        }
-
-        location /sr_except_not_a_func {
-            js_content test.sr_except_not_a_func;
-        }
-
-        location /sr_except_failed_to_convert_options_arg {
-            js_content test.sr_except_failed_to_convert_options_arg;
-        }
-
-        location /sr_except_invalid_options_header_only {
-            js_content test.sr_except_invalid_options_header_only;
-        }
-
-        location /sr_in_sr_callback {
-            js_content test.sr_in_sr_callback;
-        }
-
-        location /sr_uri_except {
-            js_content test.sr_uri_except;
-        }
-
-
-        location /file/ {
-            alias %%TESTDIR%%/;
-        }
-
-        location /p/ {
-            proxy_cache $arg_c;
-            proxy_pass http://127.0.0.1:8081/;
-        }
-
-        location /daemon/ {
-            proxy_pass http://127.0.0.1:8082/;
-        }
-
-        location /too_large/ {
-            subrequest_output_buffer_size 3;
-            proxy_pass http://127.0.0.1:8081/;
-        }
-
-        location /sr_in_sr {
-            js_content test.sr_in_sr;
-        }
-
-        location /unavail {
-            proxy_pass http://127.0.0.1:8084/;
-        }
-
-        location /sr_parent {
-             js_content test.sr_parent;
-        }
-
-        location /js_sub {
-            js_content test.js_sub;
-        }
-
-        location /return {
-            return 200 '["$request_method"]';
-        }
-
-        location /error_page_404 {
-            return 404;
-
-            error_page 404 /404.html;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081;
-        server_name  localhost;
-
-        location /sub1 {
-            add_header H $arg_h;
-            return 206 '{"a": {"b": 1}}';
-        }
-
-        location /sub2 {
-            return 404 '{"e": "msg"}';
-        }
-
-        location /method {
-            return 200 '["$request_method"]';
-        }
-
-        location /body {
-            js_content test.body;
-        }
-
-        location /detached {
-            js_content test.detached;
-        }
-
-        location /delayed {
-            js_content test.delayed;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8084;
-        server_name  localhost;
-
-        return 444;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function sr(r) {
-        subrequest_fn(r, ['/p/sub2'], ['uri', 'status'])
-    }
-
-    function sr_pr(r) {
-        r.subrequest('/p/sub1', 'h=xxx')
-        .then(reply => r.return(200, JSON.stringify({h:reply.headersOut.h})))
-    }
-
-    function sr_args(r) {
-        r.subrequest('/p/sub1', 'h=xxx', reply => {
-            r.return(200, JSON.stringify({h:reply.headersOut.h}));
-        });
-    }
-
-    function sr_options_args(r) {
-        r.subrequest('/p/sub1', {args:'h=xxx'}, reply => {
-            r.return(200, JSON.stringify({h:reply.headersOut.h}));
-        });
-    }
-
-    function sr_options_args_pr(r) {
-        r.subrequest('/p/sub1', {args:'h=xxx'})
-        .then(reply => r.return(200, JSON.stringify({h:reply.headersOut.h})))
-    }
-
-    function sr_options_method(r) {
-        r.subrequest('/p/method', {method:r.args.m}, body_fwd_cb);
-    }
-
-    function sr_options_method_pr(r) {
-        r.subrequest('/p/method', {method:r.args.m})
-        .then(body_fwd_cb);
-    }
-
-    function sr_options_body(r) {
-        r.subrequest('/p/body', {method:'POST', body:'["REQ-BODY"]'},
-                     body_fwd_cb);
-    }
-
-    function sr_options_method_head(r) {
-        r.subrequest('/p/method', {method:'HEAD'}, reply => {
-            r.return(200, JSON.stringify({c:reply.status}));
-        });
-    }
-
-    function sr_body(r) {
-        r.subrequest('/p/sub1', body_fwd_cb);
-    }
-
-    function sr_body_pr(r) {
-        r.subrequest('/p/sub1')
-        .then(body_fwd_cb);
-    }
-
-    function sr_body_special(r) {
-        r.subrequest('/p/sub2', body_fwd_cb);
-    }
-
-    function body(r) {
-        r.return(200, r.variables.request_body);
-    }
-
-    function delayed(r) {
-        setTimeout(r => r.return(200), 100, r);
-    }
-
-    function detached(r) {
-        var method = r.variables.request_method;
-        r.log(`DETACHED: \${method} args: \${r.variables.args}`);
-
-        r.return(200);
-    }
-
-    function sr_in_variable_handler(r) {
-    }
-
-    function async_var(r) {
-        r.subrequest('/p/delayed', reply => {
-            r.return(200, JSON.stringify(["CB-VAR"]));
-        });
-
-        return "";
-    }
-
-    function sr_error_page(r) {
-         r.subrequest('/error_page_404')
-         .then(reply => {r.return(200, `reply.status:\${reply.status}`)});
-    }
-
-    function subrequest_var(r) {
-        r.subrequest('/p/detached',  {detached:true});
-        r.subrequest('/p/detached',  {detached:true, args:'a=yyy',
-                                      method:'POST'});
-
-        return "subrequest_var";
-    }
-
-    function sr_file(r) {
-        r.subrequest('/file/t', body_fwd_cb);
-    }
-
-    function sr_cache(r) {
-        r.subrequest('/p/t', body_fwd_cb);
-    }
-
-    function sr_unavail(req) {
-        subrequest_fn(req, ['/unavail'], ['uri', 'status']);
-    }
-
-    function sr_unavail_pr(req) {
-        subrequest_fn_pr(req, ['/unavail'], ['uri', 'status']);
-    }
-
-    function sr_broken(r) {
-        r.subrequest('/daemon/unfinished', reply => {
-            r.return(200, JSON.stringify({code:reply.status}));
-        });
-    }
-
-    function sr_too_large(r) {
-        r.subrequest('/too_large/t', body_fwd_cb);
-    }
-
-    function sr_in_sr(r) {
-        r.subrequest('/sr', body_fwd_cb);
-    }
-
-    function sr_js_in_subrequest(r) {
-        r.subrequest('/js_sub', body_fwd_cb);
-    }
-
-    function sr_js_in_subrequest_pr(r) {
-        r.subrequest('/js_sub')
-        .then(body_fwd_cb);
-    }
-
-    function sr_in_sr_callback(r) {
-        r.subrequest('/return', function (reply) {
-                try {
-                    reply.subrequest('/return');
-
-                } catch (err) {
-                    r.return(200, JSON.stringify({e:err.message}));
-                    return;
-                }
-
-                r.return(200);
-            });
-    }
-
-    function sr_parent(r) {
-        try {
-            var parent = r.parent;
-
-        } catch (err) {
-            r.return(200, JSON.stringify({e:err.message}));
-            return;
-        }
-
-        r.return(200);
-    }
-
-    function sr_out_of_order(r) {
-        subrequest_fn(r, ['/p/delayed', '/p/sub1', '/unknown'],
-                      ['uri', 'status']);
-    }
-
-    function collect(replies, props, total, reply) {
-        reply.log(`subrequest handler: \${reply.uri} status: \${reply.status}`)
-
-        var rep = {};
-        props.forEach(p => {rep[p] = reply[p]});
-
-        replies.push(rep);
-
-        if (replies.length == total) {
-            reply.parent.return(200, JSON.stringify(replies));
-        }
-    }
-
-    function subrequest_fn(r, subs, props) {
-        var replies = [];
-
-        subs.forEach(sr =>
-                     r.subrequest(sr, collect.bind(null, replies,
-                                                   props, subs.length)));
-    }
-
-    function subrequest_fn_pr(r, subs, props) {
-        var replies = [];
-
-        subs.forEach(sr => r.subrequest(sr)
-            .then(collect.bind(null, replies, props, subs.length)));
-    }
-
-    function sr_except_not_a_func(r) {
-        r.subrequest('/sub1', 'a=1', 'b');
-    }
-
-    let Failed = {get toConvert() { return {toString(){return {};}}}};
-
-    function sr_except_failed_to_convert_options_arg(r) {
-        r.subrequest('/sub1', {args:Failed.toConvert}, ()=>{});
-    }
-
-    function sr_uri_except(r) {
-        r.subrequest(Failed.toConvert, 'a=1', 'b');
-    }
-
-    function body_fwd_cb(r) {
-        r.parent.return(200, JSON.stringify(JSON.parse(r.responseText)));
-    }
-
-    function js_sub(r) {
-        r.return(200, '["JS-SUB"]');
-    }
-
-    export default {njs:test_njs, sr, sr_pr, sr_args, sr_options_args,
-                    sr_options_args_pr, sr_options_method, sr_options_method_pr,
-                    sr_options_method_head, sr_options_body, sr_body,
-                    sr_body_pr, sr_body_special, body, delayed, detached,
-                    sr_in_variable_handler, async_var, sr_error_page,
-                    subrequest_var, sr_file, sr_cache, sr_unavail, sr_parent,
-                    sr_unavail_pr, sr_broken, sr_too_large, sr_in_sr,
-                    sr_js_in_subrequest, sr_js_in_subrequest_pr, js_sub,
-                    sr_in_sr_callback, sr_out_of_order, sr_except_not_a_func,
-                    sr_uri_except, sr_except_failed_to_convert_options_arg};
-
-EOF
-
-$t->write_file('t', '["SEE-THIS"]');
-
-$t->try_run('no njs available')->plan(32);
-$t->run_daemon(\&http_daemon);
-
-###############################################################################
-
-is(get_json('/sr'), '[{"status":404,"uri":"/p/sub2"}]', 'sr');
-is(get_json('/sr_args'), '{"h":"xxx"}', 'sr_args');
-is(get_json('/sr_options_args'), '{"h":"xxx"}', 'sr_options_args');
-is(get_json('/sr_options_method?m=POST'), '["POST"]', 'sr method POST');
-is(get_json('/sr_options_method?m=PURGE'), '["PURGE"]', 'sr method PURGE');
-is(get_json('/sr_options_body'), '["REQ-BODY"]', 'sr_options_body');
-is(get_json('/sr_options_method_head'), '{"c":200}', 'sr_options_method_head');
-is(get_json('/sr_body'), '{"a":{"b":1}}', 'sr_body');
-is(get_json('/sr_body_special'), '{"e":"msg"}', 'sr_body_special');
-is(get_json('/sr_in_variable_handler'), '["CB-VAR"]', 'sr_in_variable_handler');
-is(get_json('/sr_file'), '["SEE-THIS"]', 'sr_file');
-is(get_json('/sr_cache?c=1'), '["SEE-THIS"]', 'sr_cache');
-is(get_json('/sr_cache?c=1'), '["SEE-THIS"]', 'sr_cached');
-is(get_json('/sr_js_in_subrequest'), '["JS-SUB"]', 'sr_js_in_subrequest');
-is(get_json('/sr_unavail'), '[{"status":502,"uri":"/unavail"}]',
-	'sr_unavail');
-is(get_json('/sr_out_of_order'),
-	'[{"status":404,"uri":"/unknown"},' .
-	'{"status":206,"uri":"/p/sub1"},' .
-	'{"status":200,"uri":"/p/delayed"}]',
-	'sr_multi');
-
-is(get_json('/sr_pr'), '{"h":"xxx"}', 'sr_promise');
-is(get_json('/sr_options_args_pr'), '{"h":"xxx"}', 'sr_options_args_pr');
-is(get_json('/sr_options_method_pr?m=PUT'), '["PUT"]', 'sr method PUT');
-is(get_json('/sr_body_pr'), '{"a":{"b":1}}', 'sr_body_pr');
-is(get_json('/sr_js_in_subrequest_pr'), '["JS-SUB"]', 'sr_js_in_subrequest_pr');
-is(get_json('/sr_unavail_pr'), '[{"status":502,"uri":"/unavail"}]',
-	'sr_unavail_pr');
-
-like(http_get('/sr_detached_in_variable_handler'), qr/subrequest_var/,
-     'sr_detached_in_variable_handler');
-
-like(http_get('/sr_error_page'), qr/reply\.status:404/,
-     'sr_error_page');
-
-http_get('/sr_broken');
-http_get('/sr_in_sr');
-http_get('/sr_in_variable_handler');
-http_get('/sr_async_var');
-http_get('/sr_too_large');
-http_get('/sr_except_not_a_func');
-http_get('/sr_except_failed_to_convert_options_arg');
-http_get('/sr_uri_except');
-
-is(get_json('/sr_in_sr_callback'),
-	'{"e":"subrequest can only be created for the primary request"}',
-	'subrequest for non-primary request');
-
-$t->stop();
-
-ok(index($t->read_file('error.log'), 'callback is not a function') > 0,
-	'subrequest cb exception');
-ok(index($t->read_file('error.log'), 'failed to convert uri arg') > 0,
-	'subrequest uri exception');
-ok(index($t->read_file('error.log'), 'failed to convert options.args') > 0,
-	'subrequest invalid args exception');
-ok(index($t->read_file('error.log'), 'too big subrequest response') > 0,
-	'subrequest too large body');
-ok(index($t->read_file('error.log'), 'subrequest creation failed') > 0,
-	'subrequest creation failed');
-ok(index($t->read_file('error.log'),
-		'js subrequest: failed to get the parent context') > 0,
-	'zero parent ctx');
-
-ok(index($t->read_file('error.log'), 'DETACHED') > 0,
-	'detached subrequest');
-
-###############################################################################
-
-sub recode {
-	my $json;
-	eval { $json = JSON::PP::decode_json(shift) };
-
-	if ($@) {
-		return "<failed to parse JSON>";
-	}
-
-	JSON::PP->new()->canonical()->encode($json);
-}
-
-sub get_json {
-	http_get(shift) =~ /\x0d\x0a?\x0d\x0a?(.*)/ms;
-	recode($1);
-}
-
-###############################################################################
-
-sub http_daemon {
-	my $server = IO::Socket::INET->new(
-		Proto => 'tcp',
-		LocalAddr => '127.0.0.1:' . port(8082),
-		Listen => 5,
-		Reuse => 1
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	while (my $client = $server->accept()) {
-		$client->autoflush(1);
-
-		my $headers = '';
-		my $uri = '';
-
-		while (<$client>) {
-			$headers .= $_;
-			last if (/^\x0d?\x0a?$/);
-		}
-
-		$uri = $1 if $headers =~ /^\S+\s+([^ ]+)\s+HTTP/i;
-
-		if ($uri eq '/unfinished') {
-			print $client
-				"HTTP/1.1 200 OK" . CRLF .
-				"Transfer-Encoding: chunked" . CRLF .
-				"Content-Length: 100" . CRLF .
-				CRLF .
-				"unfinished" . CRLF;
-			close($client);
-		}
-	}
-}
-
-###############################################################################
deleted file mode 100644
--- a/js_var.t
+++ /dev/null
@@ -1,90 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, js_var directive.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    js_var $foo;
-    js_var $bar a:$arg_a;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /test {
-            js_content test.test;
-        }
-
-        location /sub {
-            return 200 DONE;
-        }
-
-        location /dest {
-            return 200 $bar;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test(r) {
-        if (r.args.sub) {
-            r.subrequest('/sub')
-            .then(reply => {
-                r.variables.bar = reply.responseText;
-                r.internalRedirect('/dest');
-            });
-
-            return;
-        }
-
-        r.return(200, `V:\${r.variables[r.args.var]}`);
-    }
-
-    export default {test};
-
-EOF
-
-$t->try_run('no njs js_var')->plan(3);
-
-###############################################################################
-
-like(http_get('/test?var=bar&a=qq'), qr/200 OK.*V:a:qq$/s, 'default value');
-like(http_get('/test?var=foo'), qr/200 OK.*V:$/s, 'default empty value');
-like(http_get('/test?sub=1&var=bar&a=qq'), qr/200 OK.*DONE$/s, 'value set');
-
-###############################################################################
deleted file mode 100644
--- a/js_var2.t
+++ /dev/null
@@ -1,90 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, js_var directive in server | location contexts.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        js_var $foo;
-
-        location /test {
-            js_content test.test;
-        }
-
-        location /sub {
-            return 200 DONE;
-        }
-
-        location /dest {
-            js_var $bar a:$arg_a;
-            return 200 $bar;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test(r) {
-        if (r.args.sub) {
-            r.subrequest('/sub')
-            .then(reply => {
-                r.variables.bar = reply.responseText;
-                r.internalRedirect('/dest');
-            });
-
-            return;
-        }
-
-        r.return(200, `V:\${r.variables[r.args.var]}`);
-    }
-
-    export default {test};
-
-EOF
-
-$t->try_run('no njs js_var')->plan(3);
-
-###############################################################################
-
-like(http_get('/test?var=bar&a=qq'), qr/200 OK.*V:a:qq$/s, 'default value');
-like(http_get('/test?var=foo'), qr/200 OK.*V:$/s, 'default empty value');
-like(http_get('/test?sub=1&var=bar&a=qq'), qr/200 OK.*DONE$/s, 'value set');
-
-###############################################################################
deleted file mode 100644
--- a/js_variables.t
+++ /dev/null
@@ -1,95 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for http njs module, setting nginx variables.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_set $test_var   test.variable;
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        set $foo       test.foo_orig;
-
-        location /var_set {
-            return 200 $test_var$foo;
-        }
-
-        location /content_set {
-            js_content test.content_set;
-        }
-
-        location /not_found_set {
-            js_content test.not_found_set;
-        }
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function variable(r) {
-        r.variables.foo = r.variables.arg_a;
-        return 'test_var';
-    }
-
-    function content_set(r) {
-        r.variables.foo = r.variables.arg_a;
-        r.return(200, r.variables.foo);
-    }
-
-    function not_found_set(r) {
-        try {
-            r.variables.unknown = 1;
-        } catch (e) {
-            r.return(500, e);
-        }
-    }
-
-    export default {variable, content_set, not_found_set};
-
-EOF
-
-$t->try_run('no njs')->plan(3);
-
-###############################################################################
-
-like(http_get('/var_set?a=bar'), qr/test_varbar/, 'var set');
-like(http_get('/content_set?a=bar'), qr/bar/, 'content set');
-like(http_get('/not_found_set'), qr/variable not found/, 'not found exception');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js.t
+++ /dev/null
@@ -1,502 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Andrey Zelenkov
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ dgram stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http proxy rewrite stream stream_return udp/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8079;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /p/ {
-            proxy_pass http://127.0.0.1:8095/;
-
-        }
-
-        location /return {
-            return 200 $http_foo;
-        }
-    }
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_set $js_addr      test.addr;
-    js_set $js_var       test.variable;
-    js_set $js_log       test.log;
-    js_set $js_unk       test.unk;
-    js_set $js_req_line  test.req_line;
-    js_set $js_sess_unk  test.sess_unk;
-    js_set $js_async     test.asyncf;
-
-    js_import test.js;
-
-    log_format status $server_port:$status;
-
-    server {
-        listen  127.0.0.1:8080;
-        return  $js_addr;
-    }
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $js_log;
-    }
-
-    server {
-        listen  127.0.0.1:8082;
-        return  $js_var;
-    }
-
-    server {
-        listen  127.0.0.1:8083;
-        return  $js_unk;
-    }
-
-    server {
-        listen  127.0.0.1:8084;
-        return  $js_sess_unk;
-    }
-
-    server {
-        listen  127.0.0.1:%%PORT_8985_UDP%% udp;
-        return  $js_addr;
-    }
-
-    server {
-        listen      127.0.0.1:8086;
-        js_access   test.access_step;
-        js_preread  test.preread_step;
-        js_filter   test.filter_step;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8087;
-        js_access   test.access_undecided;
-        return      OK;
-        access_log  %%TESTDIR%%/status.log status;
-    }
-
-    server {
-        listen      127.0.0.1:8088;
-        js_access   test.access_allow;
-        return      OK;
-        access_log  %%TESTDIR%%/status.log status;
-    }
-
-    server {
-        listen      127.0.0.1:8089;
-        js_access   test.access_deny;
-        return      OK;
-        access_log  %%TESTDIR%%/status.log status;
-    }
-
-    server {
-        listen      127.0.0.1:8091;
-        js_preread  test.preread_async;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8092;
-        js_preread  test.preread_data;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8093;
-        js_preread  test.preread_req_line;
-        return      $js_req_line;
-    }
-
-    server {
-        listen      127.0.0.1:8094;
-        js_filter   test.filter_empty;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8095;
-        js_filter   test.filter_header_inject;
-        proxy_pass  127.0.0.1:8079;
-    }
-
-    server {
-        listen      127.0.0.1:8096;
-        js_filter   test.filter_search;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8097;
-        js_access   test.access_except;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8098;
-        js_preread  test.preread_except;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8099;
-        js_filter   test.filter_except;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8100;
-        return      $js_async;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function addr(s) {
-        return 'addr=' + s.remoteAddress;
-    }
-
-    function variable(s) {
-        return 'variable=' + s.variables.remote_addr;
-    }
-
-    function sess_unk(s) {
-        return 'sess_unk=' + s.unk;
-    }
-
-    function log(s) {
-        s.log("SEE-THIS");
-    }
-
-    var res = '';
-
-    function access_step(s) {
-        res += '1';
-
-        setTimeout(function() {
-            if (s.remoteAddress.match('127.0.0.1')) {
-                s.allow();
-            }
-        }, 1);
-    }
-
-    function preread_step(s) {
-        s.on('upload', function (data) {
-            res += '2';
-            if (res.length >= 3) {
-                s.done();
-            }
-        });
-    }
-
-    function filter_step(s) {
-        s.on('upload', function(data, flags) {
-            s.send(data);
-            res += '3';
-        });
-
-        s.on('download', function(data, flags) {
-
-            if (!flags.last) {
-                res += '4';
-                s.send(data);
-
-            } else {
-                res += '5';
-                s.send(res, {last:1});
-                s.off('download');
-            }
-        });
-    }
-
-    function access_undecided(s) {
-        s.decline();
-    }
-
-    function access_allow(s) {
-        if (s.remoteAddress.match('127.0.0.1')) {
-            s.done();
-            return;
-        }
-
-        s.deny();
-    }
-
-    function access_deny(s) {
-        if (s.remoteAddress.match('127.0.0.1')) {
-            s.deny();
-            return;
-        }
-
-        s.allow();
-    }
-
-
-    function preread_async(s) {
-        setTimeout(function() {
-            s.done();
-        }, 1);
-    }
-
-    function preread_data(s) {
-        s.on('upload', function (data, flags) {
-            if (data.indexOf('z') != -1) {
-                s.done();
-            }
-        });
-    }
-
-    var line = '';
-
-    function preread_req_line(s) {
-        s.on('upload', function (data, flags) {
-            var n = data.indexOf('\\n');
-            if (n != -1) {
-                line = data.substr(0, n);
-                s.done();
-            }
-        });
-    }
-
-    function req_line(s) {
-        return line;
-    }
-
-    function filter_empty(s) {
-    }
-
-    function filter_header_inject(s) {
-        var req = '';
-
-        s.on('upload', function(data, flags) {
-            req += data;
-
-            var n = req.search('\\n');
-            if (n != -1) {
-                var rest = req.substr(n + 1);
-                req = req.substr(0, n + 1);
-
-                s.send(req + 'Foo: foo' + '\\r\\n' + rest, flags);
-
-                s.off('upload');
-            }
-        });
-    }
-
-    function filter_search(s) {
-        s.on('download', function(data, flags) {
-            var n = data.search('y');
-            if (n != -1) {
-                s.send('z');
-            }
-        });
-
-        s.on('upload', function(data, flags) {
-            var n = data.search('x');
-            if (n != -1) {
-                s.send('y');
-            }
-        });
-    }
-
-    function access_except(s) {
-        function done() {return s.a.a};
-
-        setTimeout(done, 1);
-        setTimeout(done, 2);
-    }
-
-    function preread_except(s) {
-        var fs = require('fs');
-        fs.readFileSync();
-    }
-
-    function filter_except(s) {
-        s.on('unknown', function() {});
-    }
-
-    function pr(x) {
-        return new Promise(resolve => {resolve(x)}).then(v => v).then(v => v);
-    }
-
-    async function asyncf(s) {
-        const a1 = await pr(10);
-        const a2 = await pr(20);
-
-        s.setReturnValue(`retval: \${a1 + a2}`);
-    }
-
-    export default {njs:test_njs, addr, variable, sess_unk, log, access_step,
-                    preread_step, filter_step, access_undecided, access_allow,
-                    access_deny, preread_async, preread_data, preread_req_line,
-                    req_line, filter_empty, filter_header_inject, filter_search,
-                    access_except, preread_except, filter_except, asyncf};
-
-EOF
-
-$t->run_daemon(\&stream_daemon, port(8090));
-$t->try_run('no stream njs available')->plan(23);
-$t->waitforsocket('127.0.0.1:' . port(8090));
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8080))->read(), 'addr=127.0.0.1',
-	's.remoteAddress');
-is(dgram('127.0.0.1:' . port(8985))->io('.'), 'addr=127.0.0.1',
-	's.remoteAddress udp');
-is(stream('127.0.0.1:' . port(8081))->read(), 'undefined', 's.log');
-is(stream('127.0.0.1:' . port(8082))->read(), 'variable=127.0.0.1',
-	's.variables');
-is(stream('127.0.0.1:' . port(8083))->read(), '', 'stream js unknown function');
-is(stream('127.0.0.1:' . port(8084))->read(), 'sess_unk=undefined', 's.unk');
-
-is(stream('127.0.0.1:' . port(8086))->io('0'), '0122345',
-	'async handlers order');
-is(stream('127.0.0.1:' . port(8087))->io('#'), 'OK', 'access_undecided');
-is(stream('127.0.0.1:' . port(8088))->io('#'), 'OK', 'access_allow');
-is(stream('127.0.0.1:' . port(8089))->io('#'), '', 'access_deny');
-
-is(stream('127.0.0.1:' . port(8091))->io('#'), '#', 'preread_async');
-is(stream('127.0.0.1:' . port(8092))->io('#z'), '#z', 'preread_async_data');
-is(stream('127.0.0.1:' . port(8093))->io("xy\na"), 'xy', 'preread_req_line');
-
-is(stream('127.0.0.1:' . port(8094))->io('x'), 'x', 'filter_empty');
-like(get('/p/return'), qr/foo/, 'filter_injected_header');
-is(stream('127.0.0.1:' . port(8096))->io('x'), 'z', 'filter_search');
-
-stream('127.0.0.1:' . port(8097))->io('x');
-stream('127.0.0.1:' . port(8098))->io('x');
-stream('127.0.0.1:' . port(8099))->io('x');
-
-TODO: {
-local $TODO = 'not yet' unless has_version('0.7.0');
-
-is(stream('127.0.0.1:' . port(8100))->read(), 'retval: 30', 'asyncf');
-
-}
-
-$t->stop();
-
-ok(index($t->read_file('error.log'), 'SEE-THIS') > 0, 'stream js log');
-ok(index($t->read_file('error.log'), 'at fs.readFileSync') > 0,
-	'stream js_preread backtrace');
-ok(index($t->read_file('error.log'), 'at filter_except') > 0,
-	'stream js_filter backtrace');
-
-my @p = (port(8087), port(8088), port(8089));
-like($t->read_file('status.log'), qr/$p[0]:200/, 'status undecided');
-like($t->read_file('status.log'), qr/$p[1]:200/, 'status allow');
-like($t->read_file('status.log'), qr/$p[2]:403/, 'status deny');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub stream_daemon {
-	my $server = IO::Socket::INET->new(
-		Proto => 'tcp',
-		LocalAddr => '127.0.0.1:' . port(8090),
-		Listen => 5,
-		Reuse => 1
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	while (my $client = $server->accept()) {
-		$client->autoflush(1);
-
-		log2c("(new connection $client)");
-
-		$client->sysread(my $buffer, 65536) or next;
-
-		log2i("$client $buffer");
-
-		log2o("$client $buffer");
-
-		$client->syswrite($buffer);
-
-		close $client;
-	}
-}
-
-sub log2i { Test::Nginx::log_core('|| <<', @_); }
-sub log2o { Test::Nginx::log_core('|| >>', @_); }
-sub log2c { Test::Nginx::log_core('||', @_); }
-
-sub get {
-	my ($url, %extra) = @_;
-
-	my $s = IO::Socket::INET->new(
-		Proto => 'tcp',
-		PeerAddr => '127.0.0.1:' . port(8079)
-	) or die "Can't connect to nginx: $!\n";
-
-	return http_get($url, socket => $s);
-}
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_buffer.t
+++ /dev/null
@@ -1,177 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, buffer properties.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http proxy rewrite stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /p/ {
-            proxy_pass http://127.0.0.1:8085/;
-        }
-
-        location /return {
-            return 200 'RETURN:$http_foo';
-        }
-    }
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    js_set $type        test.type;
-    js_set $binary_var  test.binary_var;
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $type;
-    }
-
-    server {
-        listen  127.0.0.1:8082;
-        return  $binary_var;
-    }
-
-    server {
-        listen      127.0.0.1:8083;
-        js_preread  test.cb_mismatch;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8084;
-        js_preread  test.cb_mismatch2;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8085;
-        js_filter   test.header_inject;
-        proxy_pass  127.0.0.1:8080;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function type(s) {
-		var v = s.rawVariables.remote_addr;
-		var type = Buffer.isBuffer(v) ? 'buffer' : (typeof v);
-		return type;
-    }
-
-    function binary_var(s) {
-        var test = s.rawVariables
-                   .binary_remote_addr.equals(Buffer.from([127,0,0,1]));
-        return test;
-    }
-
-    function cb_mismatch(s) {
-        try {
-            s.on('upload', () => {});
-            s.on('downstream', () => {});
-        } catch (e) {
-            throw new Error(`cb_mismatch:\${e.message}`)
-        }
-    }
-
-    function cb_mismatch2(s) {
-        try {
-            s.on('upstream', () => {});
-            s.on('download', () => {});
-        } catch (e) {
-            throw new Error(`cb_mismatch2:\${e.message}`)
-        }
-    }
-
-    function header_inject(s) {
-        var req = Buffer.from([]);
-
-        s.on('upstream', function(data, flags) {
-            req = Buffer.concat([req, data]);
-
-            var n = req.indexOf('\\n');
-            if (n != -1) {
-                var rest = req.slice(n + 1);
-                req = req.slice(0, n + 1);
-
-                s.send(req, flags);
-                s.send('Foo: foo\\r\\n', flags);
-                s.send(rest, flags);
-
-                s.off('upstream');
-            }
-        });
-    }
-
-    export default {njs: test_njs, type, binary_var, cb_mismatch, cb_mismatch2,
-                    header_inject};
-
-EOF
-
-$t->try_run('no njs ngx')->plan(5);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->read(), 'buffer', 'var type');
-is(stream('127.0.0.1:' . port(8082))->read(), 'true', 'binary var');
-
-stream('127.0.0.1:' . port(8083))->io('x');
-stream('127.0.0.1:' . port(8084))->io('x');
-
-like(http_get('/p/return'), qr/RETURN:foo/, 'injected header');
-
-$t->stop();
-
-ok(index($t->read_file('error.log'), 'cb_mismatch:mixing string and buffer')
-   > 0, 'cb mismatch');
-ok(index($t->read_file('error.log'), 'cb_mismatch2:mixing string and buffer')
-   > 0, 'cb mismatch');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_exit.t
+++ /dev/null
@@ -1,152 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, exit hook.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http stream/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-    }
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    server {
-        listen      127.0.0.1:8081;
-        js_access   test.access;
-        js_filter   test.filter;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8082;
-        js_access   test.access;
-        proxy_pass  127.0.0.1:1;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function access(s) {
-        njs.on('exit', () => {
-            var v = s.variables;
-            var c = `\${v.bytes_received}/\${v.bytes_sent}`;
-            var u = `\${v.upstream_bytes_received}/\${v.upstream_bytes_sent}`;
-            s.error(`s:\${s.status} C: \${c} U: \${u}`);
-        });
-
-        s.allow();
-    }
-
-    function filter(s) {
-        s.on('upload', (data, flags) => {
-            s.send(`@\${data}`, flags);
-        });
-
-        s.on('download', (data, flags) => {
-            s.send(data.slice(2), flags);
-        });
-    }
-
-    export default {njs: test_njs, access, filter};
-EOF
-
-$t->try_run('no stream njs available')->plan(2);
-
-$t->run_daemon(\&stream_daemon, port(8090));
-$t->waitforsocket('127.0.0.1:' . port(8090));
-
-###############################################################################
-
-stream('127.0.0.1:' . port(8081))->io('###');
-stream('127.0.0.1:' . port(8082))->io('###');
-
-$t->stop();
-
-ok(index($t->read_file('error.log'), 's:200 C: 3/6 U: 8/4') > 0, 'normal');
-ok(index($t->read_file('error.log'), 's:502 C: 0/0 U: 0/0') > 0, 'failed conn');
-
-###############################################################################
-
-sub stream_daemon {
-	my $server = IO::Socket::INET->new(
-		Proto => 'tcp',
-		LocalAddr => '127.0.0.1:' . port(8090),
-		Listen => 5,
-		Reuse => 1
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	while (my $client = $server->accept()) {
-		$client->autoflush(1);
-
-		log2c("(new connection $client)");
-
-		$client->sysread(my $buffer, 65536) or next;
-
-		log2i("$client $buffer");
-
-		$buffer = $buffer . $buffer;
-
-		log2o("$client $buffer");
-
-		$client->syswrite($buffer);
-
-		close $client;
-	}
-}
-
-sub log2i { Test::Nginx::log_core('|| <<', @_); }
-sub log2o { Test::Nginx::log_core('|| >>', @_); }
-sub log2c { Test::Nginx::log_core('||', @_); }
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_fetch.t
+++ /dev/null
@@ -1,277 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, fetch method.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http stream/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /validate {
-            js_content test.validate;
-        }
-
-        location /success {
-            return 200;
-        }
-
-        location /fail {
-            return 403;
-        }
-    }
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    server {
-        listen      127.0.0.1:8081;
-        js_preread  test.preread_verify;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8082;
-        js_filter   test.filter_verify;
-        proxy_pass  127.0.0.1:8091;
-    }
-
-    server {
-        listen      127.0.0.1:8083;
-        js_access   test.access_ok;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8084;
-        js_access   test.access_nok;
-        proxy_pass  127.0.0.1:8090;
-    }
-}
-
-EOF
-
-my $p = port(8080);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function validate(r) {
-        r.return((r.requestText == 'QZ') ? 200 : 403);
-    }
-
-    function preread_verify(s) {
-        var collect = Buffer.from([]);
-
-        s.on('upstream', async function (data, flags) {
-            collect = Buffer.concat([collect, data]);
-
-            if (collect.length >= 4 && collect.readUInt16BE(0) == 0xabcd) {
-                s.off('upstream');
-
-                let reply = await ngx.fetch('http://127.0.0.1:$p/validate',
-                                            {body: collect.slice(2,4)});
-
-                (reply.status == 200) ? s.done(): s.deny();
-
-            } else if (collect.length) {
-                s.deny();
-            }
-        });
-    }
-
-    function filter_verify(s) {
-        var collect = Buffer.from([]);
-
-        s.on('upstream', async function (data, flags) {
-            collect = Buffer.concat([collect, data]);
-
-            if (collect.length >= 4 && collect.readUInt16BE(0) == 0xabcd) {
-                s.off('upstream');
-
-                let reply = await ngx.fetch('http://127.0.0.1:$p/validate',
-                                            {body: collect.slice(2,4)});
-
-                if (reply.status == 200) {
-                    s.send(collect.slice(4), flags);
-
-                } else {
-                    s.send("__CLOSE__", flags);
-                }
-            }
-        });
-    }
-
-    async function access_ok(s) {
-        let reply = await ngx.fetch('http://127.0.0.1:$p/success');
-
-        (reply.status == 200) ? s.allow(): s.deny();
-    }
-
-    async function access_nok(s) {
-        let reply = await ngx.fetch('http://127.0.0.1:$p/fail');
-
-        (reply.status == 200) ? s.allow(): s.deny();
-    }
-
-    export default {njs: test_njs, validate, preread_verify, filter_verify,
-                    access_ok, access_nok};
-EOF
-
-$t->try_run('no stream njs available')->plan(9);
-
-$t->run_daemon(\&stream_daemon, port(8090), port(8091));
-$t->waitforsocket('127.0.0.1:' . port(8090));
-$t->waitforsocket('127.0.0.1:' . port(8091));
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->io('###'), '', 'preread not enough');
-is(stream('127.0.0.1:' . port(8081))->io("\xAB\xCDQZ##"), "\xAB\xCDQZ##",
-	'preread validated');
-is(stream('127.0.0.1:' . port(8081))->io("\xAC\xCDQZ##"), '',
-	'preread invalid magic');
-is(stream('127.0.0.1:' . port(8081))->io("\xAB\xCDQQ##"), '',
-	'preread validation failed');
-
-TODO: {
-todo_skip 'leaves coredump', 3 unless $ENV{TEST_NGINX_UNSAFE}
-	or has_version('0.7.7');
-
-my $s = stream('127.0.0.1:' . port(8082));
-is($s->io("\xAB\xCDQZ##", read => 1), '##', 'filter validated');
-is($s->io("@@", read => 1), '@@', 'filter off');
-
-is(stream('127.0.0.1:' . port(8082))->io("\xAB\xCDQQ##"), '',
-	'filter validation failed');
-
-}
-
-is(stream('127.0.0.1:' . port(8083))->io('ABC'), 'ABC', 'access fetch ok');
-is(stream('127.0.0.1:' . port(8084))->io('ABC'), '', 'access fetch nok');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub stream_daemon {
-	my (@ports) = @_;
-	my (@socks, @clients);
-
-	for my $port (@ports) {
-		my $server = IO::Socket::INET->new(
-			Proto => 'tcp',
-			LocalAddr => "127.0.0.1:$port",
-			Listen => 5,
-			Reuse => 1
-		)
-			or die "Can't create listening socket: $!\n";
-		push @socks, $server;
-	}
-
-	my $sel = IO::Select->new(@socks);
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	while (my @ready = $sel->can_read) {
-		foreach my $fh (@ready) {
-			if (grep $_ == $fh, @socks) {
-				my $new = $fh->accept;
-				$new->autoflush(1);
-				$sel->add($new);
-
-			} elsif (stream_handle_client($fh)
-				|| $fh->sockport() == port(8090))
-			{
-				$sel->remove($fh);
-				$fh->close;
-			}
-		}
-	}
-}
-
-sub stream_handle_client {
-	my ($client) = @_;
-
-	log2c("(new connection $client)");
-
-	$client->sysread(my $buffer, 65536) or return 1;
-
-	log2i("$client $buffer");
-
-	if ($buffer eq "__CLOSE__") {
-		return 1;
-	}
-
-	log2o("$client $buffer");
-
-	$client->syswrite($buffer);
-
-	return 0;
-}
-
-sub log2i { Test::Nginx::log_core('|| <<', @_); }
-sub log2o { Test::Nginx::log_core('|| >>', @_); }
-sub log2c { Test::Nginx::log_core('||', @_); }
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_fetch_https.t
+++ /dev/null
@@ -1,425 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, fetch method, https support.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()
-	->has(qw/http http_ssl rewrite stream stream_return socket_ssl/)
-	->has_daemon('openssl')
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081 ssl default;
-        server_name  default.example.com;
-
-        ssl_certificate default.example.com.chained.crt;
-        ssl_certificate_key default.example.com.key;
-
-        location /loc {
-            return 200 "You are at default.example.com.";
-        }
-
-        location /success {
-            return 200;
-        }
-
-        location /fail {
-            return 403;
-        }
-
-        location /backend {
-            return 200 "BACKEND OK";
-        }
-    }
-
-    server {
-        listen       127.0.0.1:8081 ssl;
-        server_name  1.example.com;
-
-        ssl_certificate 1.example.com.chained.crt;
-        ssl_certificate_key 1.example.com.key;
-
-        location /loc {
-            return 200 "You are at 1.example.com.";
-        }
-    }
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import   test.js;
-    js_var      $message;
-
-    resolver  127.0.0.1:%%PORT_8981_UDP%%;
-    resolver_timeout 1s;
-
-    server {
-        listen  127.0.0.1:8082;
-        js_preread  test.preread;
-        return  "default CA $message";
-    }
-
-    server {
-        listen  127.0.0.1:8083;
-        js_preread  test.preread;
-        return  "my CA $message";
-
-        js_fetch_ciphers HIGH:!aNull:!MD5;
-        js_fetch_protocols TLSv1.1 TLSv1.2;
-        js_fetch_trusted_certificate myca.crt;
-    }
-
-    server {
-        listen  127.0.0.1:8084;
-        js_preread  test.preread;
-        return  "my CA with verify_depth=0 $message";
-
-        js_fetch_verify_depth 0;
-        js_fetch_trusted_certificate myca.crt;
-    }
-
-    server {
-        listen  127.0.0.1:8085;
-
-        js_access test.access_ok;
-        ssl_preread on;
-
-        js_fetch_ciphers HIGH:!aNull:!MD5;
-        js_fetch_protocols TLSv1.1 TLSv1.2;
-        js_fetch_trusted_certificate myca.crt;
-
-        proxy_pass 127.0.0.1:8081;
-    }
-
-    server {
-        listen  127.0.0.1:8086;
-
-        js_access test.access_nok;
-        ssl_preread on;
-
-        js_fetch_ciphers HIGH:!aNull:!MD5;
-        js_fetch_protocols TLSv1.1 TLSv1.2;
-        js_fetch_trusted_certificate myca.crt;
-
-        proxy_pass 127.0.0.1:8081;
-    }
-}
-
-EOF
-
-my $p1 = port(8081);
-my $p2 = port(8082);
-my $p3 = port(8083);
-my $p4 = port(8084);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function preread(s) {
-        s.on('upload', function (data, flags) {
-            if (data.startsWith('GO')) {
-                s.off('upload');
-                ngx.fetch('https://' + data.substring(2) + ':$p1/loc')
-                   .then(reply => {
-                       s.variables.message = 'https OK - ' + reply.status;
-                       s.done();
-                   })
-                   .catch(e => {
-                       s.variables.message = 'https NOK - ' + e.message;
-                       s.done();
-                   })
-
-            } else if (data.length) {
-                s.deny();
-            }
-        });
-    }
-
-    async function access_ok(s) {
-        let r = await ngx.fetch('https://default.example.com:$p1/success',
-                                {body: s.remoteAddress});
-
-        (r.status == 200) ? s.allow(): s.deny();
-    }
-
-    async function access_nok(s) {
-        let r = await ngx.fetch('https://default.example.com:$p1/fail',
-                                {body: s.remoteAddress});
-
-        (r.status == 200) ? s.allow(): s.deny();
-    }
-
-    export default {njs: test_njs, preread, access_ok, access_nok};
-EOF
-
-my $d = $t->testdir();
-
-$t->write_file('openssl.conf', <<EOF);
-[ req ]
-default_bits = 2048
-encrypt_key = no
-distinguished_name = req_distinguished_name
-[ req_distinguished_name ]
-EOF
-
-$t->write_file('myca.conf', <<EOF);
-[ ca ]
-default_ca = myca
-
-[ myca ]
-new_certs_dir = $d
-database = $d/certindex
-default_md = sha256
-policy = myca_policy
-serial = $d/certserial
-default_days = 1
-x509_extensions = myca_extensions
-
-[ myca_policy ]
-commonName = supplied
-
-[ myca_extensions ]
-basicConstraints = critical,CA:TRUE
-EOF
-
-system('openssl req -x509 -new '
-	. "-config $d/openssl.conf -subj /CN=myca/ "
-	. "-out $d/myca.crt -keyout $d/myca.key "
-	. ">>$d/openssl.out 2>&1") == 0
-	or die "Can't create self-signed certificate for CA: $!\n";
-
-foreach my $name ('intermediate', 'default.example.com', '1.example.com') {
-	system("openssl req -new "
-		. "-config $d/openssl.conf -subj /CN=$name/ "
-		. "-out $d/$name.csr -keyout $d/$name.key "
-		. ">>$d/openssl.out 2>&1") == 0
-		or die "Can't create certificate signing req for $name: $!\n";
-}
-
-$t->write_file('certserial', '1000');
-$t->write_file('certindex', '');
-
-system("openssl ca -batch -config $d/myca.conf "
-	. "-keyfile $d/myca.key -cert $d/myca.crt "
-	. "-subj /CN=intermediate/ -in $d/intermediate.csr "
-	. "-out $d/intermediate.crt "
-	. ">>$d/openssl.out 2>&1") == 0
-	or die "Can't sign certificate for intermediate: $!\n";
-
-foreach my $name ('default.example.com', '1.example.com') {
-	system("openssl ca -batch -config $d/myca.conf "
-		. "-keyfile $d/intermediate.key -cert $d/intermediate.crt "
-		. "-subj /CN=$name/ -in $d/$name.csr -out $d/$name.crt "
-		. ">>$d/openssl.out 2>&1") == 0
-		or die "Can't sign certificate for $name $!\n";
-	$t->write_file("$name.chained.crt", $t->read_file("$name.crt")
-		. $t->read_file('intermediate.crt'));
-}
-
-$t->try_run('no njs.fetch')->plan(6);
-
-$t->run_daemon(\&dns_daemon, port(8981), $t);
-$t->waitforfile($t->testdir . '/' . port(8981));
-
-###############################################################################
-
-local $TODO = 'not yet' unless has_version('0.7.0');
-
-like(stream("127.0.0.1:$p2")->io('GOdefault.example.com'),
-	qr/connect failed/s, 'stream non trusted CA');
-like(stream("127.0.0.1:$p3")->io('GOdefault.example.com'),
-	qr/https OK/s, 'stream trusted CA');
-like(stream("127.0.0.1:$p3")->io('GOlocalhost'),
-	qr/connect failed/s, 'stream wrong CN');
-like(stream("127.0.0.1:$p4")->io('GOdefaul.example.com'),
-	qr/connect failed/s, 'stream verify_depth too small');
-
-like(https_get('default.example.com', port(8085), '/backend'),
-	qr!BACKEND OK!, 'access https fetch');
-is(https_get('default.example.com', port(8086), '/backend'), '<conn failed>',
-	'access https fetch not');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub get_ssl_socket {
-	my ($host, $port) = @_;
-	my $s;
-
-	eval {
-		local $SIG{ALRM} = sub { die "timeout\n" };
-		local $SIG{PIPE} = sub { die "sigpipe\n" };
-		alarm(8);
-		$s = IO::Socket::SSL->new(
-			Proto => 'tcp',
-			PeerAddr => '127.0.0.1:' . $port,
-			SSL_verify_mode => IO::Socket::SSL::SSL_VERIFY_NONE(),
-			SSL_error_trap => sub { die $_[1] }
-		);
-
-		alarm(0);
-	};
-
-	alarm(0);
-
-	if ($@) {
-		log_in("died: $@");
-		return undef;
-	}
-
-	return $s;
-}
-
-sub https_get {
-	my ($host, $port, $url) = @_;
-	my $s = get_ssl_socket($host, $port);
-
-	if (!$s) {
-		return '<conn failed>';
-	}
-
-	return http(<<EOF, socket => $s);
-GET $url HTTP/1.0
-Host: $host
-
-EOF
-}
-
-###############################################################################
-
-sub reply_handler {
-	my ($recv_data, $port, %extra) = @_;
-
-	my (@name, @rdata);
-
-	use constant NOERROR	=> 0;
-	use constant A		=> 1;
-	use constant IN		=> 1;
-
-	# default values
-
-	my ($hdr, $rcode, $ttl) = (0x8180, NOERROR, 3600);
-
-	# decode name
-
-	my ($len, $offset) = (undef, 12);
-	while (1) {
-		$len = unpack("\@$offset C", $recv_data);
-		last if $len == 0;
-		$offset++;
-		push @name, unpack("\@$offset A$len", $recv_data);
-		$offset += $len;
-	}
-
-	$offset -= 1;
-	my ($id, $type, $class) = unpack("n x$offset n2", $recv_data);
-
-	my $name = join('.', @name);
-
-	if ($type == A) {
-		push @rdata, rd_addr($ttl, '127.0.0.1');
-	}
-
-	$len = @name;
-	pack("n6 (C/a*)$len x n2", $id, $hdr | $rcode, 1, scalar @rdata,
-		0, 0, @name, $type, $class) . join('', @rdata);
-}
-
-sub rd_addr {
-	my ($ttl, $addr) = @_;
-
-	my $code = 'split(/\./, $addr)';
-
-	return pack 'n3N', 0xc00c, A, IN, $ttl if $addr eq '';
-
-	pack 'n3N nC4', 0xc00c, A, IN, $ttl, eval "scalar $code", eval($code);
-}
-
-sub dns_daemon {
-	my ($port, $t) = @_;
-
-	my ($data, $recv_data);
-	my $socket = IO::Socket::INET->new(
-		LocalAddr    => '127.0.0.1',
-		LocalPort    => $port,
-		Proto        => 'udp',
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	# signal we are ready
-
-	open my $fh, '>', $t->testdir() . '/' . $port;
-	close $fh;
-
-	while (1) {
-		$socket->recv($recv_data, 65536);
-		$data = reply_handler($recv_data, $port);
-		$socket->send($data);
-	}
-}
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_fetch_init.t
+++ /dev/null
@@ -1,149 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, Response prototype reinitialization.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http rewrite stream/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    server {
-        listen      127.0.0.1:8081;
-        js_access   test.access_ok;
-        proxy_pass  127.0.0.1:8090;
-    }
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-
-        location /success {
-            return 200;
-        }
-    }
-}
-
-EOF
-
-my $p = port(8080);
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    async function access_ok(s) {
-        let reply = await ngx.fetch('http://127.0.0.1:$p/success');
-
-        (reply.status == 200) ? s.allow(): s.deny();
-    }
-
-    export default {njs: test_njs, access_ok};
-EOF
-
-$t->try_run('no stream njs available')->plan(1);
-
-$t->run_daemon(\&stream_daemon, port(8090));
-$t->waitforsocket('127.0.0.1:' . port(8090));
-
-###############################################################################
-
-local $TODO = 'not yet' unless has_version('0.7.9');
-
-is(stream('127.0.0.1:' . port(8081))->io('ABC'), 'ABC', 'access fetch ok');
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub stream_daemon {
-	my $server = IO::Socket::INET->new(
-		Proto => 'tcp',
-		LocalAddr => '127.0.0.1:' . port(8090),
-		Listen => 5,
-		Reuse => 1
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	while (my $client = $server->accept()) {
-		$client->autoflush(1);
-
-		log2c("(new connection $client)");
-
-		$client->sysread(my $buffer, 65536) or next;
-
-		log2i("$client $buffer");
-
-		log2o("$client $buffer");
-
-		$client->syswrite($buffer);
-
-		close $client;
-	}
-}
-
-sub log2i { Test::Nginx::log_core('|| <<', @_); }
-sub log2o { Test::Nginx::log_core('|| >>', @_); }
-sub log2c { Test::Nginx::log_core('||', @_); }
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_import.t
+++ /dev/null
@@ -1,117 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, js_import directive.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_set $test foo.bar.p;
-
-    js_import lib.js;
-    js_import foo from ./main.js;
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $test;
-    }
-
-    server {
-        listen      127.0.0.1:8082;
-        js_access   lib.access;
-        js_preread  lib.preread;
-        js_filter   lib.filter;
-        proxy_pass  127.0.0.1:8083;
-    }
-
-    server {
-        listen  127.0.0.1:8083;
-        return  "x";
-    }
-}
-
-EOF
-
-$t->write_file('lib.js', <<EOF);
-    var res = '';
-
-    function access(s) {
-        res += '1';
-        s.allow();
-    }
-
-    function preread(s) {
-        s.on('upload', function (data) {
-            res += '2';
-            if (res.length >= 3) {
-                s.done();
-            }
-        });
-    }
-
-    function filter(s) {
-        s.on('upload', function(data, flags) {
-            s.send(data);
-            res += '3';
-        });
-
-        s.on('download', function(data, flags) {
-            if (!flags.last) {
-                res += '4';
-                s.send(data);
-
-            } else {
-                res += '5';
-                s.send(res, {last:1});
-                s.off('download');
-            }
-        });
-    }
-
-    export default {access, preread, filter};
-
-EOF
-
-$t->write_file('main.js', <<EOF);
-    export default {bar: {p(s) {return "P-TEST"}}};
-
-EOF
-
-$t->try_run('no njs available')->plan(2);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->read(), 'P-TEST', 'foo.bar.p');
-is(stream('127.0.0.1:' . port(8082))->io('0'), 'x122345', 'lib.access');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_import2.t
+++ /dev/null
@@ -1,117 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, js_import directive in server context.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    server {
-        listen  127.0.0.1:8081;
-        js_import foo from ./main.js;
-        js_set $test foo.bar.p;
-        return  $test;
-    }
-
-    server {
-        listen      127.0.0.1:8082;
-
-        js_import lib.js;
-
-        js_access   lib.access;
-        js_preread  lib.preread;
-        js_filter   lib.filter;
-        proxy_pass  127.0.0.1:8083;
-    }
-
-    server {
-        listen  127.0.0.1:8083;
-        return  "x";
-    }
-}
-
-EOF
-
-$t->write_file('lib.js', <<EOF);
-    var res = '';
-
-    function access(s) {
-        res += '1';
-        s.allow();
-    }
-
-    function preread(s) {
-        s.on('upload', function (data) {
-            res += '2';
-            if (res.length >= 3) {
-                s.done();
-            }
-        });
-    }
-
-    function filter(s) {
-        s.on('upload', function(data, flags) {
-            s.send(data);
-            res += '3';
-        });
-
-        s.on('download', function(data, flags) {
-            if (!flags.last) {
-                res += '4';
-                s.send(data);
-
-            } else {
-                res += '5';
-                s.send(res, {last:1});
-                s.off('download');
-            }
-        });
-    }
-
-    export default {access, preread, filter};
-
-EOF
-
-$t->write_file('main.js', <<EOF);
-    export default {bar: {p(s) {return "P-TEST"}}};
-
-EOF
-
-$t->try_run('no njs available')->plan(2);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->read(), 'P-TEST', 'foo.bar.p');
-is(stream('127.0.0.1:' . port(8082))->io('0'), 'x122345', 'lib.access');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_ngx.t
+++ /dev/null
@@ -1,94 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, ngx object.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-    }
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    js_set $log     test.log;
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $log;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function log(s) {
-        ngx.log(ngx.INFO, `ngx.log:FOO`);
-        ngx.log(ngx.WARN, `ngx.log:BAR`);
-        ngx.log(ngx.ERR, `ngx.log:BAZ`);
-        return 'OK';
-    }
-
-    export default {njs: test_njs, log};
-
-EOF
-
-$t->try_run('no njs ngx')->plan(4);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->read(), 'OK', 'log var');
-
-$t->stop();
-
-like($t->read_file('error.log'), qr/\[info\].*ngx.log:FOO/, 'ngx.log info');
-like($t->read_file('error.log'), qr/\[warn\].*ngx.log:BAR/, 'ngx.log warn');
-like($t->read_file('error.log'), qr/\[error\].*ngx.log:BAZ/, 'ngx.log err');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_object.t
+++ /dev/null
@@ -1,98 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, stream session object.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_set $test     test.test;
-
-    js_import test.js;
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $test$status;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function to_string(s) {
-        return s.toString() === '[object Stream Session]';
-    }
-
-    function define_prop(s) {
-        Object.defineProperty(s.variables, 'status', {value:400});
-        return s.variables.status == 400;
-    }
-
-    function in_operator(s) {
-        return ['status', 'unknown']
-               .map(v=>v in s.variables)
-               .toString() === 'true,false';
-    }
-
-    function redefine_proto(s) {
-        s[0] = 'a';
-        s[1] = 'b';
-        s.length = 2;
-        Object.setPrototypeOf(s, Array.prototype);
-        return s.join('|') === 'a|b';
-    }
-
-    function get_own_prop_descs(s) {
-        return Object.getOwnPropertyDescriptors(s)['on'].value === s.on;
-    }
-
-    function test(s) {
-        return [ to_string,
-                 define_prop,
-                 in_operator,
-                 redefine_proto,
-                 get_own_prop_descs,
-               ].every(v=>v(s));
-    }
-
-    export default {test};
-
-EOF
-
-$t->try_run('no njs stream session object')->plan(1);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->read(), 'true400', 'var set');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_preload_object.t
+++ /dev/null
@@ -1,122 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Vadim Zhestikov
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, js_preload_object directive.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_preload_object g1 from g.json;
-
-    js_set $test foo.bar.p;
-
-    js_import lib.js;
-    js_import foo from ./main.js;
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $test;
-    }
-
-    server {
-        listen      127.0.0.1:8082;
-        js_access   lib.access;
-        js_preread  lib.preread;
-        js_filter   lib.filter;
-        proxy_pass  127.0.0.1:8083;
-    }
-
-    server {
-        listen  127.0.0.1:8083;
-        return  "x";
-    }
-}
-
-EOF
-
-$t->write_file('lib.js', <<EOF);
-    var res = '';
-
-    function access(s) {
-        res += g1.a;
-        s.allow();
-    }
-
-    function preread(s) {
-        s.on('upload', function (data) {
-            res += g1.b[1];
-            if (res.length >= 3) {
-                s.done();
-            }
-        });
-    }
-
-    function filter(s) {
-        s.on('upload', function(data, flags) {
-            s.send(data);
-            res += g1.c.prop[0].a;
-        });
-
-        s.on('download', function(data, flags) {
-            if (!flags.last) {
-                res += g1.b[3];
-                s.send(data);
-
-            } else {
-                res += g1.b[4];
-                s.send(res, {last:1});
-                s.off('download');
-            }
-        });
-    }
-
-    export default {access, preread, filter};
-
-EOF
-
-$t->write_file('main.js', <<EOF);
-    export default {bar: {p(s) {return g1.b[2]}}};
-
-EOF
-
-$t->write_file('g.json',
-	'{"a":1, "b":[1,2,"element",4,5], "c":{"prop":[{"a":3}]}}');
-
-$t->try_run('no js_preload_object available')->plan(2);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->read(), 'element', 'foo.bar.p');
-is(stream('127.0.0.1:' . port(8082))->io('0'), 'x122345', 'lib.access');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_send.t
+++ /dev/null
@@ -1,205 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for s.send() in stream njs module.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/http stream/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-http {
-    %%TEST_GLOBALS_HTTP%%
-
-    js_import test.js;
-
-    server {
-        listen       127.0.0.1:8080;
-        server_name  localhost;
-
-        location /njs {
-            js_content test.njs;
-        }
-    }
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    server {
-        listen      127.0.0.1:8081;
-        js_filter   test.filter;
-        proxy_pass  127.0.0.1:8090;
-    }
-
-    server {
-        listen      127.0.0.1:8082;
-        js_filter   test.filter_direct;
-        proxy_pass  127.0.0.1:8090;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function test_njs(r) {
-        r.return(200, njs.version);
-    }
-
-    function filter(s) {
-      s.on("upload", async (data, flags) => {
-        s.send("__HANDSHAKE__", flags);
-
-        const p = new Promise((resolve, reject) => {
-              s.on("download", (data, flags) => {
-                  s.off("download");
-                  resolve(data);
-              });
-        });
-
-        s.off("upload");
-
-        const handshakeResponse = await p;
-        if (handshakeResponse != '__HANDSHAKE_RESPONSE__') {
-            throw `Handshake failed: \${handshakeResponse}`;
-        }
-
-        s.send(data, flags);
-      });
-    }
-
-    function filter_direct(s) {
-      s.on("upload", async (data, flags) => {
-        s.sendUpstream("__HANDSHAKE__", flags);
-
-        const p = new Promise((resolve, reject) => {
-              s.on("download", (data, flags) => {
-                  s.off("download");
-                  resolve(data);
-              });
-        });
-
-        s.off("upload");
-
-        const handshakeResponse = await p;
-        if (handshakeResponse != '__HANDSHAKE_RESPONSE__') {
-            throw `Handshake failed: \${handshakeResponse}`;
-        }
-
-        s.sendDownstream('xxx', flags);
-        s.sendUpstream(data, flags);
-      });
-    }
-
-    export default {njs:test_njs, filter, filter_direct};
-
-EOF
-
-$t->run_daemon(\&stream_daemon, port(8090));
-$t->try_run('no stream njs available')->plan(2);
-$t->waitforsocket('127.0.0.1:' . port(8090));
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->io('abc'), 'ABC',
-	'async filter');;
-is(stream('127.0.0.1:' . port(8082))->io('abc'), 'xxxABC',
-	'async filter direct');
-
-$t->stop();
-
-###############################################################################
-
-sub has_version {
-	my $need = shift;
-
-	http_get('/njs') =~ /^([.0-9]+)$/m;
-
-	my @v = split(/\./, $1);
-	my ($n, $v);
-
-	for $n (split(/\./, $need)) {
-		$v = shift @v || 0;
-		return 0 if $n > $v;
-		return 1 if $v > $n;
-	}
-
-	return 1;
-}
-
-###############################################################################
-
-sub stream_daemon {
-	my $server = IO::Socket::INET->new(
-		Proto => 'tcp',
-		LocalAddr => '127.0.0.1:' . port(8090),
-		Listen => 5,
-		Reuse => 1
-	)
-		or die "Can't create listening socket: $!\n";
-
-	local $SIG{PIPE} = 'IGNORE';
-
-	while (my $client = $server->accept()) {
-		$client->autoflush(1);
-
-		log2c("(new connection $client)");
-
-		$client->sysread(my $buffer, 65536) or next;
-
-		log2i("$client $buffer");
-
-		if ($buffer ne "__HANDSHAKE__") {
-			$buffer = "__HANDSHAKE_INVALID__";
-			log2o("$client $buffer");
-			$client->syswrite($buffer);
-
-			close $client;
-		}
-
-		$buffer = "__HANDSHAKE_RESPONSE__";
-		log2o("$client $buffer");
-		$client->syswrite($buffer);
-
-		$client->sysread($buffer, 65536) or next;
-
-		$buffer = uc($buffer);
-		log2o("$client $buffer");
-		$client->syswrite($buffer);
-
-		close $client;
-	}
-}
-
-sub log2i { Test::Nginx::log_core('|| <<', @_); }
-sub log2o { Test::Nginx::log_core('|| >>', @_); }
-sub log2c { Test::Nginx::log_core('||', @_); }
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_var.t
+++ /dev/null
@@ -1,75 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, js_var directive.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    js_var $foo;
-    js_var $bar a:$remote_addr;
-    js_set $var test.varr;
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $bar$foo;
-    }
-
-    server {
-        listen  127.0.0.1:8082;
-        return  $var$foo;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function varr(s) {
-        s.variables.foo = 'xxx';
-        return '';
-    }
-
-    export default {varr};
-EOF
-
-$t->try_run('no stream js_var')->plan(2);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->io('###'), 'a:127.0.0.1',
-	'default value');
-is(stream('127.0.0.1:' . port(8082))->io('###'), 'xxx', 'value set');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_var2.t
+++ /dev/null
@@ -1,75 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, js_var directive in server context.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_import test.js;
-
-    js_var $foo;
-
-    server {
-        listen  127.0.0.1:8081;
-        js_var $bar a:$remote_addr;
-        return  $bar$foo;
-    }
-
-    server {
-        listen  127.0.0.1:8082;
-        js_set $var test.varr;
-        return  $var$foo;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function varr(s) {
-        s.variables.foo = 'xxx';
-        return '';
-    }
-
-    export default {varr};
-EOF
-
-$t->try_run('no stream js_var')->plan(2);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->io('###'), 'a:127.0.0.1',
-	'default value');
-is(stream('127.0.0.1:' . port(8082))->io('###'), 'xxx', 'value set');
-
-###############################################################################
deleted file mode 100644
--- a/stream_js_variables.t
+++ /dev/null
@@ -1,84 +0,0 @@
-#!/usr/bin/perl
-
-# (C) Dmitry Volyntsev
-# (C) Nginx, Inc.
-
-# Tests for stream njs module, setting nginx variables.
-
-###############################################################################
-
-use warnings;
-use strict;
-
-use Test::More;
-
-BEGIN { use FindBin; chdir($FindBin::Bin); }
-
-use lib 'lib';
-use Test::Nginx;
-use Test::Nginx::Stream qw/ stream /;
-
-###############################################################################
-
-select STDERR; $| = 1;
-select STDOUT; $| = 1;
-
-my $t = Test::Nginx->new()->has(qw/stream stream_return/)
-	->write_file_expand('nginx.conf', <<'EOF');
-
-%%TEST_GLOBALS%%
-
-daemon off;
-
-events {
-}
-
-stream {
-    %%TEST_GLOBALS_STREAM%%
-
-    js_set $test_var       test.variable;
-    js_set $test_not_found test.not_found;
-
-    js_import test.js;
-
-    server {
-        listen  127.0.0.1:8081;
-        return  $test_var$status;
-    }
-
-    server {
-        listen  127.0.0.1:8082;
-        return  $test_not_found;
-    }
-}
-
-EOF
-
-$t->write_file('test.js', <<EOF);
-    function variable(s) {
-        s.variables.status = 400;
-        return 'test_var';
-    }
-
-    function not_found(s) {
-        try {
-            s.variables.unknown = 1;
-        } catch (e) {
-            return 'not_found';
-        }
-    }
-
-    export default {variable, not_found};
-
-EOF
-
-$t->try_run('no stream njs available')->plan(2);
-
-###############################################################################
-
-is(stream('127.0.0.1:' . port(8081))->read(), 'test_var400', 'var set');
-is(stream('127.0.0.1:' . port(8082))->read(), 'not_found', 'not found set');
-
-$t->stop();
-
-###############################################################################