Skip to content

Commit b513422

Browse files
chore(agent-tunnel): address maintainer review feedback
* Drop `enroll.nu` — it was a developer convenience for local smoke tests, not part of the shipped product. * Document `EnrollmentClaims.JetAgentName` end-to-end: explain that the gateway never reads it (auth is by signature/scope), the authoritative name is sent in the agent's enrollment request body, and the JWT claim is read agent-side as the default for the `--name` CLI flag — letting DVLS pre-fill the name typed in the "Generate Enrollment String" dialog. * Move the `agent_tunnel_*` integration tests out of `devolutions-gateway/tests/` and into the `testsuite` crate's central test binary (`testsuite/tests/agent_tunnel/{integration, registry, routing}.rs`), where the rest of the cross-crate integration tests already live. Drop the now-ineffective `#![allow(unused_crate_dependencies)]` inner attributes (the lint is crate-level only) and add the agent-tunnel-related dev deps to `testsuite/Cargo.toml`.
1 parent 22b1663 commit b513422

9 files changed

Lines changed: 50 additions & 42 deletions

File tree

Cargo.lock

Lines changed: 11 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

enroll.nu

Lines changed: 0 additions & 31 deletions
This file was deleted.

testsuite/Cargo.toml

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,16 +31,27 @@ typed-builder = "0.21"
3131
tokio-tungstenite = { version = "0.26", features = ["rustls-tls-native-roots"] }
3232

3333
[dev-dependencies]
34+
agent-tunnel = { path = "../crates/agent-tunnel" }
35+
agent-tunnel-proto = { path = "../crates/agent-tunnel-proto", features = ["serde"] }
36+
devolutions-gateway-task = { path = "../crates/devolutions-gateway-task" }
3437
base64 = "0.22"
35-
proxy-socks = { path = "../crates/proxy-socks" }
38+
camino = "1"
39+
ipnetwork = "0.20"
3640
libsql = { version = "0.9", default-features = false, features = ["core"] }
3741
mcp-proxy.path = "../crates/mcp-proxy"
42+
proxy-socks = { path = "../crates/proxy-socks" }
43+
quinn = "0.11"
44+
rcgen = { version = "0.13", features = ["pem", "x509-parser"] }
3845
rstest = "0.25"
46+
rustls = { version = "0.23", default-features = false, features = ["ring", "logging", "std", "tls12"] }
47+
rustls-pemfile = "2"
48+
rustls-pki-types = "1"
3949
serde_json = "1"
4050
sysevent.path = "../crates/sysevent"
4151
tempfile = "3"
4252
test-utils.path = "../crates/test-utils"
4353
tokio-rustls = { version = "0.26", features = ["ring"] }
54+
uuid = { version = "1", features = ["v4"] }
4455

4556
[target.'cfg(unix)'.dev-dependencies]
4657
sysevent-syslog.path = "../crates/sysevent-syslog"

devolutions-gateway/tests/agent_tunnel_integration.rs renamed to testsuite/tests/agent_tunnel/integration.rs

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,3 @@
1-
#![allow(unused_crate_dependencies)]
2-
#![allow(clippy::unwrap_used)]
3-
41
//! Full-stack integration test for the QUIC agent tunnel (Quinn).
52
//!
63
//! Verifies the full data path:
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
//! Agent-tunnel integration tests.
2+
//!
3+
//! Cover the QUIC tunnel data path end-to-end (`integration`), the registry
4+
//! online/offline accounting (`registry`), and the routing decision pipeline
5+
//! (`routing`). All three exercise the live `agent-tunnel` crate; no
6+
//! mocking of the QUIC layer.
7+
8+
mod integration;
9+
mod registry;
10+
mod routing;

devolutions-gateway/tests/agent_tunnel_registry.rs renamed to testsuite/tests/agent_tunnel/registry.rs

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,3 @@
1-
#![allow(unused_crate_dependencies)]
2-
#![allow(clippy::unwrap_used)]
3-
41
use std::sync::Arc;
52

63
use agent_tunnel::registry::{AGENT_OFFLINE_TIMEOUT, AgentPeer, AgentRegistry};

devolutions-gateway/tests/agent_tunnel_routing.rs renamed to testsuite/tests/agent_tunnel/routing.rs

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,3 @@
1-
#![allow(unused_crate_dependencies)]
2-
#![allow(clippy::unwrap_used)]
3-
41
use std::sync::Arc;
52

63
use agent_tunnel::registry::{AgentPeer, AgentRegistry};

testsuite/tests/main.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
#![allow(clippy::print_stdout, reason = "test code uses print for diagnostics")]
33
#![allow(clippy::print_stderr, reason = "test code uses print for diagnostics")]
44

5+
mod agent_tunnel;
56
mod cli;
67
mod mcp_proxy;
78
mod sysevent;

utils/dotnet/Devolutions.Gateway.Utils/src/EnrollmentClaims.cs

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,22 @@ public class EnrollmentClaims : IGatewayClaims
2525
[JsonPropertyName("jet_gw_url")]
2626
public string JetGwUrl { get; set; }
2727

28-
/// <summary>Optional agent display-name hint.</summary>
28+
/// <summary>
29+
/// Optional agent display-name hint.
30+
///
31+
/// The gateway never reads this claim — it only verifies the JWT
32+
/// signature, scope, and expiry on <c>POST /jet/tunnel/enroll</c>; the
33+
/// authoritative agent name is the one the agent sends in its
34+
/// <c>EnrollRequest</c> body (which the gateway also stamps into the
35+
/// signed client certificate's CN).
36+
///
37+
/// The agent-side CLI parses this claim out of the JWT it receives via
38+
/// <c>--enrollment-string</c> and uses it as the default for
39+
/// <c>--name</c> when the operator did not pass one explicitly. Setting
40+
/// it here lets DVLS pre-fill the name the admin typed in the "Generate
41+
/// Enrollment String" dialog so the agent shows up under that name in
42+
/// the registry without an extra CLI flag.
43+
/// </summary>
2944
[JsonPropertyName("jet_agent_name")]
3045
[JsonIgnore(Condition = JsonIgnoreCondition.WhenWritingNull)]
3146
public string? JetAgentName { get; set; }

0 commit comments

Comments
 (0)