feat(service): added authenticator arg

That will allow interaction between client and authentication attempts.
It also shows how cumbersome it is to deal with all these
generics ... but hey, you gotta do what you gotta do.

If boxes of pointers would be used, it would be easier to handle, but
enforces a certain memory model. That, of course, is not desired.
This commit is contained in:
Sebastian Thiel
2015-03-01 10:21:03 +01:00
parent 6fe9a5d8bf
commit f13c2960ab
4 changed files with 55 additions and 42 deletions

View File

@@ -1,16 +1,19 @@
#![feature(core)]
//!
//! # Usage
//!
//! ```test_harness
//! extern crate youtube3;
//! extern crate "youtube3-dev" as youtube3;
//! extern crate hyper;
//!
//! # #[test]
//! # fn test() {
//! let youtube = youtube3::new(hyper::Client::new());
//! youtube.videos();
//! # // TODO - generate !
//! # }
//! ```
extern crate hyper;
extern crate "rustc-serialize" as rustc_serialize;
extern crate "yup-oauth2" as oauth2;
use std::marker::PhantomData;
use std::borrow::BorrowMut;
@@ -21,48 +24,58 @@ pub mod videos;
/// Central instance to access all youtube related services
pub struct YouTube<C, NC> {
pub struct YouTube<C, NC, A> {
client: RefCell<C>,
auth: RefCell<A>,
_m: PhantomData<NC>
}
impl<'a, C, NC> YouTube<C, NC>
impl<'a, C, NC, A> YouTube<C, NC, A>
where NC: hyper::net::NetworkConnector,
C: BorrowMut<hyper::Client<NC>> + 'a {
C: BorrowMut<hyper::Client<NC>> + 'a,
A: oauth2::GetToken {
pub fn new(client: C) -> YouTube<C, NC> {
pub fn new(client: C, authenticator: A) -> YouTube<C, NC, A> {
YouTube {
client: RefCell::new(client),
auth: RefCell::new(authenticator),
_m: PhantomData,
}
}
pub fn videos(&'a self) -> videos::Service<'a, C, NC> {
videos::Service::new(&self.client)
pub fn videos(&'a self) -> videos::Service<'a, C, NC, A> {
videos::Service::new(&self.client, &self.auth)
}
}
pub fn new<C, NC>(client: C) -> YouTube<C, NC>
pub fn new<C, NC, A>(client: C, authenticator: A) -> YouTube<C, NC, A>
where NC: hyper::net::NetworkConnector,
C: BorrowMut<hyper::Client<NC>> {
YouTube::new(client)
C: BorrowMut<hyper::Client<NC>>,
A: oauth2::GetToken {
YouTube::new(client, authenticator)
}
#[cfg(test)]
mod tests {
use super::*;
use hyper;
use oauth2;
use std::default::Default;
#[test]
fn instantiate() {
let yt = YouTube::new(hyper::Client::new());
let v = yt.videos();
let secret = <oauth2::ApplicationSecret as Default>::default();
let auth = oauth2::Authenticator::new(
&secret,
oauth2::DefaultAuthenticatorDelegate,
hyper::Client::new(),
<oauth2::MemoryStorage as Default>::default(),
None);
let yt = YouTube::new(hyper::Client::new(), auth);
let mut c = hyper::Client::new();
let yt = YouTube::new(&mut c);
let v = yt.videos();
let v = yt.videos().insert("snippet", &Default::default());
}
}

View File

@@ -5,6 +5,7 @@ use std::marker::PhantomData;
use rustc_serialize;
use hyper;
use oauth2;
/// Reresents all aspects of a youtube video resource. May only be partially
/// available
@@ -69,29 +70,34 @@ pub struct GeoPoint {
}
/// The videos service - provides actual functionality through builders.
pub struct Service<'a, C, NC>
pub struct Service<'a, C, NC, A>
where NC: 'a,
C: 'a {
C: 'a,
A: 'a, {
client: &'a RefCell<C>,
auth: &'a RefCell<A>,
_m: PhantomData<NC>
}
impl<'a, C, NC> Service<'a, C, NC>
impl<'a, C, NC, A> Service<'a, C, NC, A>
where NC: hyper::net::NetworkConnector,
C: BorrowMut<hyper::Client<NC>> + 'a {
C: BorrowMut<hyper::Client<NC>> + 'a,
A: oauth2::GetToken + 'a {
pub fn new(client: &'a RefCell<C>) -> Service<'a, C, NC> {
pub fn new(client: &'a RefCell<C>, authenticator: &'a RefCell<A>) -> Service<'a, C, NC, A> {
Service {
client: client,
auth: authenticator,
_m: PhantomData,
}
}
pub fn insert(&self, parts: &str, video: &Video) -> VideosInsertBuilder<'a, C, NC> {
pub fn insert(&self, parts: &str, video: &Video) -> VideosInsertBuilder<'a, C, NC, A> {
VideosInsertBuilder {
client: self.client,
auth: self.auth,
video: video.clone(),
parts: parts.to_string(),
_m: PhantomData,
@@ -99,11 +105,13 @@ impl<'a, C, NC> Service<'a, C, NC>
}
}
pub struct VideosInsertBuilder<'a, C, NC>
pub struct VideosInsertBuilder<'a, C, NC, A>
where NC: 'a,
C: 'a {
C: 'a,
A: 'a {
client: &'a RefCell<C>,
auth: &'a RefCell<A>,
video: Video,
parts: String,
@@ -111,9 +119,10 @@ pub struct VideosInsertBuilder<'a, C, NC>
}
impl<'a, C, NC> VideosInsertBuilder<'a, C, NC>
impl<'a, C, NC, A> VideosInsertBuilder<'a, C, NC, A>
where NC: hyper::net::NetworkConnector,
C: BorrowMut<hyper::Client<NC>> + 'a {
C: BorrowMut<hyper::Client<NC>> + 'a,
A: oauth2::GetToken + 'a {
}
@@ -123,18 +132,5 @@ impl<'a, C, NC> VideosInsertBuilder<'a, C, NC>
mod tests {
use std::default::Default;
use super::*;
use hyper;
use std::cell::RefCell;
#[test]
fn insert() {
let c = RefCell::new(hyper::Client::new());
let s = Service::new(&c);
let v = <Video as Default>::default();
// todo: set data
let mut ib = s.insert("id, snippet", &v);
}
}