syntastica_core/language_set/
union.rs1use std::borrow::Cow;
2
3use syntastica_highlight::HighlightConfiguration;
4use tft::FileType;
5
6use crate::Result;
7
8use super::{LanguageSet, SupportedLanguage};
9
10#[derive(Default)]
19pub struct Union<L, R> {
20 left: L,
21 right: R,
22}
23
24#[derive(Debug, Hash, PartialEq, Eq)]
28pub enum EitherLang<L, R> {
29 Left(L),
31
32 Right(R),
34}
35
36impl<L, R> Union<L, R> {
37 pub fn new(left: L, right: R) -> Self {
39 Self { left, right }
40 }
41
42 pub fn left(&self) -> &L {
44 &self.left
45 }
46
47 pub fn right(&self) -> &R {
49 &self.right
50 }
51}
52
53impl<'s, L, R> LanguageSet<'s> for Union<L, R>
54where
55 L: LanguageSet<'s>,
56 R: LanguageSet<'s>,
57{
58 type Language = EitherLang<L::Language, R::Language>;
59
60 fn get_language(&self, language: Self::Language) -> Result<&HighlightConfiguration> {
61 match language {
62 EitherLang::Left(lang) => self.left.get_language(lang),
63 EitherLang::Right(lang) => self.right.get_language(lang),
64 }
65 }
66}
67
68impl<L, R> From<L> for EitherLang<L, R> {
69 fn from(value: L) -> Self {
70 Self::Left(value)
71 }
72}
73
74impl<'set, L, R, S, T> SupportedLanguage<'set, Union<S, T>> for EitherLang<L, R>
75where
76 L: SupportedLanguage<'set, S>,
77 R: SupportedLanguage<'set, T>,
78{
79 fn name(&self) -> Cow<'_, str> {
80 match self {
81 EitherLang::Left(lang) => lang.name(),
82 EitherLang::Right(lang) => lang.name(),
83 }
84 }
85
86 fn for_name(name: impl AsRef<str>, set: &'set Union<S, T>) -> Result<Self> {
87 L::for_name(name.as_ref(), &set.left)
88 .map(Self::Left)
89 .or_else(|_| R::for_name(name, &set.right).map(Self::Right))
90 }
91
92 fn for_file_type(file_type: FileType, set: &'set Union<S, T>) -> Option<Self> {
93 L::for_file_type(file_type, &set.left)
94 .map(Self::Left)
95 .or_else(|| R::for_file_type(file_type, &set.right).map(Self::Right))
96 }
97
98 fn for_injection(name: impl AsRef<str>, set: &'set Union<S, T>) -> Option<Self> {
99 L::for_injection(name.as_ref(), &set.left)
100 .map(Self::Left)
101 .or_else(|| R::for_injection(name, &set.right).map(Self::Right))
102 }
103}