#![forbid(unsafe_code)]
pub use sbol_core;
pub use sbol_rdf;
pub use sbol_rdf::{Graph as RdfGraph, Iri, Literal, RdfFormat, Resource, Term, Triple};
#[cfg(feature = "convert")]
pub use sbol_convert as convert;
#[cfg(feature = "v2")]
pub use sbol2 as v2;
#[cfg(feature = "v3")]
pub use sbol3 as v3;
const SBOL_V2_NS: &str = "http://sbols.org/v2#";
const SBOL_V3_NS: &str = "http://sbols.org/v3#";
#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
#[non_exhaustive]
pub enum SbolVersion {
V2,
V3,
}
pub fn detect_version_in_graph(graph: &RdfGraph) -> Option<SbolVersion> {
let mut saw_v2 = false;
for triple in graph.triples() {
if triple.predicate.as_str().starts_with(SBOL_V3_NS) {
return Some(SbolVersion::V3);
}
if let Some(iri) = triple.object.as_iri() {
if iri.as_str().starts_with(SBOL_V3_NS) {
return Some(SbolVersion::V3);
}
if iri.as_str().starts_with(SBOL_V2_NS) {
saw_v2 = true;
}
}
if triple.predicate.as_str().starts_with(SBOL_V2_NS) {
saw_v2 = true;
}
}
saw_v2.then_some(SbolVersion::V2)
}
pub fn detect_version(input: &str, format: RdfFormat) -> Option<SbolVersion> {
RdfGraph::parse(input, format)
.ok()
.and_then(|g| detect_version_in_graph(&g))
}
#[cfg(feature = "v3")]
#[non_exhaustive]
pub enum AnyDocument {
V3(v3::Document),
}
#[cfg(feature = "v3")]
impl AnyDocument {
pub fn version(&self) -> SbolVersion {
match self {
AnyDocument::V3(_) => SbolVersion::V3,
}
}
pub fn write(&self, format: RdfFormat) -> Result<String, v3::WriteError> {
match self {
AnyDocument::V3(d) => d.write(format),
}
}
pub fn as_v3(&self) -> Option<&v3::Document> {
match self {
AnyDocument::V3(d) => Some(d),
}
}
pub fn into_v3(self) -> Option<v3::Document> {
match self {
AnyDocument::V3(d) => Some(d),
}
}
}
#[cfg(feature = "v3")]
pub mod prelude {
pub use crate::v3::prelude::*;
pub use crate::{AnyDocument, SbolVersion, detect_version};
}