forked from loafle/openapi-generator-original
[rust-server] Always derive Debug (#1404)
* Add test for file response * Always derive Debug Now that we're using a byte array, we can guarantee that deriving Debug will always work
This commit is contained in:
parent
dc3a3dd15a
commit
32b8d7fee7
@ -39,9 +39,7 @@ pub const BASE_PATH: &'static str = "{{{basePathWithoutHost}}}";
|
|||||||
pub const API_VERSION: &'static str = "{{{appVersion}}}";
|
pub const API_VERSION: &'static str = "{{{appVersion}}}";
|
||||||
|
|
||||||
{{#apiInfo}}{{#apis}}{{#operations}}{{#operation}}
|
{{#apiInfo}}{{#apis}}{{#operations}}{{#operation}}
|
||||||
{{^isResponseFile}}
|
|
||||||
#[derive(Debug, PartialEq)]
|
#[derive(Debug, PartialEq)]
|
||||||
{{/isResponseFile}}
|
|
||||||
pub enum {{{operationId}}}Response {
|
pub enum {{{operationId}}}Response {
|
||||||
{{#responses}}
|
{{#responses}}
|
||||||
{{#message}} /// {{{message}}}{{/message}}
|
{{#message}} /// {{{message}}}{{/message}}
|
||||||
|
@ -34,6 +34,14 @@ paths:
|
|||||||
description: Success
|
description: Success
|
||||||
schema:
|
schema:
|
||||||
type: string
|
type: string
|
||||||
|
/file_response:
|
||||||
|
get:
|
||||||
|
summary: Get a file
|
||||||
|
responses:
|
||||||
|
200:
|
||||||
|
description: Success
|
||||||
|
schema:
|
||||||
|
type: file
|
||||||
parameters:
|
parameters:
|
||||||
nested_response:
|
nested_response:
|
||||||
name: nested_response
|
name: nested_response
|
||||||
|
@ -57,6 +57,7 @@ To run a client, follow one of the following simple steps:
|
|||||||
```
|
```
|
||||||
cargo run --example client DummyGet
|
cargo run --example client DummyGet
|
||||||
cargo run --example client DummyPut
|
cargo run --example client DummyPut
|
||||||
|
cargo run --example client FileResponseGet
|
||||||
cargo run --example client HtmlPost
|
cargo run --example client HtmlPost
|
||||||
```
|
```
|
||||||
|
|
||||||
|
@ -48,6 +48,17 @@ paths:
|
|||||||
type: string
|
type: string
|
||||||
description: Success
|
description: Success
|
||||||
summary: Test HTML handling
|
summary: Test HTML handling
|
||||||
|
/file_response:
|
||||||
|
get:
|
||||||
|
responses:
|
||||||
|
200:
|
||||||
|
content:
|
||||||
|
'*/*':
|
||||||
|
schema:
|
||||||
|
format: binary
|
||||||
|
type: string
|
||||||
|
description: Success
|
||||||
|
summary: Get a file
|
||||||
components:
|
components:
|
||||||
requestBodies:
|
requestBodies:
|
||||||
nested_response:
|
nested_response:
|
||||||
|
@ -21,6 +21,7 @@ use rust_server_test::{ApiNoContext, ContextWrapperExt,
|
|||||||
ApiError,
|
ApiError,
|
||||||
DummyGetResponse,
|
DummyGetResponse,
|
||||||
DummyPutResponse,
|
DummyPutResponse,
|
||||||
|
FileResponseGetResponse,
|
||||||
HtmlPostResponse
|
HtmlPostResponse
|
||||||
};
|
};
|
||||||
use clap::{App, Arg};
|
use clap::{App, Arg};
|
||||||
@ -32,6 +33,7 @@ fn main() {
|
|||||||
.possible_values(&[
|
.possible_values(&[
|
||||||
"DummyGet",
|
"DummyGet",
|
||||||
"DummyPut",
|
"DummyPut",
|
||||||
|
"FileResponseGet",
|
||||||
"HtmlPost",
|
"HtmlPost",
|
||||||
])
|
])
|
||||||
.required(true)
|
.required(true)
|
||||||
@ -83,6 +85,11 @@ fn main() {
|
|||||||
println!("{:?} (X-Span-ID: {:?})", result, (client.context() as &Has<XSpanIdString>).get().clone());
|
println!("{:?} (X-Span-ID: {:?})", result, (client.context() as &Has<XSpanIdString>).get().clone());
|
||||||
},
|
},
|
||||||
|
|
||||||
|
Some("FileResponseGet") => {
|
||||||
|
let result = core.run(client.file_response_get());
|
||||||
|
println!("{:?} (X-Span-ID: {:?})", result, (client.context() as &Has<XSpanIdString>).get().clone());
|
||||||
|
},
|
||||||
|
|
||||||
Some("HtmlPost") => {
|
Some("HtmlPost") => {
|
||||||
let result = core.run(client.html_post("body_example".to_string()));
|
let result = core.run(client.html_post("body_example".to_string()));
|
||||||
println!("{:?} (X-Span-ID: {:?})", result, (client.context() as &Has<XSpanIdString>).get().clone());
|
println!("{:?} (X-Span-ID: {:?})", result, (client.context() as &Has<XSpanIdString>).get().clone());
|
||||||
|
@ -13,6 +13,7 @@ use swagger::{Has, XSpanIdString};
|
|||||||
use rust_server_test::{Api, ApiError,
|
use rust_server_test::{Api, ApiError,
|
||||||
DummyGetResponse,
|
DummyGetResponse,
|
||||||
DummyPutResponse,
|
DummyPutResponse,
|
||||||
|
FileResponseGetResponse,
|
||||||
HtmlPostResponse
|
HtmlPostResponse
|
||||||
};
|
};
|
||||||
use rust_server_test::models;
|
use rust_server_test::models;
|
||||||
@ -44,6 +45,13 @@ impl<C> Api<C> for Server<C> where C: Has<XSpanIdString>{
|
|||||||
Box::new(futures::failed("Generic failure".into()))
|
Box::new(futures::failed("Generic failure".into()))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Get a file
|
||||||
|
fn file_response_get(&self, context: &C) -> Box<Future<Item=FileResponseGetResponse, Error=ApiError>> {
|
||||||
|
let context = context.clone();
|
||||||
|
println!("file_response_get() - X-Span-ID: {:?}", context.get().0.clone());
|
||||||
|
Box::new(futures::failed("Generic failure".into()))
|
||||||
|
}
|
||||||
|
|
||||||
/// Test HTML handling
|
/// Test HTML handling
|
||||||
fn html_post(&self, body: String, context: &C) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>> {
|
fn html_post(&self, body: String, context: &C) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>> {
|
||||||
let context = context.clone();
|
let context = context.clone();
|
||||||
|
@ -41,6 +41,7 @@ use swagger::{ApiError, XSpanId, XSpanIdString, Has, AuthData};
|
|||||||
use {Api,
|
use {Api,
|
||||||
DummyGetResponse,
|
DummyGetResponse,
|
||||||
DummyPutResponse,
|
DummyPutResponse,
|
||||||
|
FileResponseGetResponse,
|
||||||
HtmlPostResponse
|
HtmlPostResponse
|
||||||
};
|
};
|
||||||
use models;
|
use models;
|
||||||
@ -369,6 +370,73 @@ if let Some(body) = body {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn file_response_get(&self, context: &C) -> Box<Future<Item=FileResponseGetResponse, Error=ApiError>> {
|
||||||
|
|
||||||
|
|
||||||
|
let uri = format!(
|
||||||
|
"{}/file_response",
|
||||||
|
self.base_path
|
||||||
|
);
|
||||||
|
|
||||||
|
let uri = match Uri::from_str(&uri) {
|
||||||
|
Ok(uri) => uri,
|
||||||
|
Err(err) => return Box::new(futures::done(Err(ApiError(format!("Unable to build URI: {}", err))))),
|
||||||
|
};
|
||||||
|
|
||||||
|
let mut request = hyper::Request::new(hyper::Method::Get, uri);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
request.headers_mut().set(XSpanId((context as &Has<XSpanIdString>).get().0.clone()));
|
||||||
|
|
||||||
|
|
||||||
|
Box::new(self.client_service.call(request)
|
||||||
|
.map_err(|e| ApiError(format!("No response received: {}", e)))
|
||||||
|
.and_then(|mut response| {
|
||||||
|
match response.status().as_u16() {
|
||||||
|
200 => {
|
||||||
|
let body = response.body();
|
||||||
|
Box::new(
|
||||||
|
body
|
||||||
|
.concat2()
|
||||||
|
.map_err(|e| ApiError(format!("Failed to read response: {}", e)))
|
||||||
|
.and_then(|body| str::from_utf8(&body)
|
||||||
|
.map_err(|e| ApiError(format!("Response was not valid UTF8: {}", e)))
|
||||||
|
.and_then(|body|
|
||||||
|
|
||||||
|
serde_json::from_str::<swagger::ByteArray>(body)
|
||||||
|
.map_err(|e| e.into())
|
||||||
|
|
||||||
|
))
|
||||||
|
.map(move |body|
|
||||||
|
FileResponseGetResponse::Success(body)
|
||||||
|
)
|
||||||
|
) as Box<Future<Item=_, Error=_>>
|
||||||
|
},
|
||||||
|
code => {
|
||||||
|
let headers = response.headers().clone();
|
||||||
|
Box::new(response.body()
|
||||||
|
.take(100)
|
||||||
|
.concat2()
|
||||||
|
.then(move |body|
|
||||||
|
future::err(ApiError(format!("Unexpected response code {}:\n{:?}\n\n{}",
|
||||||
|
code,
|
||||||
|
headers,
|
||||||
|
match body {
|
||||||
|
Ok(ref body) => match str::from_utf8(body) {
|
||||||
|
Ok(body) => Cow::from(body),
|
||||||
|
Err(e) => Cow::from(format!("<Body was not UTF8: {:?}>", e)),
|
||||||
|
},
|
||||||
|
Err(e) => Cow::from(format!("<Failed to read body: {}>", e)),
|
||||||
|
})))
|
||||||
|
)
|
||||||
|
) as Box<Future<Item=_, Error=_>>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}))
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
fn html_post(&self, param_body: String, context: &C) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>> {
|
fn html_post(&self, param_body: String, context: &C) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>> {
|
||||||
|
|
||||||
|
|
||||||
|
@ -51,6 +51,12 @@ pub enum DummyPutResponse {
|
|||||||
Success ,
|
Success ,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[derive(Debug, PartialEq)]
|
||||||
|
pub enum FileResponseGetResponse {
|
||||||
|
/// Success
|
||||||
|
Success ( swagger::ByteArray ) ,
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Debug, PartialEq)]
|
#[derive(Debug, PartialEq)]
|
||||||
pub enum HtmlPostResponse {
|
pub enum HtmlPostResponse {
|
||||||
/// Success
|
/// Success
|
||||||
@ -67,6 +73,9 @@ pub trait Api<C> {
|
|||||||
|
|
||||||
fn dummy_put(&self, inline_object: Option<models::InlineObject>, context: &C) -> Box<Future<Item=DummyPutResponse, Error=ApiError>>;
|
fn dummy_put(&self, inline_object: Option<models::InlineObject>, context: &C) -> Box<Future<Item=DummyPutResponse, Error=ApiError>>;
|
||||||
|
|
||||||
|
/// Get a file
|
||||||
|
fn file_response_get(&self, context: &C) -> Box<Future<Item=FileResponseGetResponse, Error=ApiError>>;
|
||||||
|
|
||||||
/// Test HTML handling
|
/// Test HTML handling
|
||||||
fn html_post(&self, body: String, context: &C) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>>;
|
fn html_post(&self, body: String, context: &C) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>>;
|
||||||
|
|
||||||
@ -81,6 +90,9 @@ pub trait ApiNoContext {
|
|||||||
|
|
||||||
fn dummy_put(&self, inline_object: Option<models::InlineObject>) -> Box<Future<Item=DummyPutResponse, Error=ApiError>>;
|
fn dummy_put(&self, inline_object: Option<models::InlineObject>) -> Box<Future<Item=DummyPutResponse, Error=ApiError>>;
|
||||||
|
|
||||||
|
/// Get a file
|
||||||
|
fn file_response_get(&self) -> Box<Future<Item=FileResponseGetResponse, Error=ApiError>>;
|
||||||
|
|
||||||
/// Test HTML handling
|
/// Test HTML handling
|
||||||
fn html_post(&self, body: String) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>>;
|
fn html_post(&self, body: String) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>>;
|
||||||
|
|
||||||
@ -110,6 +122,11 @@ impl<'a, T: Api<C>, C> ApiNoContext for ContextWrapper<'a, T, C> {
|
|||||||
self.api().dummy_put(inline_object, &self.context())
|
self.api().dummy_put(inline_object, &self.context())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Get a file
|
||||||
|
fn file_response_get(&self) -> Box<Future<Item=FileResponseGetResponse, Error=ApiError>> {
|
||||||
|
self.api().file_response_get(&self.context())
|
||||||
|
}
|
||||||
|
|
||||||
/// Test HTML handling
|
/// Test HTML handling
|
||||||
fn html_post(&self, body: String) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>> {
|
fn html_post(&self, body: String) -> Box<Future<Item=HtmlPostResponse, Error=ApiError>> {
|
||||||
self.api().html_post(body, &self.context())
|
self.api().html_post(body, &self.context())
|
||||||
|
@ -4,6 +4,10 @@ pub mod responses {
|
|||||||
use hyper::mime::*;
|
use hyper::mime::*;
|
||||||
|
|
||||||
// The macro is called per-operation to beat the recursion limit
|
// The macro is called per-operation to beat the recursion limit
|
||||||
|
/// Create Mime objects for the response content types for FileResponseGet
|
||||||
|
lazy_static! {
|
||||||
|
pub static ref FILE_RESPONSE_GET_SUCCESS: Mime = "*/*".parse().unwrap();
|
||||||
|
}
|
||||||
/// Create Mime objects for the response content types for HtmlPost
|
/// Create Mime objects for the response content types for HtmlPost
|
||||||
lazy_static! {
|
lazy_static! {
|
||||||
pub static ref HTML_POST_SUCCESS: Mime = "text/html".parse().unwrap();
|
pub static ref HTML_POST_SUCCESS: Mime = "text/html".parse().unwrap();
|
||||||
|
@ -39,6 +39,7 @@ use swagger::auth::Scopes;
|
|||||||
use {Api,
|
use {Api,
|
||||||
DummyGetResponse,
|
DummyGetResponse,
|
||||||
DummyPutResponse,
|
DummyPutResponse,
|
||||||
|
FileResponseGetResponse,
|
||||||
HtmlPostResponse
|
HtmlPostResponse
|
||||||
};
|
};
|
||||||
#[allow(unused_imports)]
|
#[allow(unused_imports)]
|
||||||
@ -54,11 +55,13 @@ mod paths {
|
|||||||
lazy_static! {
|
lazy_static! {
|
||||||
pub static ref GLOBAL_REGEX_SET: regex::RegexSet = regex::RegexSet::new(&[
|
pub static ref GLOBAL_REGEX_SET: regex::RegexSet = regex::RegexSet::new(&[
|
||||||
r"^/dummy$",
|
r"^/dummy$",
|
||||||
|
r"^/file_response$",
|
||||||
r"^/html$"
|
r"^/html$"
|
||||||
]).unwrap();
|
]).unwrap();
|
||||||
}
|
}
|
||||||
pub static ID_DUMMY: usize = 0;
|
pub static ID_DUMMY: usize = 0;
|
||||||
pub static ID_HTML: usize = 1;
|
pub static ID_FILE_RESPONSE: usize = 1;
|
||||||
|
pub static ID_HTML: usize = 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct NewService<T, C> {
|
pub struct NewService<T, C> {
|
||||||
@ -246,6 +249,60 @@ where
|
|||||||
},
|
},
|
||||||
|
|
||||||
|
|
||||||
|
// FileResponseGet - GET /file_response
|
||||||
|
&hyper::Method::Get if path.matched(paths::ID_FILE_RESPONSE) => {
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Box::new({
|
||||||
|
{{
|
||||||
|
|
||||||
|
Box::new(api_impl.file_response_get(&context)
|
||||||
|
.then(move |result| {
|
||||||
|
let mut response = Response::new();
|
||||||
|
response.headers_mut().set(XSpanId((&context as &Has<XSpanIdString>).get().0.to_string()));
|
||||||
|
|
||||||
|
match result {
|
||||||
|
Ok(rsp) => match rsp {
|
||||||
|
FileResponseGetResponse::Success
|
||||||
|
|
||||||
|
(body)
|
||||||
|
|
||||||
|
|
||||||
|
=> {
|
||||||
|
response.set_status(StatusCode::try_from(200).unwrap());
|
||||||
|
|
||||||
|
response.headers_mut().set(ContentType(mimetypes::responses::FILE_RESPONSE_GET_SUCCESS.clone()));
|
||||||
|
|
||||||
|
|
||||||
|
let body = serde_json::to_string(&body).expect("impossible to fail to serialize");
|
||||||
|
|
||||||
|
response.set_body(body);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Err(_) => {
|
||||||
|
// Application code returned an error. This should not happen, as the implementation should
|
||||||
|
// return a valid response.
|
||||||
|
response.set_status(StatusCode::InternalServerError);
|
||||||
|
response.set_body("An internal error occurred");
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
future::ok(response)
|
||||||
|
}
|
||||||
|
))
|
||||||
|
|
||||||
|
}}
|
||||||
|
}) as Box<Future<Item=Response, Error=Error>>
|
||||||
|
|
||||||
|
|
||||||
|
},
|
||||||
|
|
||||||
|
|
||||||
// HtmlPost - POST /html
|
// HtmlPost - POST /html
|
||||||
&hyper::Method::Post if path.matched(paths::ID_HTML) => {
|
&hyper::Method::Post if path.matched(paths::ID_HTML) => {
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user