mirror of
https://github.com/deps-rs/deps.rs.git
synced 2024-11-22 10:26:30 +00:00
implement redirect for crate report
This commit is contained in:
parent
8939b41e32
commit
e0352539bd
3 changed files with 86 additions and 7 deletions
|
@ -9,6 +9,7 @@ use hyper::Client;
|
|||
use hyper::client::HttpConnector;
|
||||
use hyper_tls::HttpsConnector;
|
||||
use relative_path::{RelativePath, RelativePathBuf};
|
||||
use semver::VersionReq;
|
||||
use slog::Logger;
|
||||
use tokio_service::Service;
|
||||
|
||||
|
@ -136,6 +137,23 @@ impl Engine {
|
|||
})
|
||||
}
|
||||
|
||||
pub fn find_latest_crate_release(&self, name: CrateName, req: Option<VersionReq>) ->
|
||||
impl Future<Item=Option<CrateRelease>, Error=Error>
|
||||
{
|
||||
self.query_crate.call(name).from_err().map(move |query_response| {
|
||||
if let Some(vreq) = req {
|
||||
query_response.releases.iter()
|
||||
.filter(|release| vreq.matches(&release.version))
|
||||
.max_by(|r1, r2| r1.version.cmp(&r2.version))
|
||||
.cloned()
|
||||
} else {
|
||||
query_response.releases.iter()
|
||||
.max_by(|r1, r2| r1.version.cmp(&r2.version))
|
||||
.cloned()
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
fn fetch_releases<I: IntoIterator<Item=CrateName>>(&self, names: I) ->
|
||||
impl Iterator<Item=impl Future<Item=Vec<CrateRelease>, Error=Error>>
|
||||
{
|
||||
|
|
|
@ -1,8 +1,9 @@
|
|||
use std::env;
|
||||
use std::sync::Arc;
|
||||
|
||||
use futures::{Future, IntoFuture, future};
|
||||
use hyper::{Error as HyperError, Method, Request, Response, StatusCode};
|
||||
use hyper::header::ContentType;
|
||||
use hyper::header::{ContentType, Location};
|
||||
use route_recognizer::{Params, Router};
|
||||
use slog::Logger;
|
||||
use tokio_service::Service;
|
||||
|
@ -11,7 +12,7 @@ mod assets;
|
|||
mod views;
|
||||
|
||||
use ::engine::{Engine, AnalyzeDependenciesOutcome};
|
||||
use ::models::crates::CratePath;
|
||||
use ::models::crates::{CrateName, CratePath};
|
||||
use ::models::repo::RepoPath;
|
||||
use ::models::SubjectPath;
|
||||
|
||||
|
@ -31,6 +32,7 @@ enum Route {
|
|||
Index,
|
||||
Static(StaticFile),
|
||||
RepoStatus(StatusFormat),
|
||||
CrateRedirect,
|
||||
CrateStatus(StatusFormat)
|
||||
}
|
||||
|
||||
|
@ -53,6 +55,7 @@ impl Server {
|
|||
router.add("/repo/:site/:qual/:name", Route::RepoStatus(StatusFormat::Html));
|
||||
router.add("/repo/:site/:qual/:name/status.svg", Route::RepoStatus(StatusFormat::Svg));
|
||||
|
||||
router.add("/crate/:name", Route::CrateRedirect);
|
||||
router.add("/crate/:name/:version", Route::CrateStatus(StatusFormat::Html));
|
||||
router.add("/crate/:name/:version/status.svg", Route::CrateStatus(StatusFormat::Svg));
|
||||
|
||||
|
@ -86,6 +89,11 @@ impl Service for Server {
|
|||
return Box::new(self.crate_status(req, route_match.params, logger, format));
|
||||
}
|
||||
},
|
||||
&Route::CrateRedirect => {
|
||||
if *req.method() == Method::Get {
|
||||
return Box::new(self.crate_redirect(req, route_match.params, logger));
|
||||
}
|
||||
},
|
||||
&Route::Static(file) => {
|
||||
if *req.method() == Method::Get {
|
||||
return Box::new(future::ok(Server::static_file(file)));
|
||||
|
@ -156,6 +164,55 @@ impl Server {
|
|||
})
|
||||
}
|
||||
|
||||
fn crate_redirect(&self, _req: Request, params: Params, logger: Logger) ->
|
||||
impl Future<Item=Response, Error=HyperError>
|
||||
{
|
||||
let engine = self.engine.clone();
|
||||
|
||||
let name = params.find("name").expect("route param 'name' not found");
|
||||
|
||||
name.parse::<CrateName>().into_future().then(move |crate_name_result| {
|
||||
match crate_name_result {
|
||||
Err(err) => {
|
||||
error!(logger, "error: {}", err);
|
||||
let mut response = views::html::error::render("Could not parse crate name",
|
||||
"Please make sure to provide a valid crate name.");
|
||||
response.set_status(StatusCode::BadRequest);
|
||||
future::Either::A(future::ok(response))
|
||||
},
|
||||
Ok(crate_name) => {
|
||||
future::Either::B(engine.find_latest_crate_release(crate_name, None).then(move |release_result| {
|
||||
match release_result {
|
||||
Err(err) => {
|
||||
error!(logger, "error: {}", err);
|
||||
let mut response = views::html::error::render("Could not fetch crate information",
|
||||
"Please make sure to provide a valid crate name.");
|
||||
response.set_status(StatusCode::NotFound);
|
||||
future::ok(response)
|
||||
},
|
||||
Ok(None) => {
|
||||
let mut response = views::html::error::render("Could not fetch crate information",
|
||||
"Please make sure to provide a valid crate name.");
|
||||
response.set_status(StatusCode::NotFound);
|
||||
future::ok(response)
|
||||
},
|
||||
Ok(Some(release)) => {
|
||||
let mut response = Response::new();
|
||||
response.set_status(StatusCode::TemporaryRedirect);
|
||||
let url = format!("{}/crate/{}/{}",
|
||||
&SELF_BASE_URL as &str,
|
||||
release.name.as_ref(),
|
||||
release.version);
|
||||
response.headers_mut().set(Location::new(url));
|
||||
future::ok(response)
|
||||
}
|
||||
}
|
||||
}))
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
fn crate_status(&self, _req: Request, params: Params, logger: Logger, format: StatusFormat) ->
|
||||
impl Future<Item=Response, Error=HyperError>
|
||||
{
|
||||
|
@ -216,3 +273,10 @@ impl Server {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
lazy_static! {
|
||||
static ref SELF_BASE_URL: String = {
|
||||
env::var("BASE_URL")
|
||||
.unwrap_or_else(|_| "http://localhost:8080".to_string())
|
||||
};
|
||||
}
|
||||
|
|
|
@ -9,12 +9,9 @@ pub mod index;
|
|||
pub mod error;
|
||||
pub mod status;
|
||||
|
||||
lazy_static! {
|
||||
static ref SELF_BASE_URL: String = {
|
||||
env::var("BASE_URL")
|
||||
.unwrap_or_else(|_| "http://localhost:8080".to_string())
|
||||
};
|
||||
use super::super::SELF_BASE_URL;
|
||||
|
||||
lazy_static! {
|
||||
static ref GAUGES_SITE_ID: Option<String> = {
|
||||
env::var("GAUGES_SITE_ID").ok().map(|s| s.to_string())
|
||||
};
|
||||
|
|
Loading…
Reference in a new issue