Skip to content

Commit ab12fa7

Browse files
authored
Merge pull request #530 from AmbireTech/pr-review
`sentry` API docs PR review
2 parents 72bb5af + f80f20b commit ab12fa7

File tree

11 files changed

+99
-63
lines changed

11 files changed

+99
-63
lines changed

.DS_Store

-10 KB
Binary file not shown.

primitives/Cargo.toml

Lines changed: 7 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -21,32 +21,29 @@ postgres = ["bytes", "tokio-postgres", "deadpool-postgres"]
2121
test-util = []
2222

2323
[[example]]
24-
name = "channel_list_query"
25-
required-features = ["test-util"]
24+
name = "analytics_query"
2625

2726
[[example]]
28-
name = "campaign_list_query"
29-
required-features = ["test-util"]
27+
name = "analytics_response"
3028

3129
[[example]]
32-
name = "campaign_list_response"
30+
name = "campaign_list_query"
3331
required-features = ["test-util"]
3432

3533
[[example]]
36-
name = "create_campaign"
34+
name = "campaign_list_response"
3735
required-features = ["test-util"]
3836

3937
[[example]]
40-
name = "modify_campaign"
38+
name = "channel_list_query"
4139
required-features = ["test-util"]
4240

4341
[[example]]
44-
name = "analytics_query"
42+
name = "create_campaign"
4543
required-features = ["test-util"]
4644

4745
[[example]]
48-
name = "analytics_response"
49-
required-features = ["test-util"]
46+
name = "modify_campaign"
5047

5148
[dependencies]
5249
# (De)Serialization

primitives/examples/analytics_query.rs

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -41,8 +41,16 @@ fn main() {
4141

4242
// Query with all possible fields (publisher/advertiser/admin)
4343
{
44-
let query_str = "limit=200&eventType=CLICK&metric=paid&segmentBy=country&timeframe=week&start=2022-08-04+09:00:00.000000000+UTC&campaignId=0x936da01f9abd4d9d80c702af85c822a8&adUnit=QmcUVX7fvoLMM93uN2bD3wGTH8MXSxeL8hojYfL2Lhp7mR&adSlot=Qmasg8FrbuSQpjFu3kRnZF9beg8rEBFrqgi1uXDRwCbX5f&adSlotType=legacy_300x100&advertiser=0xDd589B43793934EF6Ad266067A0d1D4896b0dff0&publisher=0xE882ebF439207a70dDcCb39E13CA8506c9F45fD9\
45-
&hostname=localhost&country=Bulgaria&osName=Windows&chains[0]=1&chains[1]=1337";
44+
let query_str = "limit=200&eventType=CLICK&metric=paid&segmentBy=country\
45+
&timeframe=week&start=2022-08-04+09:00:00.000000000+UTC\
46+
&campaignId=0x936da01f9abd4d9d80c702af85c822a8\
47+
&adUnit=QmcUVX7fvoLMM93uN2bD3wGTH8MXSxeL8hojYfL2Lhp7mR\
48+
&adSlot=Qmasg8FrbuSQpjFu3kRnZF9beg8rEBFrqgi1uXDRwCbX5f\
49+
&adSlotType=legacy_300x100\
50+
&advertiser=0xDd589B43793934EF6Ad266067A0d1D4896b0dff0\
51+
&publisher=0xE882ebF439207a70dDcCb39E13CA8506c9F45fD9\
52+
&hostname=localhost&country=Bulgaria&osName=Windows\
53+
&chains[0]=1&chains[1]=1337";
4654
let query: AnalyticsQuery = serde_qs::from_str(query_str).unwrap();
4755

4856
assert_eq!(query.limit, 200);

primitives/examples/create_campaign.rs

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3,15 +3,15 @@ use serde_json::json;
33
use std::str::FromStr;
44

55
fn main() {
6-
// CreateCampaign in an HTTP request
6+
// CreateCampaign in an HTTP request.
7+
// A CampaignId will be randomly generated for the newly created Campaign.
78
{
89
let create_campaign = CreateCampaign::from_campaign_erased(DUMMY_CAMPAIGN.clone(), None);
910

10-
let create_campaign_str =
11+
let _create_campaign_str =
1112
serde_json::to_string(&create_campaign).expect("should serialize");
1213

1314
let create_campaign_json = json!({
14-
"id":null,
1515
"channel":{
1616
"leader":"0x80690751969B234697e9059e04ed72195c3507fa",
1717
"follower":"0xf3f583AEC5f7C030722Fe992A5688557e1B86ef7",
@@ -34,7 +34,10 @@ fn main() {
3434
}
3535
],
3636
"title":"Dummy Campaign",
37-
"pricingBounds":{"CLICK":{"min":"0","max":"0"},"IMPRESSION":{"min":"1","max":"10"}},
37+
"pricingBounds":{
38+
"CLICK":{"min":"0","max":"0"},
39+
"IMPRESSION":{"min":"1","max":"10"}
40+
},
3841
"eventSubmission":{"allow":[]},
3942
"targetingRules":[],
4043
"created":1612162800000_u64,
@@ -43,6 +46,7 @@ fn main() {
4346

4447
let create_campaign_json =
4548
serde_json::to_string(&create_campaign_json).expect("should serialize");
49+
4650
let deserialized: CreateCampaign =
4751
serde_json::from_str(&create_campaign_json).expect("should deserialize");
4852

primitives/examples/modify_campaign.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
use primitives::{sentry::campaign_modify::ModifyCampaign, unified_num::FromWhole, UnifiedNum};
22
use serde_json::json;
3-
use std::str::FromStr;
43

54
fn main() {
65
{

primitives/src/sentry.rs

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -319,9 +319,10 @@ pub struct FetchedAnalytics {
319319
pub segment: Option<String>,
320320
}
321321

322-
// Response returned when getting Analytics - an array of FetchedAnalytics
323-
//
324-
/// # Examples:
322+
/// Response returned when getting Analytics which returns the [`FetchedAnalytics`].
323+
///
324+
/// # Examples
325+
///
325326
/// ```
326327
#[doc = include_str!("../examples/analytics_response.rs")]
327328
/// ```
@@ -651,6 +652,13 @@ pub struct ValidationErrorResponse {
651652
pub validation: Vec<String>,
652653
}
653654

655+
/// Request body for posting new [`Event`]s to a [`Campaign`](crate::Campaign).
656+
#[derive(Serialize, Deserialize, Clone, Debug, PartialEq, Eq)]
657+
#[serde(rename_all = "camelCase")]
658+
pub struct InsertEventsRequest {
659+
pub events: Vec<Event>,
660+
}
661+
654662
pub mod channel_list {
655663
use crate::{ChainId, Channel, ValidatorId};
656664
use serde::{Deserialize, Serialize};

sentry/.DS_Store

-6 KB
Binary file not shown.

sentry/src/routes.rs

Lines changed: 46 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,8 @@
106106
//!
107107
//! Request body (json): [`ValidatorMessagesCreateRequest`](primitives::sentry::ValidatorMessagesCreateRequest)
108108
//!
109-
//! Example:
109+
//! ##### Examples:
110+
//!
110111
//! ```json
111112
//! {
112113
//! "messages": [
@@ -231,14 +232,20 @@
231232
//! **Authentication is required** to validate [`Campaign.creator`](primitives::Campaign::creator) == [`Auth.uid`](crate::Auth::uid)
232233
//!
233234
//! It will make sure the `Channel` is created if new and it will update
234-
//! the spendable amount using the [`Adapter`]`::get_deposit()`.
235+
//! the spendable amount using the [`Adapter.get_deposit()`](adapter::client::Locked::get_deposit).
235236
//!
236237
//! The route is handled by [`campaign::create_campaign()`].
237238
//!
238239
//! Request body (json): [`CreateCampaign`][primitives::sentry::campaign_create::CreateCampaign]
239240
//!
240241
//! Response: [`Campaign`]
241242
//!
243+
//! ##### Examples
244+
//!
245+
//! ```
246+
#![doc = include_str!("../../primitives/examples/create_campaign.rs")]
247+
//! ```
248+
//!
242249
//! #### POST `/v5/campaign/:id` (auth required)
243250
//!
244251
//! Modify the [`Campaign`]. Request must be sent by the [`Campaign.creator`](primitives::Campaign::creator).
@@ -251,22 +258,20 @@
251258
//!
252259
//! Response: [`Campaign`]
253260
//!
261+
//! ##### Examples
262+
//!
263+
//! ```
264+
#![doc = include_str!("../../primitives/examples/modify_campaign.rs")]
265+
//! ```
266+
//!
254267
//! #### POST `/v5/campaign/:id/events`
255268
//!
256269
//! Add new [`Event`]s (`IMPRESSION`s & `CLICK`s) to the [`Campaign`].
257270
//! Applies [`Campaign.event_submission`] rules and additional validation using [`check_access()`].
258271
//!
259272
//! The route is handled by [`campaign::insert_events::handle_route()`].
260273
//!
261-
//! Request body (json):
262-
//!
263-
//! ```json
264-
//! {
265-
//! "events": [
266-
//! // Events
267-
//! ]
268-
//! }
269-
//! ```
274+
//! Request body (json): [`InsertEventsRequest`](primitives::sentry::InsertEventsRequest)
270275
//!
271276
//! Response: [`SuccessResponse`]
272277
//!
@@ -290,10 +295,24 @@
290295
//!
291296
//! Allowed keys: [`AllowedKey::Country`][primitives::analytics::query::AllowedKey::Country], [`AllowedKey::AdSlotType`][primitives::analytics::query::AllowedKey::AdSlotType]
292297
//!
293-
//! Request query parameters: [`AnalyticsQuery`][primitives::analytics::AnalyticsQuery]
298+
//! Request query parameters: [`AnalyticsQuery`]
294299
//!
295300
//! Response: [`AnalyticsResponse`]
296301
//!
302+
//! ##### Examples
303+
//!
304+
//! Query:
305+
//!
306+
//! ```
307+
#![doc = include_str!("../../primitives/examples/analytics_query.rs")]
308+
//! ```
309+
//!
310+
//! Response:
311+
//!
312+
//! ```
313+
#![doc = include_str!("../../primitives/examples/analytics_response.rs")]
314+
//! ```
315+
//!
297316
//! #### GET `/v5/analytics/for-publisher` (auth required)
298317
//!
299318
//! Returns all analytics where the currently authenticated address [`Auth.uid`](crate::Auth::uid) is a **publisher**.
@@ -302,10 +321,14 @@
302321
//!
303322
//! The route is handled by [`get_analytics()`].
304323
//!
305-
//! Request query parameters: [`AnalyticsQuery`][primitives::analytics::AnalyticsQuery]
324+
//! Request query parameters: [`AnalyticsQuery`]
306325
//!
307326
//! Response: [`AnalyticsResponse`]
308327
//!
328+
//! ##### Examples
329+
//!
330+
//! See [GET `/v5/analytics`](#get-v5analytics)
331+
//!
309332
//! #### GET `/v5/analytics/for-advertiser` (auth required)
310333
//!
311334
//! Returns all analytics where the currently authenticated address [`Auth.uid`](crate::Auth::uid) is an **advertiser**.
@@ -314,10 +337,14 @@
314337
//!
315338
//! The route is handled by [`get_analytics()`].
316339
//!
317-
//! Request query parameters: [`AnalyticsQuery`][primitives::analytics::AnalyticsQuery]
340+
//! Request query parameters: [`AnalyticsQuery`]
318341
//!
319342
//! Response: [`AnalyticsResponse`]
320343
//!
344+
//! ##### Examples
345+
//!
346+
//! See [GET `/v5/analytics`](#get-v5analytics)
347+
//!
321348
//! #### GET `/v5/analytics/for-admin` (auth required)
322349
//!
323350
//! Admin access to the analytics with no restrictions on the keys for filtering.
@@ -328,10 +355,14 @@
328355
//!
329356
//! The route is handled by [`get_analytics()`].
330357
//!
331-
//! Request query parameters: [`AnalyticsQuery`][primitives::analytics::AnalyticsQuery]
358+
//! Request query parameters: [`AnalyticsQuery`]
332359
//!
333360
//! Response: [`AnalyticsResponse`]
334361
//!
362+
//! ##### Examples
363+
//!
364+
//! See [GET `/v5/analytics`](#get-v5analytics)
365+
//!
335366
//! [`Adapter`]: adapter::Adapter
336367
//! [`Address`]: primitives::Address
337368
//! [`AllowedKey`]: primitives::analytics::query::AllowedKey

sentry/src/routes/analytics.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,9 +19,9 @@ use primitives::{
1919
};
2020

2121
/// GET `/v5/analytics` routes
22-
/// Request query parameters: [`primitives::analytics::AnalyticsQuery`].
22+
/// Request query parameters: [`AnalyticsQuery`].
2323
///
24-
/// Response: [`primitives::sentry::AnalyticsResponse`]
24+
/// Response: [`AnalyticsResponse`]
2525
///
2626
/// Analytics routes:
2727
/// - GET `/v5/analytics`

sentry/src/routes/campaign.rs

Lines changed: 10 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -144,9 +144,9 @@ pub async fn fetch_campaign_ids_for_channel(
144144

145145
/// POST `/v5/campaign`
146146
///
147-
/// Request body (json): [`CreateCampaign`](`primitives::sentry::campaign_create::CreateCampaign`)
147+
/// Request body (json): [`CreateCampaign`](primitives::sentry::campaign_create::CreateCampaign)
148148
///
149-
/// Response: [Campaign](`primitives::Campaign`)
149+
/// Response: [`Campaign`](primitives::Campaign)
150150
pub async fn create_campaign<C>(
151151
req: Request<Body>,
152152
app: &Application<C>,
@@ -593,8 +593,6 @@ pub mod update_campaign {
593593

594594
pub mod insert_events {
595595

596-
use std::collections::HashMap;
597-
598596
use crate::{
599597
access::{self, check_access},
600598
analytics,
@@ -608,7 +606,7 @@ pub mod insert_events {
608606
use hyper::{Body, Request, Response};
609607
use primitives::{
610608
balances::{Balances, CheckedState, OverflowError},
611-
sentry::{Event, SuccessResponse},
609+
sentry::{Event, InsertEventsRequest, SuccessResponse},
612610
Address, Campaign, CampaignId, ChainOf, DomainError, UnifiedNum, ValidatorDesc,
613611
};
614612
use slog::{error, Logger};
@@ -642,15 +640,9 @@ pub mod insert_events {
642640

643641
/// POST `/v5/campaign/:id/events`
644642
///
645-
/// Request body (json):
646-
///
647-
/// ```json
648-
/// {
649-
/// "events": [[`Event`](`primitives::Event`)]
650-
/// }
651-
/// ```
643+
/// Request body (json): [`InsertEventsRequest`]
652644
///
653-
/// Response: [`SuccessResponse`](primitives::sentry::SuccessResponse)
645+
/// Response: [`SuccessResponse`]
654646
pub async fn handle_route<C: Locked + 'static>(
655647
req: Request<Body>,
656648
app: &Application<C>,
@@ -669,17 +661,13 @@ pub mod insert_events {
669661
.expect("request should have a Campaign loaded");
670662

671663
let body_bytes = hyper::body::to_bytes(req_body).await?;
672-
let mut request_body = serde_json::from_slice::<HashMap<String, Vec<Event>>>(&body_bytes)?;
673-
674-
let events = request_body
675-
.remove("events")
676-
.ok_or_else(|| ResponseError::BadRequest("invalid request".to_string()))?;
664+
let request_body = serde_json::from_slice::<InsertEventsRequest>(&body_bytes)?;
677665

678-
let processed = process_events(app, auth, session, campaign_context, events).await?;
666+
process_events(app, auth, session, campaign_context, request_body.events).await?;
679667

680668
Ok(Response::builder()
681669
.header("Content-type", "application/json")
682-
.body(serde_json::to_string(&SuccessResponse { success: processed })?.into())
670+
.body(serde_json::to_string(&SuccessResponse { success: true })?.into())
683671
.unwrap())
684672
}
685673

@@ -689,7 +677,7 @@ pub mod insert_events {
689677
session: &Session,
690678
campaign_context: &ChainOf<Campaign>,
691679
events: Vec<Event>,
692-
) -> Result<bool, ResponseError> {
680+
) -> Result<(), ResponseError> {
693681
let campaign = &campaign_context.context;
694682

695683
// handle events - check access
@@ -738,7 +726,7 @@ pub mod insert_events {
738726
events_success,
739727
);
740728

741-
Ok(true)
729+
Ok(())
742730
}
743731

744732
/// Max retries is `5` after which an error logging message will be recorded.

0 commit comments

Comments
 (0)