Skip to content

Commit

Permalink
Update samples
Browse files Browse the repository at this point in the history
  • Loading branch information
richardwhiuk committed Aug 19, 2024
1 parent 6d909bc commit 6ae4634
Show file tree
Hide file tree
Showing 37 changed files with 4,763 additions and 28 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
Cargo.toml
README.md
api/openapi.yaml
bin/cli.rs
docs/MultipartRelatedRequest.md
docs/MultipartRequestObjectField.md
docs/MultipleIdenticalMimeTypesPostRequest.md
Expand Down
15 changes: 15 additions & 0 deletions samples/server/petstore/rust-server/output/multipart-v3/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@ server = [
"hyper_0_10", "mime_multipart", "swagger/multipart_related",
"serde_ignored", "hyper", "regex", "percent-encoding", "url", "lazy_static"
]
cli = [
"anyhow", "clap-verbosity-flag", "simple_logger", "structopt", "tokio"
]
conversion = ["frunk", "frunk_derives", "frunk_core", "frunk-enum-core", "frunk-enum-derive"]

[target.'cfg(any(target_os = "macos", target_os = "windows", target_os = "ios"))'.dependencies]
Expand Down Expand Up @@ -62,6 +65,13 @@ lazy_static = { version = "1.4", optional = true }
percent-encoding = {version = "2.1.0", optional = true}
regex = {version = "1.3", optional = true}

# CLI-specific
anyhow = { version = "1", optional = true }
clap-verbosity-flag = { version = "0.3", optional = true }
simple_logger = { version = "2.0", features = ["stderr"], optional = true }
structopt = { version = "0.3", optional = true }
tokio = { version = "0.2", features = ["rt-threaded", "macros", "stream"], optional = true }

# Conversion
frunk = { version = "0.4.0", optional = true }
frunk_derives = { version = "0.4.0", optional = true }
Expand Down Expand Up @@ -89,3 +99,8 @@ required-features = ["client"]
[[example]]
name = "server"
required-features = ["server"]

[[bin]]
name = "multipart-v3"
path = "bin/cli.rs"
required-features = ["client", "cli"]
27 changes: 27 additions & 0 deletions samples/server/petstore/rust-server/output/multipart-v3/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ This autogenerated project defines an API crate `multipart-v3` which contains:
* Data types representing the underlying data model.
* A `Client` type which implements `Api` and issues HTTP requests for each operation.
* A router which accepts HTTP requests and invokes the appropriate `Api` method for each operation.
* A CLI tool to drive basic API operations from the command line.

It also contains an example server and client which make use of `multipart-v3`:

Expand All @@ -36,6 +37,30 @@ It also contains an example server and client which make use of `multipart-v3`:
You can use the example server and client as a basis for your own code.
See below for [more detail on the examples](#using-the-generated-library).

## CLI

Run the included CLI tool with:

```
cargo run --bin cli --features=cli
```

To pass in arguments, put them after `--`, for example:

```
cargo run --bin cli --features=cli -- --help
```

See the help text for available options.

To build a standalone tool, use:

```
cargo build --bin cli --features=cli --release
```

You'll find the binary at `target/release/cli`.

## Examples

Run examples with:
Expand Down Expand Up @@ -88,6 +113,8 @@ The generated library has a few optional features that can be activated through
* The constructed client implements the API trait by making remote API call.
* `conversions`
* This defaults to disabled and creates extra derives on models to allow "transmogrification" between objects of structurally similar types.
* `cli`
* This defaults to disabled and is required for building the included CLI tool.

See https://doc.rust-lang.org/cargo/reference/manifest.html#the-features-section for how to use features in your `Cargo.toml`.

Expand Down
218 changes: 218 additions & 0 deletions samples/server/petstore/rust-server/output/multipart-v3/bin/cli.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,218 @@
//! CLI tool driving the API client
use anyhow::{anyhow, Context, Result};
use log::{debug, info};
// models may be unused if all inputs are primitive types
#[allow(unused_imports)]
use multipart_v3::{
models, ApiNoContext, Client, ContextWrapperExt,
MultipartRelatedRequestPostResponse,
MultipartRequestPostResponse,
MultipleIdenticalMimeTypesPostResponse,
};
use simple_logger::SimpleLogger;
use structopt::StructOpt;
use swagger::{AuthData, ContextBuilder, EmptyContext, Push, XSpanIdString};

type ClientContext = swagger::make_context_ty!(
ContextBuilder,
EmptyContext,
Option<AuthData>,
XSpanIdString
);

#[derive(StructOpt, Debug)]
#[structopt(
name = "Multipart OpenAPI V3 Rust Server Test",
version = "1.0.7",
about = "CLI access to Multipart OpenAPI V3 Rust Server Test"
)]
struct Cli {
#[structopt(subcommand)]
operation: Operation,

/// Address or hostname of the server hosting this API, including optional port
#[structopt(short = "a", long, default_value = "http://localhost")]
server_address: String,

/// Path to the client private key if using client-side TLS authentication
#[cfg(not(any(target_os = "macos", target_os = "windows", target_os = "ios")))]
#[cfg(feature = "client-tls")]
#[structopt(long, requires_all(&["client-certificate", "server-certificate"]))]
client_key: Option<String>,

/// Path to the client's public certificate associated with the private key
#[cfg(not(any(target_os = "macos", target_os = "windows", target_os = "ios")))]
#[cfg(feature = "client-tls")]
#[structopt(long, requires_all(&["client-key", "server-certificate"]))]
client_certificate: Option<String>,

/// Path to CA certificate used to authenticate the server
#[cfg(not(any(target_os = "macos", target_os = "windows", target_os = "ios")))]
#[cfg(feature = "client-tls")]
#[structopt(long)]
server_certificate: Option<String>,

/// If set, write output to file instead of stdout
#[structopt(short, long)]
output_file: Option<String>,

#[structopt(flatten)]
verbosity: clap_verbosity_flag::Verbosity,
}

#[derive(StructOpt, Debug)]
enum Operation {
MultipartRelatedRequestPost {
#[structopt(parse(try_from_str = parse_json))]
required_binary_field: swagger::ByteArray,
#[structopt(parse(try_from_str = parse_json))]
object_field: Option<models::MultipartRequestObjectField>,
#[structopt(parse(try_from_str = parse_json))]
optional_binary_field: Option<swagger::ByteArray>,
},
MultipartRequestPost {
string_field: String,
#[structopt(parse(try_from_str = parse_json))]
binary_field: swagger::ByteArray,
optional_string_field: Option<String>,
#[structopt(parse(try_from_str = parse_json))]
object_field: Option<models::MultipartRequestObjectField>,
},
MultipleIdenticalMimeTypesPost {
#[structopt(parse(try_from_str = parse_json))]
binary1: Option<swagger::ByteArray>,
#[structopt(parse(try_from_str = parse_json))]
binary2: Option<swagger::ByteArray>,
},
}

#[cfg(not(any(target_os = "macos", target_os = "windows", target_os = "ios")))]
fn create_client(args: &Cli, context: ClientContext) -> Result<Box<dyn ApiNoContext<ClientContext>>> {
if args.client_certificate.is_some() {
debug!("Using mutual TLS");
let client = Client::try_new_https_mutual(
&args.server_address,
args.server_certificate.unwrap(),
args.client_key.unwrap(),
args.client_certificate.unwrap(),
)
.context("Failed to create HTTPS client")?;
Ok(Box::new(client.with_context(context)))
} else if args.server_certificate.is_some() {
debug!("Using TLS with pinned server certificate");
let client =
Client::try_new_https_pinned(&args.server_address, args.server_certificate.unwrap())
.context("Failed to create HTTPS client")?;
Ok(Box::new(client.with_context(context)))
} else {
debug!("Using client without certificates");
let client =
Client::try_new(&args.server_address).context("Failed to create HTTP(S) client")?;
Ok(Box::new(client.with_context(context)))
}
}

#[cfg(any(target_os = "macos", target_os = "windows", target_os = "ios"))]
fn create_client(args: &Cli, context: ClientContext) -> Result<Box<dyn ApiNoContext<ClientContext>>> {
let client =
Client::try_new(&args.server_address).context("Failed to create HTTP(S) client")?;
Ok(Box::new(client.with_context(context)))
}

#[tokio::main]
async fn main() -> Result<()> {
let args = Cli::from_args();
if let Some(log_level) = args.verbosity.log_level() {
SimpleLogger::new().with_level(log_level.to_level_filter()).init()?;
}

debug!("Arguments: {:?}", &args);

let auth_data: Option<AuthData> = None;

#[allow(trivial_casts)]
let context = swagger::make_context!(
ContextBuilder,
EmptyContext,
auth_data,
XSpanIdString::default()
);

let client = create_client(&args, context)?;

let result = match args.operation {
Operation::MultipartRelatedRequestPost {
required_binary_field,
object_field,
optional_binary_field,
} => {
info!("Performing a MultipartRelatedRequestPost request");

let result = client.multipart_related_request_post(
required_binary_field,
object_field,
optional_binary_field,
).await?;
debug!("Result: {:?}", result);

match result {
MultipartRelatedRequestPostResponse::OK
=> "OK\n".to_string()
,
}
}
Operation::MultipartRequestPost {
string_field,
binary_field,
optional_string_field,
object_field,
} => {
info!("Performing a MultipartRequestPost request");

let result = client.multipart_request_post(
string_field,
binary_field,
optional_string_field,
object_field,
).await?;
debug!("Result: {:?}", result);

match result {
MultipartRequestPostResponse::OK
=> "OK\n".to_string()
,
}
}
Operation::MultipleIdenticalMimeTypesPost {
binary1,
binary2,
} => {
info!("Performing a MultipleIdenticalMimeTypesPost request");

let result = client.multiple_identical_mime_types_post(
binary1,
binary2,
).await?;
debug!("Result: {:?}", result);

match result {
MultipleIdenticalMimeTypesPostResponse::OK
=> "OK\n".to_string()
,
}
}
};

if let Some(output_file) = args.output_file {
std::fs::write(output_file, result)?
} else {
println!("{}", result);
}
Ok(())
}

// May be unused if all inputs are primitive types
#[allow(dead_code)]
fn parse_json<'a, T: serde::de::Deserialize<'a>>(json_string: &'a str) -> Result<T> {
serde_json::from_str(json_string).map_err(|err| anyhow!("Error parsing input: {}", err))
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
Cargo.toml
README.md
api/openapi.yaml
bin/cli.rs
docs/OpGetRequest.md
docs/default_api.md
examples/ca.pem
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,9 @@ client = [
server = [
"serde_ignored", "hyper", "regex", "percent-encoding", "url", "lazy_static"
]
cli = [
"anyhow", "clap-verbosity-flag", "simple_logger", "structopt", "tokio"
]
conversion = ["frunk", "frunk_derives", "frunk_core", "frunk-enum-core", "frunk-enum-derive"]

[target.'cfg(any(target_os = "macos", target_os = "windows", target_os = "ios"))'.dependencies]
Expand Down Expand Up @@ -52,6 +55,13 @@ lazy_static = { version = "1.4", optional = true }
percent-encoding = {version = "2.1.0", optional = true}
regex = {version = "1.3", optional = true}

# CLI-specific
anyhow = { version = "1", optional = true }
clap-verbosity-flag = { version = "0.3", optional = true }
simple_logger = { version = "2.0", features = ["stderr"], optional = true }
structopt = { version = "0.3", optional = true }
tokio = { version = "0.2", features = ["rt-threaded", "macros", "stream"], optional = true }

# Conversion
frunk = { version = "0.4.0", optional = true }
frunk_derives = { version = "0.4.0", optional = true }
Expand Down Expand Up @@ -79,3 +89,8 @@ required-features = ["client"]
[[example]]
name = "server"
required-features = ["server"]

[[bin]]
name = "no-example-v3"
path = "bin/cli.rs"
required-features = ["client", "cli"]
27 changes: 27 additions & 0 deletions samples/server/petstore/rust-server/output/no-example-v3/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ This autogenerated project defines an API crate `no-example-v3` which contains:
* Data types representing the underlying data model.
* A `Client` type which implements `Api` and issues HTTP requests for each operation.
* A router which accepts HTTP requests and invokes the appropriate `Api` method for each operation.
* A CLI tool to drive basic API operations from the command line.

It also contains an example server and client which make use of `no-example-v3`:

Expand All @@ -36,6 +37,30 @@ It also contains an example server and client which make use of `no-example-v3`:
You can use the example server and client as a basis for your own code.
See below for [more detail on the examples](#using-the-generated-library).

## CLI

Run the included CLI tool with:

```
cargo run --bin cli --features=cli
```

To pass in arguments, put them after `--`, for example:

```
cargo run --bin cli --features=cli -- --help
```

See the help text for available options.

To build a standalone tool, use:

```
cargo build --bin cli --features=cli --release
```

You'll find the binary at `target/release/cli`.

## Examples

Run examples with:
Expand Down Expand Up @@ -85,6 +110,8 @@ The generated library has a few optional features that can be activated through
* The constructed client implements the API trait by making remote API call.
* `conversions`
* This defaults to disabled and creates extra derives on models to allow "transmogrification" between objects of structurally similar types.
* `cli`
* This defaults to disabled and is required for building the included CLI tool.

See https://doc.rust-lang.org/cargo/reference/manifest.html#the-features-section for how to use features in your `Cargo.toml`.

Expand Down
Loading

0 comments on commit 6ae4634

Please sign in to comment.