18
18
//! If this works, it means that the client is correctly configured and you can use it to make requests to the DB.
19
19
20
20
mod client_request;
21
+ mod precondition;
21
22
22
- use client_request:: { ClientRequest , PingRequest , VerifyApiTokenRequest } ;
23
+ use client_request:: {
24
+ ClientRequest , OneShotRequest , PingRequest , VerifyApiTokenRequest , WriteEventsRequest ,
25
+ } ;
23
26
27
+ pub use precondition:: Precondition ;
24
28
use reqwest;
25
29
use url:: Url ;
26
30
27
- use crate :: error:: ClientError ;
31
+ use crate :: {
32
+ error:: ClientError ,
33
+ event:: { Event , EventCandidate } ,
34
+ } ;
28
35
29
36
/// Client for an [EventsourcingDB](https://www.eventsourcingdb.io/) instance.
30
37
#[ derive( Debug ) ]
@@ -72,9 +79,14 @@ impl Client {
72
79
73
80
/// Utility function to request an endpoint of the API.
74
81
///
82
+ /// This function will return a [`reqwest::RequestBuilder`] which can be used to send the request.
83
+ ///
75
84
/// # Errors
76
85
/// This function will return an error if the request fails or if the URL is invalid.
77
- async fn request < R : ClientRequest > ( & self , endpoint : R ) -> Result < R :: Response , ClientError > {
86
+ fn build_request < R : ClientRequest > (
87
+ & self ,
88
+ endpoint : & R ,
89
+ ) -> Result < reqwest:: RequestBuilder , ClientError > {
78
90
let url = self
79
91
. base_url
80
92
. join ( endpoint. url_path ( ) )
@@ -93,15 +105,27 @@ impl Client {
93
105
} else {
94
106
request
95
107
} ;
108
+ Ok ( request)
109
+ }
96
110
97
- let response = request. send ( ) . await ?;
111
+ /// Utility function to request an endpoint of the API as a oneshot.
112
+ ///
113
+ /// This means, that the response is not streamed, but returned as a single value.
114
+ ///
115
+ /// # Errors
116
+ /// This function will return an error if the request fails or if the URL is invalid.
117
+ async fn request_oneshot < R : OneShotRequest > (
118
+ & self ,
119
+ endpoint : R ,
120
+ ) -> Result < R :: Response , ClientError > {
121
+ let response = self . build_request ( & endpoint) ?. send ( ) . await ?;
98
122
99
123
if response. status ( ) . is_success ( ) {
100
124
let result = response. json ( ) . await ?;
101
125
endpoint. validate_response ( & result) ?;
102
126
Ok ( result)
103
127
} else {
104
- Err ( ClientError :: DBError (
128
+ Err ( ClientError :: DBApiError (
105
129
response. status ( ) ,
106
130
response. text ( ) . await . unwrap_or_default ( ) ,
107
131
) )
@@ -125,7 +149,7 @@ impl Client {
125
149
/// # Errors
126
150
/// This function will return an error if the request fails or if the URL is invalid.
127
151
pub async fn ping ( & self ) -> Result < ( ) , ClientError > {
128
- let _ = self . request ( PingRequest ) . await ?;
152
+ let _ = self . request_oneshot ( PingRequest ) . await ?;
129
153
Ok ( ( ) )
130
154
}
131
155
@@ -146,7 +170,45 @@ impl Client {
146
170
/// # Errors
147
171
/// This function will return an error if the request fails or if the URL is invalid.
148
172
pub async fn verify_api_token ( & self ) -> Result < ( ) , ClientError > {
149
- let _ = self . request ( VerifyApiTokenRequest ) . await ?;
173
+ let _ = self . request_oneshot ( VerifyApiTokenRequest ) . await ?;
150
174
Ok ( ( ) )
151
175
}
176
+
177
+ /// Writes events to the DB instance.
178
+ ///
179
+ /// ```
180
+ /// use eventsourcingdb_client_rust::event::EventCandidate;
181
+ /// # use serde_json::json;
182
+ /// # tokio_test::block_on(async {
183
+ /// # let container = eventsourcingdb_client_rust::container::Container::start_default().await.unwrap();
184
+ /// let db_url = "http://localhost:3000/";
185
+ /// let api_token = "secrettoken";
186
+ /// # let db_url = container.get_base_url().await.unwrap();
187
+ /// # let api_token = container.get_api_token();
188
+ /// let client = eventsourcingdb_client_rust::client::Client::new(db_url, api_token);
189
+ /// let candidates = vec![
190
+ /// EventCandidate::builder()
191
+ /// .source("https://www.eventsourcingdb.io".to_string())
192
+ /// .data(json!({"value": 1}))
193
+ /// .subject("/test".to_string())
194
+ /// .r#type("io.eventsourcingdb.test".to_string())
195
+ /// .build()
196
+ /// ];
197
+ /// let written_events = client.write_events(candidates, vec![]).await.expect("Failed to write events");
198
+ /// # })
199
+ /// ```
200
+ ///
201
+ /// # Errors
202
+ /// This function will return an error if the request fails or if the URL is invalid.
203
+ pub async fn write_events (
204
+ & self ,
205
+ events : Vec < EventCandidate > ,
206
+ preconditions : Vec < Precondition > ,
207
+ ) -> Result < Vec < Event > , ClientError > {
208
+ self . request_oneshot ( WriteEventsRequest {
209
+ events,
210
+ preconditions,
211
+ } )
212
+ . await
213
+ }
152
214
}
0 commit comments