Skip to content

fix(js): propagate proxy, timeout, and custom headers to JS templates#7281

Open
eyupcanakman wants to merge 2 commits intoprojectdiscovery:devfrom
eyupcanakman:fix/js-template-flags-6645
Open

fix(js): propagate proxy, timeout, and custom headers to JS templates#7281
eyupcanakman wants to merge 2 commits intoprojectdiscovery:devfrom
eyupcanakman:fix/js-template-flags-6645

Conversation

@eyupcanakman
Copy link
Copy Markdown

@eyupcanakman eyupcanakman commented Mar 21, 2026

Proposed changes

Fixes #6645

JS protocol templates ignored --proxy, --timeout, and -H flags because these values were not forwarded to the JS execution context. This forwards them through ExecuteOptions into the JS runtime so net.Open/OpenTLS can route connections through an HTTP CONNECT proxy and respect the configured timeout. Custom headers are exposed as a template variable.

Proof

$ go vet ./pkg/js/... ./pkg/protocols/javascript/...
$ go test -v -race ./pkg/js/libs/net/...
=== RUN   TestGetTimeoutFromContext
--- PASS: TestGetTimeoutFromContext (0.00s)
=== RUN   TestBufferedConn
--- PASS: TestBufferedConn (0.00s)
=== RUN   TestDialHTTPProxy
    --- PASS: TestDialHTTPProxy/successful_CONNECT_tunnel (0.00s)
    --- PASS: TestDialHTTPProxy/proxy_returns_non-200_status (0.00s)
    --- PASS: TestDialHTTPProxy/invalid_proxy_URL (0.00s)
    --- PASS: TestDialHTTPProxy/unreachable_proxy (0.00s)
--- PASS: TestDialHTTPProxy (0.00s)
PASS

Checklist

  • Pull request is created against the dev branch
  • All checks passed (lint, unit/integration/regression tests etc.) with my changes
  • I have added tests that prove my fix is effective or that my feature works
  • I have added necessary documentation (if appropriate)

Summary by CodeRabbit

  • New Features

    • HTTP proxy support via HTTP CONNECT tunneling for applicable network requests
    • Connection timeouts now respect execution-context timeout variants
    • Exposes CLI custom headers to JavaScript templates
    • JS runtime receives per-execution proxy and timeout values to ensure correct behavior in pooled runtimes
  • Tests

    • Added tests for proxy handling, timeout resolution, buffered-connection behavior, and CONNECT tunneling success/failure

@auto-assign auto-assign bot requested a review from dogancanbakir March 21, 2026 06:21
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai bot commented Mar 21, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 2fee4d27-d0d5-4204-8b9d-4c753c2f20af

📥 Commits

Reviewing files that changed from the base of the PR and between 8f0568c and 53a1503.

📒 Files selected for processing (2)
  • pkg/js/libs/net/net.go
  • pkg/js/libs/net/net_test.go

Walkthrough

Adds ProxyURL to JS execution options, injects proxyURL and timeoutVariants into pooled Goja runtimes, implements HTTP CONNECT proxy dialing and context-driven timeouts in the JS net library with buffering and TLS-over-proxy support, adds unit tests, and threads proxy and custom headers into JavaScript execution paths.

Changes

Cohort / File(s) Summary
Compiler Configuration
pkg/js/compiler/compiler.go
Added exported ProxyURL string to ExecuteOptions with comment clarifying HTTP CONNECT usage and noting SOCKS handled elsewhere.
Runtime Context Injection
pkg/js/compiler/pool.go
Inject proxyURL and timeoutVariants into pooled goja.Runtime when present; remove them (and executionId) after execution to avoid leaking values across runtime reuse.
Network Proxy & Timeout Implementation
pkg/js/libs/net/net.go
Use getTimeoutFromContext for per-call timeouts; implement dialHTTPProxy supporting http/https proxy URLs, optional TLS-to-proxy, Basic auth header, CONNECT request/response handling (require 200 OK), deadline management, and bufferedConn to preserve buffered bytes. Wrap TLS over proxy and ensure handshake errors close the connection.
Network Tests
pkg/js/libs/net/net_test.go
Add tests for getTimeoutFromContext, bufferedConn read semantics, and dialHTTPProxy (successful CONNECT, non-200 responses, invalid URL, TLS proxy, unreachable proxy). Includes test helpers like directDial and fakeConn.
JavaScript Integration
pkg/protocols/javascript/js.go
Pass AliveHttpProxy into compiler.ExecuteOptions.ProxyURL for template init, pre-condition, and main execution; expose CLI CustomHeaders into payloadValues["custom_headers"] as a map[string]string when provided.

Sequence Diagram(s)

sequenceDiagram
    rect rgba(135,206,250,0.5)
    participant JS as JavaScript Runtime
    end
    rect rgba(144,238,144,0.5)
    participant Pool as Runtime Pool
    end
    rect rgba(255,228,181,0.5)
    participant Net as net library
    end
    rect rgba(255,182,193,0.5)
    participant Proxy as HTTP CONNECT Proxy
    end
    rect rgba(221,160,221,0.5)
    participant Target as Remote Target
    end

    JS->>Pool: ExecuteWithOptions { ProxyURL, timeoutVariants }
    Pool->>JS: inject context values (proxyURL, timeoutVariants)
    JS->>Net: Open/OpenTLS(ctx, address)
    Net->>Net: getTimeoutFromContext(ctx)
    alt proxyURL present (http/https)
        Net->>Proxy: dialHTTPProxy CONNECT target (with optional BasicAuth)
        Proxy-->>Net: 200 OK (tunnel established)
        Net->>Target: (over tunnel) TLS handshake / TCP I/O
    else no proxy
        Net->>Target: direct dial (respect timeout)
    end
    Net-->>JS: return net.Conn or error
    Pool->>JS: cleanup context values (proxyURL, timeoutVariants)
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Poem

🐰 I dug a tunnel, quick and neat,
Brought timeouts, headers, a proxy seat,
JS hops through CONNECT's door,
Buffered bytes and TLS explore,
Hooray — requests now find their beat.

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 45.45% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately describes the main changes: propagating proxy, timeout, and custom headers to JS templates.
Linked Issues check ✅ Passed The PR addresses all coding requirements from issue #6645: proxy forwarding via ExecuteOptions, timeout propagation, custom headers exposure, and HTTP CONNECT proxy implementation.
Out of Scope Changes check ✅ Passed All changes are directly scoped to addressing issue #6645: proxy/timeout/headers support in JS templates and net helpers.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
⚔️ Resolve merge conflicts
  • Resolve merge conflict in branch fix/js-template-flags-6645

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@neo-by-projectdiscovery-dev
Copy link
Copy Markdown

neo-by-projectdiscovery-dev bot commented Mar 21, 2026

Neo - PR Security Review

No security issues found

Highlights

  • Adds HTTP CONNECT proxy tunneling for JS templates via new dialHTTPProxy function
  • Exposes CLI custom headers (-H flag) to JS templates as custom_headers variable
  • Implements context-based timeout propagation to replace hardcoded 5s default
Hardening Notes
  • Consider validating the address parameter in dialHTTPProxy (net.go:44) to reject addresses containing CRLF characters (\r or \n) as defense-in-depth against potential template-based injection, though JS templates are trusted code
  • Add explicit documentation in net.Open/OpenTLS JSDoc comments noting that address parameters should not contain user-controlled data without validation
  • Consider rate-limiting or logging proxy connection attempts in dialHTTPProxy to detect potential abuse patterns

Comment @pdneo help for available commands. · Open in Neo

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (2)
pkg/js/libs/net/net.go (1)

106-115: Silent fallback to direct connection when proxy URL parsing fails.

If url.Parse(proxyURL) returns an error, the code silently falls through to direct dialing without logging or notifying the user. This could mask configuration issues where the user expects traffic to go through a proxy but it doesn't.

Consider logging a warning when proxy URL parsing fails so users are aware their proxy configuration is being ignored.

💡 Suggested enhancement for Open (similar change needed in OpenTLS)
 	// check for HTTP proxy in context
 	if proxyURL, ok := ctx.Value("proxyURL").(string); ok && proxyURL != "" && protocol == "tcp" {
 		parsed, err := url.Parse(proxyURL)
+		if err != nil {
+			// Log and fall through to direct connection
+			// Consider: gologger.Warning().Msgf("invalid proxy URL %q, using direct connection: %v", proxyURL, err)
+		}
 		if err == nil && (parsed.Scheme == "http" || parsed.Scheme == "https") {

Also applies to: 146-160

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@pkg/js/libs/net/net.go` around lines 106 - 115, The code silently falls back
to direct dialing when url.Parse(proxyURL) fails; modify the block that checks
ctx.Value("proxyURL") in the TCP proxy branch to detect the parse error and emit
a warning (using the existing logger or processLogger) including the proxyURL
and the parse error before continuing to the direct dial fallback; update the
same pattern in the corresponding OpenTLS branch (the code around dialHTTPProxy
and NetConn creation) so both Open and OpenTLS warn on parse failure rather than
failing silently.
pkg/protocols/javascript/js.go (1)

396-404: Inconsistent indentation on line 396.

Line 396 has unusual leading whitespace before result, err := that doesn't match the surrounding code style.

💅 Suggested fix
-			result, err := request.options.JsCompiler.ExecuteWithOptions(request.preConditionCompiled, argsCopy,
+		result, err := request.options.JsCompiler.ExecuteWithOptions(request.preConditionCompiled, argsCopy,
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@pkg/protocols/javascript/js.go` around lines 396 - 404, The indentation for
the call that assigns result and err (the line starting with "result, err :=" in
the block invoking request.options.JsCompiler.ExecuteWithOptions) is misaligned;
align that line with the surrounding block so it matches the indentation of the
subsequent argument lines and the enclosing function/method (look for
ExecuteWithOptions invocation inside the method where
request.preConditionCompiled and argsCopy are passed). Ensure the entire call
uses consistent indentation (same indent level for the "result, err :=" line and
the following argument lines) to match project style.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@pkg/js/libs/net/net.go`:
- Around line 106-115: The code silently falls back to direct dialing when
url.Parse(proxyURL) fails; modify the block that checks ctx.Value("proxyURL") in
the TCP proxy branch to detect the parse error and emit a warning (using the
existing logger or processLogger) including the proxyURL and the parse error
before continuing to the direct dial fallback; update the same pattern in the
corresponding OpenTLS branch (the code around dialHTTPProxy and NetConn
creation) so both Open and OpenTLS warn on parse failure rather than failing
silently.

In `@pkg/protocols/javascript/js.go`:
- Around line 396-404: The indentation for the call that assigns result and err
(the line starting with "result, err :=" in the block invoking
request.options.JsCompiler.ExecuteWithOptions) is misaligned; align that line
with the surrounding block so it matches the indentation of the subsequent
argument lines and the enclosing function/method (look for ExecuteWithOptions
invocation inside the method where request.preConditionCompiled and argsCopy are
passed). Ensure the entire call uses consistent indentation (same indent level
for the "result, err :=" line and the following argument lines) to match project
style.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 9e48f834-ad14-4dfb-af02-852afd33cfe1

📥 Commits

Reviewing files that changed from the base of the PR and between 48e05ca and 7b2d48a.

📒 Files selected for processing (5)
  • pkg/js/compiler/compiler.go
  • pkg/js/compiler/pool.go
  • pkg/js/libs/net/net.go
  • pkg/js/libs/net/net_test.go
  • pkg/protocols/javascript/js.go

@eyupcanakman eyupcanakman force-pushed the fix/js-template-flags-6645 branch from 7b2d48a to 07f21d8 Compare March 21, 2026 06:46
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
pkg/protocols/javascript/js.go (1)

157-162: ⚠️ Potential issue | 🟡 Minor

Init block does not receive ProxyURL unlike other execution paths.

The Init execution (lines 157-162) passes TimeoutVariants but not ProxyURL, while pre-condition (line 402) and request execution (line 579) both pass ProxyURL. If Init code makes network calls via net.Open/OpenTLS, those connections won't use the configured proxy.

This may be intentional (Init runs once during template compilation, typically for payload preparation), but worth verifying whether Init should also support proxy routing for consistency.

Proposed fix if proxy support is needed in Init
 		opts := &compiler.ExecuteOptions{
 			ExecutionId:     request.options.Options.ExecutionId,
 			TimeoutVariants: request.options.Options.GetTimeouts(),
+			ProxyURL:        request.options.Options.AliveHttpProxy,
 			Source:          &request.Init,
 			Context:         context.Background(),
 		}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@pkg/protocols/javascript/js.go` around lines 157 - 162, Init execution builds
compiler.ExecuteOptions without setting ProxyURL, so Init network calls won't
use the configured proxy; update the code that constructs
compiler.ExecuteOptions for the Init run (the opts variable in the Init path) to
include the same ProxyURL assignment as other paths (e.g., set ProxyURL:
request.options.Options.GetProxyURL() or use request.options.Options.ProxyURL)
so that compiler.ExecuteOptions used by Init includes ProxyURL just like the
pre-condition and request execution paths; modify the block that creates opts
(where ExecutionId, TimeoutVariants, Source, Context are set) to also populate
ProxyURL from the request options.
🧹 Nitpick comments (1)
pkg/protocols/javascript/js.go (1)

396-404: Minor formatting inconsistency.

Line 396 appears to have inconsistent indentation (extra leading whitespace before result, err :=). Consider running go fmt ./... to ensure consistent formatting.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@pkg/protocols/javascript/js.go` around lines 396 - 404, The call to
request.options.JsCompiler.ExecuteWithOptions in js.go has inconsistent leading
whitespace before "result, err :="; fix by normalizing indentation to align with
surrounding code (remove the extra leading space) and run go fmt (go fmt ./...)
to ensure consistent formatting across the file; look for the ExecuteWithOptions
invocation in the same function where request.preConditionCompiled, argsCopy and
compiler.ExecuteOptions are passed to locate and correct the indentation.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@pkg/js/libs/net/net.go`:
- Around line 71-85: The code currently discards any bytes buffered by
bufio.NewReader(proxyConn) after parsing the CONNECT response, causing data
loss; change the return to wrap proxyConn in a new bufferedConn that preserves
the bufio.Reader's buffered bytes. Implement a bufferedConn type that holds the
original net.Conn and the bufio.Reader (or an io.Reader created from the
reader's buffer + conn), have its Read first drain the reader's buffered bytes
and then read from the underlying conn, delegate Close/SetDeadline/etc. to the
underlying connection, and return that bufferedConn from the function instead of
proxyConn so no bytes are lost after http.ReadResponse.

---

Outside diff comments:
In `@pkg/protocols/javascript/js.go`:
- Around line 157-162: Init execution builds compiler.ExecuteOptions without
setting ProxyURL, so Init network calls won't use the configured proxy; update
the code that constructs compiler.ExecuteOptions for the Init run (the opts
variable in the Init path) to include the same ProxyURL assignment as other
paths (e.g., set ProxyURL: request.options.Options.GetProxyURL() or use
request.options.Options.ProxyURL) so that compiler.ExecuteOptions used by Init
includes ProxyURL just like the pre-condition and request execution paths;
modify the block that creates opts (where ExecutionId, TimeoutVariants, Source,
Context are set) to also populate ProxyURL from the request options.

---

Nitpick comments:
In `@pkg/protocols/javascript/js.go`:
- Around line 396-404: The call to request.options.JsCompiler.ExecuteWithOptions
in js.go has inconsistent leading whitespace before "result, err :="; fix by
normalizing indentation to align with surrounding code (remove the extra leading
space) and run go fmt (go fmt ./...) to ensure consistent formatting across the
file; look for the ExecuteWithOptions invocation in the same function where
request.preConditionCompiled, argsCopy and compiler.ExecuteOptions are passed to
locate and correct the indentation.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 63b76d89-fc75-4d50-a6eb-490f0ec376e1

📥 Commits

Reviewing files that changed from the base of the PR and between 7b2d48a and 07f21d8.

📒 Files selected for processing (5)
  • pkg/js/compiler/compiler.go
  • pkg/js/compiler/pool.go
  • pkg/js/libs/net/net.go
  • pkg/js/libs/net/net_test.go
  • pkg/protocols/javascript/js.go
✅ Files skipped from review due to trivial changes (1)
  • pkg/js/libs/net/net_test.go
🚧 Files skipped from review as they are similar to previous changes (1)
  • pkg/js/compiler/compiler.go

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (1)
pkg/js/libs/net/net_test.go (1)

19-44: Consider testing the actual implementation function.

These tests validate the context value pattern and URL parsing behavior, but they don't exercise the actual proxyURLFromContext function (or equivalent) from net.go. While this documents the expected pattern, consider adding a test that calls the real function to ensure it handles these cases correctly.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@pkg/js/libs/net/net_test.go` around lines 19 - 44, Add a unit test that calls
the actual proxyURLFromContext function (and optionally dialHTTPProxy where
relevant) instead of only asserting on raw context values and url.Parse;
specifically, create contexts that contain "proxyURL" with
"http://proxy.example.com:8080", an empty context, and a
"socks5://proxy.example.com:1080" context and assert proxyURLFromContext(ctx)
returns the expected results (the http URL and true, empty/false for missing,
and either empty/false or no-op for the socks5 case) and that dialHTTPProxy is
not triggered for a socks scheme; reference proxyURLFromContext and
dialHTTPProxy to locate the implementations and ensure the tests exercise their
real behavior.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@pkg/js/libs/net/net_test.go`:
- Around line 19-44: Add a unit test that calls the actual proxyURLFromContext
function (and optionally dialHTTPProxy where relevant) instead of only asserting
on raw context values and url.Parse; specifically, create contexts that contain
"proxyURL" with "http://proxy.example.com:8080", an empty context, and a
"socks5://proxy.example.com:1080" context and assert proxyURLFromContext(ctx)
returns the expected results (the http URL and true, empty/false for missing,
and either empty/false or no-op for the socks5 case) and that dialHTTPProxy is
not triggered for a socks scheme; reference proxyURLFromContext and
dialHTTPProxy to locate the implementations and ensure the tests exercise their
real behavior.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 14e89dde-0a04-4c9a-b244-f5cdb8dcba9f

📥 Commits

Reviewing files that changed from the base of the PR and between 07f21d8 and c0f4973.

📒 Files selected for processing (4)
  • pkg/js/compiler/compiler.go
  • pkg/js/libs/net/net.go
  • pkg/js/libs/net/net_test.go
  • pkg/protocols/javascript/js.go
🚧 Files skipped from review as they are similar to previous changes (2)
  • pkg/js/libs/net/net.go
  • pkg/protocols/javascript/js.go

@eyupcanakman eyupcanakman force-pushed the fix/js-template-flags-6645 branch from c0f4973 to 8f0568c Compare March 25, 2026 17:30
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@pkg/js/libs/net/net.go`:
- Around line 127-140: The warning logs in the proxy handling code currently
print proxyURL verbatim (the ctx.Value("proxyURL") usage inside the TCP branch
and the matching OpenTLS branch), which can leak credentials; create a small
helper function (e.g., redactProxyURL(proxyURL string) string) that parses the
URL, strips or masks url.User (replace password with "***" or remove userinfo
entirely) and returns a safe string, then call that helper in the
gologger.Warning().Msgf calls instead of printing proxyURL directly; update both
the tcp branch around dialHTTPProxy and the OpenTLS proxy handling to use the
same helper so credential-containing proxy URLs are never logged.
- Around line 39-69: The dialHTTPProxy function currently treats all proxy URLs
as plaintext and always writes the CONNECT request directly to proxyConn; when
parsed.Scheme == "https" you must TLS-wrap the proxy connection first and use
default port 443 (instead of 8080) for host:port resolution. Update
dialHTTPProxy to: detect parsed.Scheme, set proxyAddr default port 443 for
"https" and 8080 otherwise, call dial to obtain proxyConn, and if parsed.Scheme
== "https" perform a tls.Client handshake (using parsed.Hostname() for
ServerName) before calling connectReq.Write; ensure Proxy-Authorization header
is still set on connectReq and that deadlines and error handling (Close on
error) remain intact.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 079d41ea-0884-4fd9-bc5d-81fca741081f

📥 Commits

Reviewing files that changed from the base of the PR and between c0f4973 and 8f0568c.

📒 Files selected for processing (5)
  • pkg/js/compiler/compiler.go
  • pkg/js/compiler/pool.go
  • pkg/js/libs/net/net.go
  • pkg/js/libs/net/net_test.go
  • pkg/protocols/javascript/js.go
🚧 Files skipped from review as they are similar to previous changes (1)
  • pkg/protocols/javascript/js.go

@neo-by-projectdiscovery-dev
Copy link
Copy Markdown

neo-by-projectdiscovery-dev bot commented Apr 2, 2026

Neo - PR Security Review

No security issues found

Comment @pdneo help for available commands. · Open in Neo

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[BUG] Javascript based templates ignore flags

1 participant