1+ syntax = "proto3" ;
2+
3+ //
4+ // This protocol is UNSTABLE in the sense of being subject to change.
5+ //
6+
7+ package kurrentdb.protocol.v2 ;
8+
9+ option csharp_namespace = "KurrentDB.Protocol.V2" ;
10+ option java_package = "io.kurrentdb.v2" ;
11+ option java_multiple_files = true ;
12+
13+ import "dynamic-value.proto" ;
14+
15+ service StreamsService {
16+ // Executes an atomic operation to append records to multiple streams.
17+ // This transactional method ensures that all appends either succeed
18+ // completely, or are entirely rolled back, thereby maintaining strict data
19+ // consistency across all involved streams.
20+ rpc MultiStreamAppend (MultiStreamAppendRequest ) returns (MultiStreamAppendResponse );
21+
22+ // Streaming version of MultiStreamAppend that allows clients to send multiple
23+ // append requests over a single connection. When the stream completes, all
24+ // records are appended transactionally (all succeed or fail together).
25+ // Provides improved efficiency for high-throughput scenarios while
26+ // maintaining the same transactional guarantees.
27+ rpc MultiStreamAppendSession (stream AppendStreamRequest ) returns (MultiStreamAppendResponse );
28+ }
29+
30+ // Record to be appended to a stream.
31+ message AppendRecord {
32+ // Universally Unique identifier for the record. Must be a guid.
33+ // If not provided, the server will generate a new one.
34+ optional string record_id = 1 ;
35+
36+ // A collection of properties providing additional system information about the
37+ // record.
38+ map <string , kurrentdb.protobuf.DynamicValue > properties = 2 ;
39+
40+ // The actual data payload of the record, stored as bytes.
41+ bytes data = 3 ;
42+ }
43+
44+ // Constants that match the expected state of a stream during an
45+ // append operation. It can be used to specify whether the stream should exist,
46+ // not exist, or can be in any state.
47+ enum ExpectedRevisionConstants {
48+ // The stream should exist and have a single event.
49+ EXPECTED_REVISION_CONSTANTS_SINGLE_EVENT = 0 ;
50+
51+ // It is not important whether the stream exists or not.
52+ EXPECTED_REVISION_CONSTANTS_ANY = -2 ;
53+
54+ // The stream should not exist. If it does, the append will fail.
55+ EXPECTED_REVISION_CONSTANTS_NO_STREAM = -1 ;
56+
57+ // The stream should exist
58+ EXPECTED_REVISION_CONSTANTS_EXISTS = -4 ;
59+ }
60+
61+ // Represents the input for appending records to a specific stream.
62+ message AppendStreamRequest {
63+ // The name of the stream to append records to.
64+ string stream = 1 ;
65+
66+ // The records to append to the stream.
67+ repeated AppendRecord records = 2 ;
68+
69+ // The expected revision of the stream. If the stream's current revision does
70+ // not match, the append will fail.
71+ // The expected revision can also be one of the special values
72+ // from ExpectedRevisionConstants.
73+ // missing value means no expectation: same as EXPECTED_REVISION_CONSTANTS_ANY
74+ optional sint64 expected_revision = 3 ;
75+ }
76+
77+ // Success represents the successful outcome of an append operation.
78+ message AppendStreamSuccess {
79+ // The name of the stream to which records were appended.
80+ string stream = 1 ;
81+
82+ // The position of the last appended record in the transaction.
83+ int64 position = 2 ;
84+
85+ // The revision of the stream after the append operation.
86+ int64 stream_revision = 3 ;
87+ }
88+
89+ // Failure represents the detailed error information when an append operation fails.
90+ message AppendStreamFailure {
91+ // The name of the stream to which records failed to append.
92+ string stream = 1 ;
93+
94+ // The error details
95+ oneof error {
96+ // Failed because the actual stream revision didn't match the expected revision.
97+ ErrorDetails.WrongExpectedRevision wrong_expected_revision = 2 ;
98+
99+ // Failed because the client lacks sufficient permissions.
100+ ErrorDetails.AccessDenied access_denied = 3 ;
101+
102+ // Failed because the target stream has been deleted.
103+ ErrorDetails.StreamDeleted stream_deleted = 4 ;
104+
105+ ErrorDetails.TransactionMaxSizeExceeded transaction_max_size_exceeded = 5 ;
106+ }
107+ }
108+
109+ // Represents the output of appending records to a specific stream.
110+ message AppendStreamResponse {
111+ // The result of the append operation.
112+ oneof result {
113+ // Success represents the successful outcome of an append operation.
114+ AppendStreamSuccess success = 1 ;
115+
116+ // Failure represents the details of a failed append operation.
117+ AppendStreamFailure failure = 2 ;
118+ }
119+ }
120+
121+ // MultiStreamAppendRequest represents a request to append records to multiple streams.
122+ message MultiStreamAppendRequest {
123+ // A list of AppendStreamInput messages, each representing a stream to which records should be appended.
124+ repeated AppendStreamRequest input = 1 ;
125+ }
126+
127+ // Response from the MultiStreamAppend operation.
128+ message MultiStreamAppendResponse {
129+ oneof result {
130+ // Success represents the successful outcome of a multi-stream append operation.
131+ Success success = 1 ;
132+
133+ // Failure represents the details of a failed multi-stream append operation.
134+ Failure failure = 2 ;
135+ }
136+
137+ message Success {
138+ repeated AppendStreamSuccess output = 1 ;
139+ }
140+
141+ message Failure {
142+ repeated AppendStreamFailure output = 1 ;
143+ }
144+ }
145+
146+ // ErrorDetails provides detailed information about specific error conditions.
147+ message ErrorDetails {
148+ // When the user does not have sufficient permissions to perform the operation.
149+ message AccessDenied {
150+ // The reason for access denial.
151+ string reason = 1 ;
152+ }
153+
154+ // When the stream has been deleted.
155+ message StreamDeleted {
156+ }
157+
158+ // When the expected revision of the stream does not match the actual revision.
159+ message WrongExpectedRevision {
160+ // The actual revision of the stream.
161+ int64 stream_revision = 1 ;
162+ }
163+
164+ // When the transaction exceeds the maximum size allowed
165+ // (it's bigger than the configured chunk size).
166+ message TransactionMaxSizeExceeded {
167+ // The maximum allowed size of the transaction.
168+ int32 max_size = 1 ;
169+ }
170+ }
0 commit comments