Skip to content

Commit d176a9a

Browse files
committed
chore: remove I/O functions to account for YAML optionality
1 parent 56f62e2 commit d176a9a

18 files changed

+145
-171
lines changed

crates/oas3/CHANGELOG.md

+10
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,16 @@
22

33
## Unreleased
44

5+
- Add new crate feature `yaml-spec` (on-by-default).
6+
- Add top-level `from_json()` function.
7+
- Add top-level `from_yaml()` function, guarded by the `yaml-spec` crate feature.
8+
- The top-level `to_json()` function now returns `serde_json` errors directly.
9+
- The top-level `to_yaml()` function now returns `serde_yaml` errors directly.
10+
- The top-level `to_yaml()` function is now guarded by the `yaml-spec` crate feature.
11+
- Remove top-level `from_reader()` function.
12+
- Remove top-level `from_path()` function.
13+
- Remove top-level `Error` type.
14+
515
## 0.14.0
616

717
- Implement `Default` for `spec::{Components, Contact, Example, Flows}`.

crates/oas3/Cargo.toml

+4-6
Original file line numberDiff line numberDiff line change
@@ -11,9 +11,8 @@ edition = { workspace = true }
1111
rust-version = { workspace = true }
1212

1313
[features]
14-
default = ["validation", "yaml_spec"]
15-
validation = []
16-
yaml_spec = ["dep:serde_yaml"]
14+
default = []
15+
yaml-spec = ["dep:serde_yaml"]
1716

1817
[dependencies]
1918
derive_more = { workspace = true, features = ["display", "error", "from"] }
@@ -33,9 +32,8 @@ indoc = { workspace = true }
3332
pretty_assertions = { workspace = true }
3433

3534
[[example]]
36-
name = "printers"
37-
path = "examples/printer.rs"
38-
required-features = ["yaml_spec"]
35+
name = "printer"
36+
required-features = ["yaml-spec"]
3937

4038
[lints]
4139
workspace = true

crates/oas3/README.md

+3-1
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,9 @@ specs in the older format.
2424
## Example
2525

2626
```rust
27-
match oas3::from_path("path/to/openapi.yml") {
27+
let yaml = std::fs::read_to_string("path/to/openapi.yml").unwrap();
28+
29+
match oas3::from_yaml(yaml) {
2830
Ok(spec) => println!("spec: {:?}", spec),
2931
Err(err) => println!("error: {}", err)
3032
}

crates/oas3/examples/printer.rs

+8-5
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,15 @@
11
//! Demonstrates reading an OpenAPI spec file and printing back to stdout.
22
3-
use std::env;
3+
use std::{env, fs};
44

55
fn main() -> eyre::Result<()> {
6-
if let Some(path) = env::args().nth(1) {
7-
let spec = oas3::from_path(path)?;
8-
println!("{}", oas3::to_yaml(&spec).unwrap());
9-
}
6+
let Some(path) = env::args().nth(1) else {
7+
return Ok(());
8+
};
9+
10+
let yaml = fs::read_to_string(path)?;
11+
let spec = oas3::from_yaml(yaml)?;
12+
println!("{}", oas3::to_yaml(&spec).unwrap());
1013

1114
Ok(())
1215
}

crates/oas3/src/error.rs

-28
This file was deleted.

crates/oas3/src/lib.rs

+32-48
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,9 @@
66
//! # Example
77
//!
88
//! ```no_run
9-
//! match oas3::from_path("path/to/openapi.yml") {
9+
//! let yaml = std::fs::read_to_string("path/to/openapi.yml").unwrap();
10+
//!
11+
//! match oas3::from_yaml(yaml) {
1012
//! Ok(spec) => println!("spec: {:?}", spec),
1113
//! Err(err) => println!("error: {}", err)
1214
//! }
@@ -17,12 +19,9 @@
1719
#![warn(missing_docs)]
1820
#![cfg_attr(docsrs, feature(doc_auto_cfg))]
1921

20-
use std::{fs::File, io::Read, path::Path};
21-
22-
mod error;
2322
pub mod spec;
2423

25-
pub use self::{error::Error, spec::Spec};
24+
pub use self::spec::Spec;
2625

2726
/// Version 3.1.0 of the OpenAPI specification.
2827
///
@@ -32,63 +31,48 @@ pub use self::{error::Error, spec::Spec};
3231
pub type OpenApiV3Spec = spec::Spec;
3332

3433
/// Try deserializing an OpenAPI spec (YAML or JSON) from a file, giving the path.
35-
///
36-
/// If the `yaml` feature flag is disabled only `JSON` specs are supported
37-
pub fn from_path<P>(path: P) -> Result<OpenApiV3Spec, Error>
38-
where
39-
P: AsRef<Path>,
40-
{
41-
from_reader(File::open(path)?)
34+
#[cfg(all(test, feature = "yaml-spec"))]
35+
pub(crate) fn from_path(
36+
path: impl AsRef<std::path::Path>,
37+
) -> std::io::Result<Result<OpenApiV3Spec, serde_yaml::Error>> {
38+
let file = std::fs::File::open(path.as_ref())?;
39+
Ok(from_reader(file))
4240
}
4341

4442
/// Try deserializing an OpenAPI spec (YAML or JSON) from a [`Read`] type.
45-
///
46-
/// If the `yaml` feature flag is disabled only `JSON` specs are supported
47-
pub fn from_reader<R>(read: R) -> Result<OpenApiV3Spec, Error>
48-
where
49-
R: Read,
50-
{
51-
#[cfg(feature = "yaml_spec")]
52-
{
53-
Ok(serde_yaml::from_reader::<R, OpenApiV3Spec>(read)?)
54-
}
55-
#[cfg(not(feature = "yaml_spec"))]
56-
{
57-
Ok(serde_json::from_reader::<R, OpenApiV3Spec>(read)?)
58-
}
43+
#[cfg(all(test, feature = "yaml-spec"))]
44+
pub(crate) fn from_reader(read: impl std::io::Read) -> Result<OpenApiV3Spec, serde_yaml::Error> {
45+
serde_yaml::from_reader::<_, OpenApiV3Spec>(read)
5946
}
6047

61-
/// Try deserializing an OpenAPI spec (YAML or JSON) from string.
62-
///
63-
/// If the `yaml` feature flag is disabled only `JSON` specs are supported
64-
pub fn from_str(val: impl AsRef<str>) -> Result<OpenApiV3Spec, Error> {
65-
#[cfg(feature = "yaml_spec")]
66-
{
67-
Ok(serde_yaml::from_str::<OpenApiV3Spec>(val.as_ref())?)
68-
}
69-
#[cfg(not(feature = "yaml_spec"))]
70-
{
71-
Ok(serde_json::from_str::<OpenApiV3Spec>(val.as_ref())?)
72-
}
48+
/// Deserializes an OpenAPI spec (YAML-format) from a string.
49+
#[cfg(feature = "yaml-spec")]
50+
pub fn from_yaml(yaml: impl AsRef<str>) -> Result<OpenApiV3Spec, serde_yaml::Error> {
51+
serde_yaml::from_str(yaml.as_ref())
52+
}
53+
54+
/// Deserializes an OpenAPI spec (JSON-format) from a string.
55+
pub fn from_json(json: impl AsRef<str>) -> Result<OpenApiV3Spec, serde_json::Error> {
56+
serde_json::from_str(json.as_ref())
7357
}
7458

75-
/// Try serializing to a YAML string.
76-
#[cfg(feature = "yaml_spec")]
77-
pub fn to_yaml(spec: &OpenApiV3Spec) -> Result<String, Error> {
78-
Ok(serde_yaml::to_string(spec)?)
59+
/// Serializes OpenAPI spec to a YAML string.
60+
#[cfg(feature = "yaml-spec")]
61+
pub fn to_yaml(spec: &OpenApiV3Spec) -> Result<String, serde_yaml::Error> {
62+
serde_yaml::to_string(spec)
7963
}
8064

81-
/// Try serializing to a JSON string.
82-
pub fn to_json(spec: &OpenApiV3Spec) -> Result<String, Error> {
83-
Ok(serde_json::to_string_pretty(spec)?)
65+
/// Serializes OpenAPI spec to a JSON string.
66+
pub fn to_json(spec: &OpenApiV3Spec) -> Result<String, serde_json::Error> {
67+
serde_json::to_string_pretty(spec)
8468
}
8569

86-
#[cfg(all(test, feature = "yaml_spec"))]
70+
#[cfg(all(test, feature = "yaml-spec"))]
8771
mod tests {
8872
use std::{
8973
fs::{self, read_to_string, File},
9074
io::Write,
91-
path,
75+
path::{self, Path},
9276
};
9377

9478
use pretty_assertions::assert_eq;
@@ -143,7 +127,7 @@ mod tests {
143127
// File -> `Spec` -> `serde_json::Value` -> `String`
144128

145129
// Parse the input file
146-
let parsed_spec = from_path(input_file).unwrap();
130+
let parsed_spec = from_path(input_file).unwrap().unwrap();
147131
// Convert to serde_json::Value
148132
let parsed_spec_json = serde_json::to_value(parsed_spec).unwrap();
149133
// Convert to a JSON string

crates/oas3/src/spec/discriminator.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ pub struct Discriminator {
2424
pub mapping: Option<BTreeMap<String, String>>,
2525
}
2626

27-
#[cfg(all(test, feature = "yaml_spec"))]
27+
#[cfg(all(test, feature = "yaml-spec"))]
2828
mod tests {
2929
use super::*;
3030

crates/oas3/src/spec/media_type_examples.rs

+1-6
Original file line numberDiff line numberDiff line change
@@ -81,9 +81,8 @@ impl MediaTypeExamples {
8181
}
8282
}
8383

84-
#[cfg(test)]
84+
#[cfg(all(test, feature = "yaml-spec"))]
8585
mod tests {
86-
#[cfg(feature = "yaml_spec")]
8786
use serde_json::json;
8887

8988
use super::*;
@@ -99,7 +98,6 @@ mod tests {
9998
}
10099

101100
#[test]
102-
#[cfg(feature = "yaml_spec")]
103101
fn deserialize() {
104102
assert_eq!(
105103
serde_yaml::from_str::<MediaTypeExamples>(indoc::indoc! {"
@@ -121,7 +119,6 @@ mod tests {
121119
}
122120

123121
#[test]
124-
#[cfg(feature = "yaml_spec")]
125122
fn serialize() {
126123
let mt_examples = MediaTypeExamples::default();
127124
assert_eq!(
@@ -143,7 +140,6 @@ mod tests {
143140
}
144141

145142
#[test]
146-
#[cfg(feature = "yaml_spec")]
147143
fn single_example() {
148144
let spec = serde_yaml::from_str::<Spec>(indoc::indoc! {"
149145
openapi: 3.1.0
@@ -171,7 +167,6 @@ paths: {}
171167
}
172168

173169
#[test]
174-
#[cfg(feature = "yaml_spec")]
175170
fn resolve_references() {
176171
let spec = serde_yaml::from_str::<Spec>(indoc::indoc! {"
177172
openapi: 3.1.0

crates/oas3/src/spec/mod.rs

-43
Original file line numberDiff line numberDiff line change
@@ -227,46 +227,3 @@ impl Spec {
227227
self.servers.first()
228228
}
229229
}
230-
231-
#[cfg(all(test, feature = "yaml_spec"))]
232-
mod tests {
233-
use pretty_assertions::assert_eq;
234-
235-
use super::*;
236-
237-
#[test]
238-
fn spec_extensions_deserialize() {
239-
let spec = indoc::indoc! {"
240-
openapi: '3.1.0'
241-
info:
242-
title: test
243-
version: v1
244-
components: {}
245-
x-bar: true
246-
qux: true
247-
"};
248-
249-
let spec = serde_yaml::from_str::<Spec>(spec).unwrap();
250-
assert!(spec.components.is_some());
251-
assert!(!spec.extensions.contains_key("x-bar"));
252-
assert!(!spec.extensions.contains_key("qux"));
253-
assert_eq!(spec.extensions.get("bar").unwrap(), true);
254-
}
255-
256-
#[test]
257-
fn spec_extensions_serialize() {
258-
let spec = indoc::indoc! {"
259-
openapi: 3.1.0
260-
info:
261-
title: test
262-
version: v1
263-
components: {}
264-
x-bar: true
265-
"};
266-
267-
let parsed_spec = serde_yaml::from_str::<Spec>(spec).unwrap();
268-
let round_trip_spec = serde_yaml::to_string(&parsed_spec).unwrap();
269-
270-
assert_eq!(spec, round_trip_spec);
271-
}
272-
}

crates/oas3/src/spec/parameter.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -223,7 +223,7 @@ impl FromRef for Parameter {
223223
}
224224
}
225225

226-
#[cfg(all(test, feature = "yaml_spec"))]
226+
#[cfg(all(test, feature = "yaml-spec"))]
227227
mod tests {
228228
use indoc::indoc;
229229

crates/oas3/src/spec/schema.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -593,7 +593,7 @@ where
593593
T::deserialize(de).map(Some)
594594
}
595595

596-
#[cfg(all(test, feature = "yaml_spec"))]
596+
#[cfg(all(test, feature = "yaml-spec"))]
597597
mod tests {
598598
use super::*;
599599

0 commit comments

Comments
 (0)