You've already forked flix
Throw away flix files in favor of a flix database
This commit is contained in:
@@ -0,0 +1,29 @@
|
||||
[package]
|
||||
name = "flix-model"
|
||||
version = "0.0.9"
|
||||
|
||||
categories = []
|
||||
description = "Core types for flix data"
|
||||
repository = "https://github.com/QuantumShade/flix"
|
||||
|
||||
authors.workspace = true
|
||||
edition.workspace = true
|
||||
license-file.workspace = true
|
||||
rust-version.workspace = true
|
||||
|
||||
[package.metadata.docs.rs]
|
||||
all-features = true
|
||||
rustdoc-args = ["--cfg", "docsrs"]
|
||||
|
||||
[lints]
|
||||
workspace = true
|
||||
|
||||
[features]
|
||||
default = []
|
||||
serde = ["dep:serde"]
|
||||
|
||||
[dependencies]
|
||||
seamantic = { workspace = true }
|
||||
|
||||
serde = { workspace = true, optional = true, features = ["std", "derive"] }
|
||||
thiserror = { workspace = true }
|
||||
@@ -0,0 +1,5 @@
|
||||
# flix-model
|
||||
|
||||
[](https://crates.io/crates/flix-model)
|
||||
|
||||
A library providing core types for flix data
|
||||
@@ -0,0 +1,26 @@
|
||||
//! This module contains types relating to flix media IDs
|
||||
|
||||
use seamantic::model::id::Id;
|
||||
|
||||
/// Type alias for the raw ID representation
|
||||
pub use seamantic::model::id::SeaOrmRepr as RawId;
|
||||
|
||||
#[doc(hidden)]
|
||||
pub enum Library {}
|
||||
/// Type alias for a library ID
|
||||
pub type LibraryId = Id<Library>;
|
||||
|
||||
#[doc(hidden)]
|
||||
pub enum Collection {}
|
||||
/// Type alias for a collection ID
|
||||
pub type CollectionId = Id<Collection>;
|
||||
|
||||
#[doc(hidden)]
|
||||
pub enum Movie {}
|
||||
/// Type alias for a movie ID
|
||||
pub type MovieId = Id<Movie>;
|
||||
|
||||
#[doc(hidden)]
|
||||
pub enum Show {}
|
||||
/// Type alias for a show ID
|
||||
pub type ShowId = Id<Show>;
|
||||
@@ -0,0 +1,6 @@
|
||||
//! flix-model provides core types for flix data
|
||||
|
||||
#![cfg_attr(docsrs, feature(doc_cfg))]
|
||||
|
||||
pub mod id;
|
||||
pub mod numbers;
|
||||
@@ -0,0 +1,78 @@
|
||||
//! This module contains season and episode numbers and related errors
|
||||
|
||||
use core::ops::RangeInclusive;
|
||||
use std::collections::HashSet;
|
||||
|
||||
/// Type alias for representing season numbers
|
||||
pub type SeasonNumber = u32;
|
||||
/// Type alias for representing episode numbers
|
||||
pub type EpisodeNumber = u32;
|
||||
|
||||
/// Potential errors when building EpisodeNumbers
|
||||
#[derive(Debug, thiserror::Error)]
|
||||
pub enum Error {
|
||||
/// There are no episodes
|
||||
#[error("zero episodes")]
|
||||
Zero,
|
||||
/// There are gaps in the episodes
|
||||
#[error("noncontiguous episodes")]
|
||||
Noncontiguous,
|
||||
}
|
||||
|
||||
/// A wrapper for handling single and multi-episode entries
|
||||
#[derive(Debug)]
|
||||
#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
|
||||
pub struct EpisodeNumbers(RangeInclusive<EpisodeNumber>);
|
||||
|
||||
impl TryFrom<&[EpisodeNumber]> for EpisodeNumbers {
|
||||
type Error = Error;
|
||||
|
||||
fn try_from(value: &[EpisodeNumber]) -> Result<Self, Self::Error> {
|
||||
match value {
|
||||
[] => Err(Error::Zero),
|
||||
[n] => Ok(Self(*n..=*n)),
|
||||
_ => {
|
||||
// min and max will always exist
|
||||
let min = value.iter().copied().min().unwrap_or_default();
|
||||
let max = value.iter().copied().max().unwrap_or_default();
|
||||
let len = value.len();
|
||||
|
||||
if usize::try_from(max.saturating_sub(min).saturating_add(1)) != Ok(len) {
|
||||
return Err(Error::Noncontiguous);
|
||||
}
|
||||
|
||||
let set: HashSet<_> = value.iter().copied().collect();
|
||||
if set.len() != len {
|
||||
return Err(Error::Noncontiguous);
|
||||
}
|
||||
|
||||
Ok(Self(min..=max))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl EpisodeNumbers {
|
||||
/// Get the range of episodes
|
||||
pub fn as_range(&self) -> &RangeInclusive<EpisodeNumber> {
|
||||
&self.0
|
||||
}
|
||||
}
|
||||
|
||||
// impl EpisodeNumbers {
|
||||
// /// Get the primary episode number of this episode
|
||||
// pub fn primary_episode_number(&self) -> Option<EpisodeNumber> {
|
||||
// match self {
|
||||
// EpisodeNumbers::Single { number } => Some(*number),
|
||||
// EpisodeNumbers::Multiple { numbers } => numbers.first().copied(),
|
||||
// }
|
||||
// }
|
||||
|
||||
// /// Get additional episode numbers of this episode
|
||||
// pub fn additional_episode_numbers(&self) -> &[EpisodeNumber] {
|
||||
// match self {
|
||||
// EpisodeNumbers::Single { number: _ } => &[],
|
||||
// EpisodeNumbers::Multiple { numbers } => numbers.get(1..).unwrap_or(&[]),
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
Reference in New Issue
Block a user