Added Cookied as a response: can now set cookies. Added example of setting cookies. Working on retrieving them.

This commit is contained in:
Sergio Benitez 2016-08-06 23:14:05 -07:00
parent 55d5dd2b46
commit bceb1ecfb6
8 changed files with 163 additions and 1 deletions

View File

@ -0,0 +1,10 @@
[package]
name = "cookies"
version = "0.0.1"
authors = ["Sergio Benitez <sb@sergio.bz>"]
[dependencies]
rocket = { path = "../../lib" }
rocket_macros = { path = "../../macros" }
lazy_static = "*"
tera = { git = "https://github.com/Keats/tera" }

View File

@ -0,0 +1,16 @@
Rocket Todo Example
===================
Before running this example, you'll need to ensure there's a database file
present. You can do this with Diesel.
Running migration with Diesel
-----------------------------
Just run the following commands in your shell:
```
cargo install diesel_cli # installs the diesel CLI tools
DATABASE_URL=db/db.sql diesel migration run # create db/db.sql
```

View File

@ -0,0 +1,43 @@
#![feature(plugin, custom_derive, custom_attribute)]
#![plugin(rocket_macros)]
#[macro_use]
extern crate lazy_static;
extern crate rocket;
extern crate tera;
mod static_files;
use rocket::Rocket;
use rocket::response::{Cookied, Redirect};
lazy_static!(static ref TERA: tera::Tera = tera::Tera::new("templates/**/*"););
fn ctxt(message: Option<&str>) -> tera::Context {
let mut context = tera::Context::new();
context.add("have_message", &message.is_some());
context.add("message", &message.unwrap_or("").to_string());
context
}
#[derive(FromForm)]
struct Message {
message: String
}
#[route(POST, path = "/submit", form = "<message>")]
fn submit(message: Message) -> Cookied<Redirect> {
Cookied::new(Redirect::to("/")).add("message", &message.message)
}
#[route(GET, path = "/")]
fn index() -> tera::TeraResult<String> {
TERA.render("index.html", ctxt(None))
}
fn main() {
let mut rocket = Rocket::new("127.0.0.1", 8000);
rocket.mount("/", static_files::routes());
rocket.mount("/", routes![submit, index]);
rocket.launch();
}

View File

@ -0,0 +1,19 @@
use std::fs::File;
use std::io;
use rocket;
#[route(GET, path = "/<top>/<file>")]
fn all_level_one(top: &str, file: &str) -> io::Result<File> {
let file = format!("static/{}/{}", top, file);
File::open(file)
}
#[route(GET, path = "/<file>")]
fn all(file: &str) -> io::Result<File> {
let file = format!("static/{}", file);
File::open(file)
}
pub fn routes() -> Vec<rocket::Route> {
routes![all_level_one, all]
}

View File

@ -0,0 +1,22 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width" />
<title>Rocket: Cookie Examples</title>
</head>
<body>
<h1>Rocket Cookie Examples</h1>
{% if have_message %}
<p>{{ message }}</p>
{% else %}
<p>No message yet.</p>
{% endif %}
<form action="/submit" method="post" accept-charset="utf-8">
<textarea placeholder="Your message here..."
name="message" rows="10" cols="50"></textarea>
<p><input type="submit" value="Set Cookie"></p>
</form>
</body>
</html>

View File

@ -1,7 +1,7 @@
#! /usr/bin/env bash
SCRIPT_PATH=$(cd "$(dirname "$0")" ; pwd -P)
DATABASE_URL=${SCRIPT_PATH}/db/db.sql
DATABASE_URL=${SCRIPT_PATH}/db/db.sql
pushd $SCRIPT_PATH
# install the diesel CLI tools

View File

@ -0,0 +1,50 @@
use response::*;
use std::string::ToString;
use hyper::header::{SetCookie, CookiePair};
pub struct Cookied<R: Responder> {
cookies: Option<Vec<CookiePair>>,
responder: R
}
impl<R: Responder> Cookied<R> {
pub fn new(responder: R) -> Cookied<R> {
Cookied {
cookies: None,
responder: responder
}
}
pub fn with(responder: R, pairs: &[(&ToString, &ToString)]) -> Cookied<R> {
Cookied {
cookies: Some(
pairs.iter()
.map(|p| CookiePair::new(p.0.to_string(), p.1.to_string()))
.collect()
),
responder: responder
}
}
#[inline(always)]
pub fn add<A: ToString, B: ToString>(mut self, a: A, b: B) -> Self {
let new_pair = CookiePair::new(a.to_string(), b.to_string());
match self.cookies {
Some(ref mut pairs) => pairs.push(new_pair),
None => self.cookies = Some(vec![new_pair])
};
self
}
}
impl<R: Responder> Responder for Cookied<R> {
fn respond<'b>(&mut self, mut res: FreshHyperResponse<'b>) -> Outcome<'b> {
if let Some(pairs) = self.cookies.take() {
res.headers_mut().set(SetCookie(pairs));
}
self.responder.respond(res)
}
}

View File

@ -3,6 +3,7 @@ mod responder;
mod redirect;
mod with_status;
mod outcome;
mod cookied;
pub use hyper::server::Response as HyperResponse;
pub use hyper::net::Fresh as HyperFresh;
@ -15,6 +16,7 @@ pub use self::empty::{Empty, Forward};
pub use self::redirect::Redirect;
pub use self::with_status::StatusResponse;
pub use self::outcome::Outcome;
pub use self::cookied::Cookied;
use std::ops::{Deref, DerefMut};