quick_responses/
quick_responses.rs

1use std::io;
2use std::net::TcpListener;
3use std::net::TcpStream;
4use std::thread;
5
6use rusty_http::Http;
7use rusty_http::Request;
8use rusty_http::Response;
9use rusty_http::StatusCode;
10
11const DIALOG_A_NOT_FOUND: &str = "
12    <h1>400 Bad Request</h1>
13    <p>Parameter 'a' not found</p>
14";
15
16const DIALOG_B_NOT_FOUND: &str = "
17    <h1>400 Bad Request</h1>
18    <p>Parameter 'b' not found</p>
19";
20
21const DIALOG_A_INVALID: &str = "
22    <h1>400 Bad Request</h1>
23    <p>Parameter 'a' can only be a number from 0 to 255</p>
24";
25
26const DIALOG_B_INVALID: &str = "
27    <h1>400 Bad Request</h1>
28    <p>Parameter 'b' can only be a number from 0 to 255</p>
29";
30
31fn add(request: Request, response: Response) -> io::Result<()> {
32    let Some(a) = request.params.get("a") else {
33        response.status_code(StatusCode::BadRequest)
34                .html(&DIALOG_A_NOT_FOUND)?;
35        
36        return Ok(());
37    };
38
39    let Some(b) = request.params.get("b") else {
40        response.status_code(StatusCode::BadRequest)
41                .html(&DIALOG_B_NOT_FOUND)?;
42        
43        return Ok(());
44    };
45
46    let Ok(a) = a.parse::<u8>() else {
47        response.status_code(StatusCode::BadRequest)
48                .html(&DIALOG_A_INVALID)?;
49        
50        return Ok(());
51    };
52
53    let Ok(b) = b.parse::<u8>() else {
54        response.status_code(StatusCode::BadRequest)
55                .html(&DIALOG_B_INVALID)?;
56        return Ok(());
57    };
58
59    let content = format!("<h1>{} + {} = {}</h1>", a, b, a as u16 + b as u16);
60
61    response.html(content)?;
62
63    Ok(())
64}
65
66fn sub(request: Request, response: Response) -> io::Result<()> {
67    let Some(a) = request.params.get("a") else {
68        response.status_code(StatusCode::BadRequest)
69                .html(&DIALOG_A_NOT_FOUND)?;
70        
71        return Ok(());
72    };
73
74    let Some(b) = request.params.get("b") else {
75        response.status_code(StatusCode::BadRequest)
76                .html(&DIALOG_B_NOT_FOUND)?;
77        
78        return Ok(());
79    };
80
81    let Ok(a) = a.parse::<u8>() else {
82        response.status_code(StatusCode::BadRequest)
83                .html(&DIALOG_A_INVALID)?;
84        
85        return Ok(());
86    };
87
88    let Ok(b) = b.parse::<u8>() else {
89        response.status_code(StatusCode::BadRequest)
90                .html(&DIALOG_B_INVALID)?;
91        return Ok(());
92    };
93
94    let content = format!("<h1>{} - {} = {}</h1>", a, b, a as i16 - b as i16);
95    
96    response.html(content)?;
97
98    Ok(())
99}
100
101fn not_found(request: Request, response: Response) -> io::Result<()> {
102    let content = format!("
103        <h1>400 Bad Request</h1>
104        <p>Page '{}' could not been found</p>
105    ", request.uri);
106
107    response.status_code(StatusCode::NotFound)
108            .html(content)?;
109
110    Ok(())
111}
112
113fn init_stream(stream: TcpStream) -> io::Result<()> {
114    let (request, response) = Http::from(stream)?;
115
116    match request.uri.as_str() {
117        "/add" => add(request, response)?,
118        "/sub" => sub(request, response)?,
119        _      => not_found(request, response)?
120    }
121
122    Ok(())
123}
124
125fn main() -> io::Result<()> {
126    let listener = TcpListener::bind("127.0.0.1:8080")?;
127
128    for stream in listener.incoming().filter_map(Result::ok) {
129        thread::spawn(|| init_stream(stream));
130    }
131
132    Ok(())
133}