From 0a637859a2e0f0b2015cf567af3bfeab7bbd58da Mon Sep 17 00:00:00 2001 From: Bryan Newbold Date: Fri, 25 May 2018 18:00:59 -0700 Subject: file_release --- rust/fatcat-api/README.md | 2 +- rust/fatcat-api/api.yaml | 5 +++ rust/fatcat-api/api/swagger.yaml | 7 ++++ rust/fatcat-api/src/models.rs | 5 +++ rust/fatcat-openapi2.yml | 5 +++ rust/src/api_server.rs | 90 +++++++++++++++++++++++++++++++--------- rust/src/database_models.rs | 3 +- rust/src/database_schema.rs | 2 +- rust/tests/test_api_server.rs | 41 +++++++++++++++++- 9 files changed, 135 insertions(+), 25 deletions(-) (limited to 'rust') diff --git a/rust/fatcat-api/README.md b/rust/fatcat-api/README.md index e9ba065c..b67ad8f1 100644 --- a/rust/fatcat-api/README.md +++ b/rust/fatcat-api/README.md @@ -13,7 +13,7 @@ To see how to make this your own, look here: [README](https://github.com/swagger-api/swagger-codegen/blob/master/README.md) - API version: 0.1.0 -- Build date: 2018-05-25T21:11:43.744Z +- Build date: 2018-05-26T00:48:55.047Z This autogenerated project defines an API crate `fatcat` which contains: * An `Api` trait defining the API in Rust. diff --git a/rust/fatcat-api/api.yaml b/rust/fatcat-api/api.yaml index 827bb8d7..8dd4177f 100644 --- a/rust/fatcat-api/api.yaml +++ b/rust/fatcat-api/api.yaml @@ -121,6 +121,11 @@ definitions: type: string format: url example: "https://example.edu/~frau/prcding.pdf" + releases: + type: array + items: + type: string + #format: uuid release_entity: type: object required: diff --git a/rust/fatcat-api/api/swagger.yaml b/rust/fatcat-api/api/swagger.yaml index 6e37a5d6..ce85d813 100644 --- a/rust/fatcat-api/api/swagger.yaml +++ b/rust/fatcat-api/api/swagger.yaml @@ -1115,6 +1115,10 @@ definitions: file_entity: type: "object" properties: + releases: + type: "array" + items: + type: "string" url: type: "string" format: "url" @@ -1158,6 +1162,9 @@ definitions: editgroup_id: 16 state: "wip" url: "https://example.edu/~frau/prcding.pdf" + releases: + - "releases" + - "releases" revision: 42 upperCaseName: "FILE_ENTITY" release_entity: diff --git a/rust/fatcat-api/src/models.rs b/rust/fatcat-api/src/models.rs index 350e9698..8d3abe7d 100644 --- a/rust/fatcat-api/src/models.rs +++ b/rust/fatcat-api/src/models.rs @@ -327,6 +327,10 @@ impl ErrorResponse { #[derive(Debug, Clone, PartialEq, Serialize, Deserialize)] pub struct FileEntity { + #[serde(rename = "releases")] + #[serde(skip_serializing_if = "Option::is_none")] + pub releases: Option>, + #[serde(rename = "url")] #[serde(skip_serializing_if = "Option::is_none")] pub url: Option, @@ -368,6 +372,7 @@ pub struct FileEntity { impl FileEntity { pub fn new() -> FileEntity { FileEntity { + releases: None, url: None, sha1: None, size: None, diff --git a/rust/fatcat-openapi2.yml b/rust/fatcat-openapi2.yml index 827bb8d7..8dd4177f 100644 --- a/rust/fatcat-openapi2.yml +++ b/rust/fatcat-openapi2.yml @@ -121,6 +121,11 @@ definitions: type: string format: url example: "https://example.edu/~frau/prcding.pdf" + releases: + type: array + items: + type: string + #format: uuid release_entity: type: object required: diff --git a/rust/src/api_server.rs b/rust/src/api_server.rs index 19e33994..eee68e02 100644 --- a/rust/src/api_server.rs +++ b/rust/src/api_server.rs @@ -5,8 +5,8 @@ use api_helpers::*; use chrono; use database_models::*; use database_schema::{changelog, container_ident, container_rev, creator_ident, creator_rev, - editgroup, editor, file_ident, file_rev, release_ident, release_rev, - release_contrib, release_ref, work_ident, work_rev}; + editgroup, editor, file_ident, file_release, file_rev, release_contrib, + release_ident, release_ref, release_rev, work_ident, work_rev}; use diesel::prelude::*; use diesel::{self, insert_into}; use errors::*; @@ -209,10 +209,19 @@ impl Server { Err(e) => return Err(e.into()), }; + let releases: Vec = file_release::table + .filter(file_release::file_rev.eq(rev.id)) + .get_results(&conn) + .expect("fetch file releases") + .iter() + .map(|r: &FileReleaseRow| r.target_release_ident_id.to_string()) + .collect(); + let entity = FileEntity { sha1: rev.sha1, size: rev.size.map(|v| v as i64), url: rev.url, + releases: Some(releases), state: Some(ident.state().unwrap().shortname()), ident: Some(ident.id.to_string()), revision: ident.rev_id.map(|v| v), @@ -223,6 +232,7 @@ impl Server { Ok(Some(entity)) } + // TODO: refactor this to not be redundant with file_id_get_handler() code fn file_lookup_get_handler(&self, sha1: String) -> Result> { let conn = self.db_pool.get().expect("db_pool error"); @@ -239,10 +249,19 @@ impl Server { Err(e) => return Err(e.into()), }; + let releases: Vec = file_release::table + .filter(file_release::file_rev.eq(rev.id)) + .get_results(&conn) + .expect("fetch file releases") + .iter() + .map(|r: &FileReleaseRow| r.target_release_ident_id.to_string()) + .collect(); + let entity = FileEntity { sha1: rev.sha1, size: rev.size.map(|v| v as i64), url: rev.url, + releases: Some(releases), state: Some(ident.state().unwrap().shortname()), ident: Some(ident.id.to_string()), revision: ident.rev_id.map(|v| v), @@ -303,7 +322,7 @@ impl Server { .map(|r: &ReleaseRefRow| ReleaseRef { index: r.index.clone(), stub: r.stub.clone(), - target_release_id: r.target_release_ident_id.map(|v| v.to_string()) + target_release_id: r.target_release_ident_id.map(|v| v.to_string()), }) .collect(); @@ -367,7 +386,7 @@ impl Server { .map(|r: &ReleaseRefRow| ReleaseRef { index: r.index.clone(), stub: r.stub.clone(), - target_release_id: r.target_release_ident_id.map(|v| v.to_string()) + target_release_id: r.target_release_ident_id.map(|v| v.to_string()), }) .collect(); @@ -630,6 +649,29 @@ impl Api for Server { .unwrap(); let edit = &edit; + let _releases: Option> = match body.releases { + None => None, + Some(release_list) => { + if release_list.len() == 0 { + Some(vec![]) + } else { + let release_rows: Vec = release_list + .iter() + .map(|r| FileReleaseRow { + file_rev: edit.rev_id.unwrap(), + target_release_ident_id: + uuid::Uuid::parse_str(r).expect("valid UUID"), + }) + .collect(); + let release_rows: Vec = insert_into(file_release::table) + .values(release_rows) + .get_results(&conn) + .expect("error inserting file_releases"); + Some(release_rows) + } + } + }; + let entity_edit = EntityEdit { editgroup_id: Some(edit.editgroup_id), revision: Some(edit.rev_id.unwrap()), @@ -733,14 +775,18 @@ impl Api for Server { if ref_list.len() == 0 { Some(vec![]) } else { - let ref_rows: Vec = ref_list.iter().map(|r| ReleaseRefNewRow { - release_rev: edit.rev_id.unwrap(), - target_release_ident_id: - r.target_release_id.clone().map(|v| uuid::Uuid::parse_str(&v).expect("valid UUID")), - // XXX: index: r.index, - index: None, - stub: r.stub.clone(), - }).collect(); + let ref_rows: Vec = ref_list + .iter() + .map(|r| ReleaseRefNewRow { + release_rev: edit.rev_id.unwrap(), + target_release_ident_id: r.target_release_id + .clone() + .map(|v| uuid::Uuid::parse_str(&v).expect("valid UUID")), + // XXX: index: r.index, + index: None, + stub: r.stub.clone(), + }) + .collect(); let ref_rows: Vec = insert_into(release_ref::table) .values(ref_rows) .get_results(&conn) @@ -756,14 +802,18 @@ impl Api for Server { if contrib_list.len() == 0 { Some(vec![]) } else { - let contrib_rows: Vec = contrib_list.iter().map(|c| ReleaseContribNewRow { - release_rev: edit.rev_id.unwrap(), - creator_ident_id: - c.creator_id.clone().map(|v| uuid::Uuid::parse_str(&v).expect("valid UUID")), - // XXX: index: r.index, - contrib_type: c.contrib_type.clone(), - stub: c.creator_stub.clone(), - }).collect(); + let contrib_rows: Vec = contrib_list + .iter() + .map(|c| ReleaseContribNewRow { + release_rev: edit.rev_id.unwrap(), + creator_ident_id: c.creator_id + .clone() + .map(|v| uuid::Uuid::parse_str(&v).expect("valid UUID")), + // XXX: index: r.index, + contrib_type: c.contrib_type.clone(), + stub: c.creator_stub.clone(), + }) + .collect(); let contrib_rows: Vec = insert_into(release_contrib::table) .values(contrib_rows) .get_results(&conn) diff --git a/rust/src/database_models.rs b/rust/src/database_models.rs index 44b57f85..1b4841a0 100644 --- a/rust/src/database_models.rs +++ b/rust/src/database_models.rs @@ -187,10 +187,9 @@ pub struct ReleaseRefNewRow { pub stub: Option, } -#[derive(Debug, Queryable, Identifiable, Associations, AsChangeset)] +#[derive(Debug, Queryable, Insertable, Associations, AsChangeset)] #[table_name = "file_release"] pub struct FileReleaseRow { - pub id: i64, pub file_rev: i64, pub target_release_ident_id: Uuid, } diff --git a/rust/src/database_schema.rs b/rust/src/database_schema.rs index 3ccf5033..fcbd809c 100644 --- a/rust/src/database_schema.rs +++ b/rust/src/database_schema.rs @@ -215,8 +215,8 @@ joinable!(creator_ident -> creator_rev (rev_id)); joinable!(file_edit -> editgroup (editgroup_id)); joinable!(file_edit -> file_rev (rev_id)); joinable!(file_ident -> file_rev (rev_id)); -joinable!(file_release -> creator_ident (target_release_ident_id)); joinable!(file_release -> file_rev (file_rev)); +joinable!(file_release -> release_ident (target_release_ident_id)); joinable!(release_contrib -> creator_ident (creator_ident_id)); joinable!(release_contrib -> release_rev (release_rev)); joinable!(release_edit -> editgroup (editgroup_id)); diff --git a/rust/tests/test_api_server.rs b/rust/tests/test_api_server.rs index 5d4aaf1d..ac9a8dcc 100644 --- a/rust/tests/test_api_server.rs +++ b/rust/tests/test_api_server.rs @@ -78,6 +78,45 @@ fn test_post_container() { //assert!(body.contains("test journal")); } +#[test] +fn test_post_file() { + let server = fatcat::test_server().unwrap(); + let router = fatcat_api::router(server); + let mut headers = Headers::new(); + let mime: Mime = "application/json".parse().unwrap(); + headers.set(ContentType(mime)); + + let response = request::post( + "http://localhost:9411/v0/file", + headers.clone(), + r#"{ }"#, + &router, + ).unwrap(); + let status = response.status; + let body = response::extract_body_to_string(response); + println!("{}", body); + assert_eq!(status, Some(status::Created)); + + let response = request::post( + "http://localhost:9411/v0/file", + headers, + r#"{"size": 76543, + "sha1": "f013d66c7f6817d08b7eb2a93e6d0440c1f3e7f8", + "url": "http://archive.org/asdf.txt", + "releases": [ + "f1f046a3-45c9-4b99-4444-000000000001", + "f1f046a3-45c9-4b99-4444-000000000002" + ] + }"#, + &router, + ).unwrap(); + let status = response.status; + let body = response::extract_body_to_string(response); + println!("{}", body); + assert_eq!(status, Some(status::Created)); + //assert!(body.contains("secret paper")); +} + #[test] fn test_post_release() { let server = fatcat::test_server().unwrap(); @@ -85,7 +124,7 @@ fn test_post_release() { let mut headers = Headers::new(); let mime: Mime = "application/json".parse().unwrap(); headers.set(ContentType(mime)); - + let response = request::post( "http://localhost:9411/v0/release", headers.clone(), -- cgit v1.2.3