#[derive(Clone, Debug)]
pub enum UrlMatchingFunction
{
Url(SpecifiedUrl),
UrlPrefix(String),
Domain(String),
RegExp(String),
}
macro_rules! parse_quoted_or_unquoted_string
{
($input:ident, $url_matching_function:expr) =>
{
$input.parse_nested_block(|input|
{
let start = input.position();
input.parse_entirely(|input|
{
match input.next()
{
Ok(&Token::QuotedString(ref value)) => Ok($url_matching_function(value.as_ref().to_owned())),
Ok(t) => Err(BasicParseError::UnexpectedToken(t.clone()).into()),
Err(e) => Err(e.into()),
}
}).or_else(|_: ParseError<'i, CustomParseError<'i>>|
{
while let Ok(_) = input.next()
{
}
Ok($url_matching_function(input.slice_from(start).to_string()))
})
})
}
}
impl ToCss for UrlMatchingFunction
{
fn to_css<W: fmt::Write >(&self, dest: &mut W) -> fmt::Result
{
use self::UrlMatchingFunction::*;
match *self
{
Url(ref url) => url.to_css(dest),
UrlPrefix(ref url_prefix) =>
{
dest.write_str("url-prefix(")?;
serialize_string(url_prefix, dest)?;
dest.write_char(')')
},
Domain(ref domain) =>
{
dest.write_str("domain(")?;
serialize_string(domain, dest)?;
dest.write_char(')')
},
RegExp(ref regex) =>
{
dest.write_str("regexp(")?;
serialize_string(regex, dest)?;
dest.write_char(')')
},
}
}
}
impl UrlMatchingFunction
{
pub(crate) fn parse<'i, 't>(context: &ParserContext, input: &mut Parser<'i, 't>) -> Result<UrlMatchingFunction, ParseError<'i, CustomParseError<'i>>>
{
if input.try(|input| input.expect_function_matching("url-prefix")).is_ok()
{
parse_quoted_or_unquoted_string!(input, UrlMatchingFunction::UrlPrefix)
}
else if input.try(|input| input.expect_function_matching("domain")).is_ok()
{
parse_quoted_or_unquoted_string!(input, UrlMatchingFunction::Domain)
}
else if input.try(|input| input.expect_function_matching("regexp")).is_ok()
{
input.parse_nested_block(|input|
{
Ok(UrlMatchingFunction::RegExp(input.expect_string()?.as_ref().to_owned()))
})
}
else if let Ok(url) = input.try(|input| SpecifiedUrl::parse(context, input))
{
Ok(UrlMatchingFunction::Url(url))
}
else
{
Err(ParseError::Custom(CustomParseError::DocumentAtRuleUrlMatchingFunctionWasInvalid))
}
}
pub fn evaluate<D: Document>(&self, document: &D) -> bool
{
document.documentMatchesUrl(self)
}
}