Stop data sync after account authorization revoke
This commit is contained in:
@@ -335,6 +335,51 @@ public sealed class RemoteControlClientTests
|
||||
Assert.All(handler.Requests, request => Assert.Equal("Bearer node-token", request.Authorization));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task FlushDropsAllQueuedBatchesAndBlocksAccountAfterRevocation()
|
||||
{
|
||||
var directory = Directory.CreateTempSubdirectory("wxagent-revoke-");
|
||||
try
|
||||
{
|
||||
var config = new ReportingConfig
|
||||
{
|
||||
Enabled = true,
|
||||
ConfigVersion = 1,
|
||||
Accounts = [new AccountReportingConfig
|
||||
{
|
||||
AccountId = "account-a", Enabled = true,
|
||||
AllowedChats = [new AllowedChat { Type = ReportingChatType.Private, ChatId = "chat-a", Enabled = true, IdentityVerified = true }]
|
||||
}]
|
||||
};
|
||||
var queue = new RemoteDataBatchQueue(Path.Combine(directory.FullName, "queue.json"));
|
||||
Assert.True(queue.Enqueue(config, SyncBatch("batch-1")).Accepted);
|
||||
Assert.True(queue.Enqueue(config, SyncBatch("batch-2")).Accepted);
|
||||
|
||||
var handler = new RevokedBatchHandler();
|
||||
using var http = new HttpClient(handler);
|
||||
using var client = new RemoteControlClient(new RemoteAgentOptions
|
||||
{
|
||||
AuthAddress = "http://127.0.0.1:8090",
|
||||
Token = "node-token",
|
||||
NodeId = "node-1"
|
||||
}, http);
|
||||
await client.RegisterAsync(new RemoteNodeRegistration("node-1", "test", RemoteProtocol.Version, ["db-messages"], 1, []));
|
||||
|
||||
var blockedAccounts = new HashSet<string>(StringComparer.Ordinal);
|
||||
var confirmed = await client.FlushDataBatchesAsync(queue, config, blockedAccounts);
|
||||
|
||||
Assert.Empty(confirmed);
|
||||
Assert.Contains("account-a", blockedAccounts);
|
||||
Assert.Empty(queue.Pending());
|
||||
Assert.Empty(new RemoteDataBatchQueue(Path.Combine(directory.FullName, "queue.json")).Pending());
|
||||
Assert.Equal(1, handler.BatchRequests);
|
||||
}
|
||||
finally
|
||||
{
|
||||
directory.Delete(true);
|
||||
}
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task MissingRemoteCredentialsAreRejectedWithoutNetworkAccess()
|
||||
{
|
||||
@@ -345,6 +390,38 @@ public sealed class RemoteControlClientTests
|
||||
Assert.Empty(handler.Requests);
|
||||
}
|
||||
|
||||
private static RemoteSyncBatch SyncBatch(string batchId) => new(
|
||||
"node-1", "account-a", batchId, "generation-a", "messages", 1, "{}", "{\"chat-a\\u001fmessage/a.db\":1}",
|
||||
"hash-" + batchId, "complete", [],
|
||||
[new RemoteSyncMessage(batchId, "chat-a", ReportingChatType.Private, batchId, "incoming", "text", "queued secret",
|
||||
DateTimeOffset.UtcNow, DateTimeOffset.UtcNow, "wx-1", "payload-" + batchId)]);
|
||||
|
||||
private sealed class RevokedBatchHandler : HttpMessageHandler
|
||||
{
|
||||
public int BatchRequests { get; private set; }
|
||||
|
||||
protected override Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
|
||||
{
|
||||
if (request.RequestUri!.AbsolutePath == "/v1/data/batches")
|
||||
{
|
||||
BatchRequests++;
|
||||
return Task.FromResult(new HttpResponseMessage(HttpStatusCode.Forbidden)
|
||||
{
|
||||
Content = new StringContent("{\"error\":{\"code\":\"AccountNotAuthorized\",\"message\":\"revoked\"}}", Encoding.UTF8, "application/json")
|
||||
});
|
||||
}
|
||||
if (request.RequestUri.AbsolutePath == "/v1/nodes/register")
|
||||
{
|
||||
var body = JsonSerializer.Serialize(new RemoteNodeRegistrationResponse("node-1", RemoteNodeStatus.Online, true, "register"), RemoteJson.Options);
|
||||
return Task.FromResult(new HttpResponseMessage(HttpStatusCode.OK)
|
||||
{
|
||||
Content = new StringContent(body, Encoding.UTF8, "application/json")
|
||||
});
|
||||
}
|
||||
throw new InvalidOperationException("Unexpected request " + request.RequestUri.AbsolutePath);
|
||||
}
|
||||
}
|
||||
|
||||
private sealed class RecordingHandler : HttpMessageHandler
|
||||
{
|
||||
public List<RecordedRequest> Requests { get; } = [];
|
||||
|
||||
Reference in New Issue
Block a user