- Fix pull consumer fetch: send original stream subject in HMSG (not inbox) so NATS client distinguishes data messages from control messages - Fix MaxAge expiry: add background timer in StreamManager for periodic pruning - Fix JetStream wire format: Go-compatible anonymous objects with string enums, proper offset-based pagination for stream/consumer list APIs - Add 42 E2E black-box tests (core messaging, auth, TLS, accounts, JetStream) - Add ~1000 parity tests across all subsystems (gaps closure) - Update gap inventory docs to reflect implementation status
67 lines
2.2 KiB
C#
67 lines
2.2 KiB
C#
using System.Text;
|
|
using NATS.Server.WebSocket;
|
|
|
|
namespace NATS.Server.Tests.WebSocket;
|
|
|
|
public class WsUpgradeHelperParityBatch1Tests
|
|
{
|
|
[Fact]
|
|
public void MakeChallengeKey_returns_base64_of_16_random_bytes()
|
|
{
|
|
var key = WsUpgrade.MakeChallengeKey();
|
|
var decoded = Convert.FromBase64String(key);
|
|
|
|
decoded.Length.ShouldBe(16);
|
|
}
|
|
|
|
[Fact]
|
|
public void Url_helpers_match_ws_and_wss_schemes()
|
|
{
|
|
WsUpgrade.IsWsUrl("ws://localhost:8080").ShouldBeTrue();
|
|
WsUpgrade.IsWsUrl("wss://localhost:8443").ShouldBeFalse();
|
|
WsUpgrade.IsWsUrl("http://localhost").ShouldBeFalse();
|
|
|
|
WsUpgrade.IsWssUrl("wss://localhost:8443").ShouldBeTrue();
|
|
WsUpgrade.IsWssUrl("ws://localhost:8080").ShouldBeFalse();
|
|
WsUpgrade.IsWssUrl("https://localhost").ShouldBeFalse();
|
|
}
|
|
|
|
[Fact]
|
|
public async Task RejectNoMaskingForTest_forces_no_masking_handshake_rejection()
|
|
{
|
|
var request = BuildValidRequest("/leafnode", "Nats-No-Masking: true\r\n");
|
|
using var input = new MemoryStream(Encoding.ASCII.GetBytes(request));
|
|
using var output = new MemoryStream();
|
|
|
|
try
|
|
{
|
|
WsUpgrade.RejectNoMaskingForTest = true;
|
|
var result = await WsUpgrade.TryUpgradeAsync(input, output, new WebSocketOptions { NoTls = true });
|
|
|
|
result.Success.ShouldBeFalse();
|
|
output.Position = 0;
|
|
var response = Encoding.ASCII.GetString(output.ToArray());
|
|
response.ShouldContain("400 Bad Request");
|
|
response.ShouldContain("invalid value for no-masking");
|
|
}
|
|
finally
|
|
{
|
|
WsUpgrade.RejectNoMaskingForTest = false;
|
|
}
|
|
}
|
|
|
|
private static string BuildValidRequest(string path = "/", string extraHeaders = "")
|
|
{
|
|
var sb = new StringBuilder();
|
|
sb.Append($"GET {path} HTTP/1.1\r\n");
|
|
sb.Append("Host: localhost:8080\r\n");
|
|
sb.Append("Upgrade: websocket\r\n");
|
|
sb.Append("Connection: Upgrade\r\n");
|
|
sb.Append("Sec-WebSocket-Key: dGhlIHNhbXBsZSBub25jZQ==\r\n");
|
|
sb.Append("Sec-WebSocket-Version: 13\r\n");
|
|
sb.Append(extraHeaders);
|
|
sb.Append("\r\n");
|
|
return sb.ToString();
|
|
}
|
|
}
|