clockwork_http/state/
request.rs

1use super::Api;
2
3use {
4    crate::errors::ClockworkError,
5    anchor_lang::{prelude::*, AnchorDeserialize},
6    std::{
7        collections::HashMap,
8        convert::TryFrom,
9        fmt::{Display, Formatter},
10        str::FromStr,
11    },
12};
13
14pub const SEED_REQUEST: &[u8] = b"request";
15
16/**
17 * Request
18 */
19
20#[account]
21#[derive(Debug)]
22pub struct Request {
23    pub api: Pubkey,
24    pub caller: Pubkey,
25    pub created_at: u64,
26    pub fee_amount: u64,
27    pub headers: HashMap<String, String>,
28    pub id: String,
29    pub method: HttpMethod,
30    pub route: String,
31    pub url: String,
32    pub workers: Vec<Pubkey>,
33}
34
35impl Request {
36    pub fn pubkey(api: Pubkey, caller: Pubkey, id: String) -> Pubkey {
37        Pubkey::find_program_address(
38            &[
39                SEED_REQUEST,
40                api.as_ref(),
41                caller.as_ref(),
42                id.as_bytes().as_ref(),
43            ],
44            &crate::ID,
45        )
46        .0
47    }
48}
49
50impl TryFrom<Vec<u8>> for Request {
51    type Error = Error;
52    fn try_from(data: Vec<u8>) -> std::result::Result<Self, Self::Error> {
53        Request::try_deserialize(&mut data.as_slice())
54    }
55}
56
57/**
58 * RequestAccount
59 */
60
61pub trait RequestAccount {
62    fn new(
63        &mut self,
64        api: &Account<Api>,
65        caller: Pubkey,
66        created_at: u64,
67        fee_amount: u64,
68        headers: HashMap<String, String>,
69        id: String,
70        method: HttpMethod,
71        route: String,
72        workers: Vec<Pubkey>,
73    ) -> Result<()>;
74}
75
76impl RequestAccount for Account<'_, Request> {
77    fn new(
78        &mut self,
79        api: &Account<Api>,
80        caller: Pubkey,
81        created_at: u64,
82        fee_amount: u64,
83        headers: HashMap<String, String>,
84        id: String,
85        method: HttpMethod,
86        route: String,
87        workers: Vec<Pubkey>,
88    ) -> Result<()> {
89        self.api = api.key();
90        self.caller = caller;
91        self.created_at = created_at;
92        self.fee_amount = fee_amount;
93        self.headers = headers;
94        self.id = id;
95        self.method = method;
96        self.route = route.clone();
97        self.url = api.clone().base_url.to_owned() + route.as_str();
98        self.workers = workers;
99        Ok(())
100    }
101}
102
103/**
104 * HttpMethod
105 */
106
107#[derive(AnchorDeserialize, AnchorSerialize, Clone, Debug, PartialEq)]
108pub enum HttpMethod {
109    Get,
110    Post,
111}
112
113impl Display for HttpMethod {
114    fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
115        match *self {
116            HttpMethod::Get => write!(f, "GET"),
117            HttpMethod::Post => write!(f, "POST"),
118        }
119    }
120}
121
122impl FromStr for HttpMethod {
123    type Err = Error;
124
125    fn from_str(input: &str) -> std::result::Result<HttpMethod, Self::Err> {
126        match input.to_uppercase().as_str() {
127            "GET" => Ok(HttpMethod::Get),
128            "POST" => Ok(HttpMethod::Post),
129            _ => Err(ClockworkError::InvalidHttpMethod.into()),
130        }
131    }
132}