1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
//! # effin - Rust client for Fuck Off As A Service
//!
//! https://www.foaas.com/
//!
//! A very non-idiomatic Rust implementation of a client of an
//! API that no one uses so I can waste more time in my life.
//!
//! # Example
//! ```rust
//! use effin::FoaasClient;
//! let fc = effin::FoaasClient::new();
//! let res_awesome = fc.awesome("John");
//! assert_eq!(res_awesome.unwrap().message, "This is Fucking Awesome.")
//! ```

#[allow(unused_imports)]
#[macro_use]
extern crate serde_json;
extern crate serde;

#[macro_use]
mod api;

use crate::api::{Operation, OperationResult};
use serde_json::Result;

/// Not sure why but this is defined here
/// maybe TODO for later
static API: &str = "http://www.foaas.com";

/// A FOAAS Client type
pub struct FoaasClient();

impl FoaasClient {
    /// Returns a client object to perform operations
    ///
    /// # Arguments
    /// None
    ///
    /// # Example
    /// ```rust
    /// use effin::FoaasClient;
    /// let fc = effin::FoaasClient::new();
    /// ```
    pub fn new() -> Self {
        Self {}
    }

    fn get_fq_url(&self, segment: &str) -> String {
        let fq: String = "".to_string();
        fq + &API + segment
    }

    fn call(&self, segment: &str) -> String {
        let client = reqwest::Client::new();
        let mut response = client
            .get(&self.get_fq_url(segment))
            .header(reqwest::header::ACCEPT, "application/json")
            .send()
            .expect("Failed to send request.");
        response.text().expect("Failed to read the response.")
    }

    fn operations(&self) -> Result<Vec<Operation>> {
        let resp = self.call("/operations");
        serde_json::from_str(&resp)
    }

    caller!(version);
    caller!(anyway, company: &str, from: &str);
    caller!(asshole, from: &str);
    caller!(awesome, from: &str);
    caller!(back, name: &str, from: &str);
    caller!(bag, from: &str);
    caller!(ballmer, name: &str, company: &str, from: &str);
    caller!(bday, name: &str, from: &str);
    caller!(because, from: &str);
    caller!(blackadder, name: &str, from: &str);
    caller!(bm, name: &str, from: &str);
    caller!(bucket, from: &str);
    caller!(bus, name: &str, from: &str);
    caller!(bye, from: &str);
    caller!(caniuse, tool: &str, from: &str);
    caller!(chainsaw, name: &str, from: &str);
    //TODO add more endpoints here
}

#[cfg(test)]
mod tests {
    #[test]
    fn uri_building() {
        let f = crate::FoaasClient::new();
        assert_eq!(f.get_fq_url("/version"), "http://www.foaas.com/version")
    }

    #[test]
    fn api_call() {
        // mocks/stubs for api checks?
        // what to use for real api calls, like some kind of integration checks?
        let f = crate::FoaasClient::new();
        let resp = f.call("/version");
        assert_eq!(resp.contains("2.0.0"), true)
    }

    #[test]
    fn ops() {
        let ops = crate::FoaasClient::new();
        let p = ops.operations();
        assert_eq!(p.is_ok(), true)
    }

    #[test]
    fn ops_with_endpoint() {
        let ops = crate::FoaasClient::new();
        let p = ops.operations().unwrap();
        assert_eq!(
            "/anyway/:company/:from",
            p.into_iter()
                .find(|x| x.name == "Who the fuck are you anyway")
                .unwrap()
                .url
        )
    }

    #[test]
    fn ballmer() {
        let b = crate::FoaasClient::new();
        let res = b.ballmer("John", "Apple", "Seed");
        assert_eq!(res.unwrap().message, "Fucking John is a fucking pussy. I\'m going to fucking bury that guy, I have done it before, and I will do it again. I\'m going to fucking kill Apple.")
    }

    #[test]
    fn ballmer_subtitle() {
        let b = crate::FoaasClient::new();
        let res = b.ballmer("John", "Apple", "Seed");
        assert_eq!(res.unwrap().subtitle, Some("- Seed".to_string()))
    }

    #[test]
    fn anyway() {
        let fc = crate::FoaasClient::new();
        let res_anyway = fc.anyway("Apple", "John");
        assert_eq!(res_anyway.unwrap().message, "Who the fuck are you anyway, Apple, why are you stirring up so much trouble, and, who pays you?")
    }

    #[test]
    fn asshole() {
        let fc = crate::FoaasClient::new();
        let res_asshole = fc.asshole("John");
        assert_eq!(res_asshole.unwrap().message, "Fuck you, asshole.")
    }

    #[test]
    fn awesome() {
        let fc = crate::FoaasClient::new();
        let res_awesome = fc.awesome("John");
        assert_eq!(res_awesome.unwrap().message, "This is Fucking Awesome.")
    }

    #[test]
    fn back() {
        let fc = crate::FoaasClient::new();
        let res_back = fc.back("Apple", "John");
        assert_eq!(res_back.unwrap().message, "Apple, back the fuck off.")
    }
}