Skip to main content

alpm_types/
file_type.rs

1//! File type handling.
2
3use std::str::FromStr;
4
5use alpm_parsers::{iter_str_context, traits::AlpmParser};
6#[cfg(feature = "serde")]
7use serde::{Deserialize, Serialize};
8use strum::{AsRefStr, Display, EnumString, IntoStaticStr, VariantNames};
9use winnow::{
10    Parser,
11    ascii::alpha1,
12    error::{ContextError, ErrMode, StrContext, StrContextValue},
13};
14
15/// The identifier of a file type used in ALPM.
16///
17/// These identifiers are used in the file names of file types such as binary packages (see
18/// [alpm-package]), source packages and repository sync databases (see alpm-repo-db).
19///
20/// [alpm-package]: https://alpm.archlinux.page/specifications/alpm-package.7.html
21#[derive(
22    AsRefStr, Clone, Copy, Debug, Display, EnumString, Eq, IntoStaticStr, PartialEq, VariantNames,
23)]
24#[cfg_attr(feature = "serde", derive(Deserialize, Serialize))]
25pub enum FileTypeIdentifier {
26    /// The identifier for [alpm-package] files.
27    ///
28    /// [alpm-package]: https://alpm.archlinux.page/specifications/alpm-package.7.html
29    #[cfg_attr(feature = "serde", serde(rename = "pkg"))]
30    #[strum(to_string = "pkg")]
31    BinaryPackage,
32
33    /// The identifier for alpm-repo-db files.
34    #[cfg_attr(feature = "serde", serde(rename = "db"))]
35    #[strum(to_string = "db")]
36    RepositorySyncDatabase,
37
38    /// The identifier for source package files.
39    #[cfg_attr(feature = "serde", serde(rename = "src"))]
40    #[strum(to_string = "src")]
41    SourcePackage,
42}
43
44impl AlpmParser for FileTypeIdentifier {
45    /// Recognizes a [`FileTypeIdentifier`] in a string slice.
46    ///
47    /// # Errors
48    ///
49    /// Returns an error if `input` does not begin with a valid variant
50    /// of a [`FileTypeIdentifier`].
51    fn parser(input: &mut &str) -> Result<Self, ErrMode<ContextError>> {
52        alpha1
53            .try_map(FileTypeIdentifier::from_str)
54            .context(StrContext::Label("file type identifier"))
55            .context_with(iter_str_context!([FileTypeIdentifier::VARIANTS]))
56            .parse_next(input)
57    }
58
59    fn delimiter_error_context<'a, O, P>(
60        parser: P,
61    ) -> impl Parser<&'a str, O, ErrMode<ContextError>>
62    where
63        P: Parser<&'a str, O, ErrMode<ContextError>>,
64    {
65        parser
66            .context(StrContext::Label("file type identifier"))
67            .context(StrContext::Expected(StrContextValue::Description(
68                "a string consisting of alphabetic characters",
69            )))
70    }
71}