[librsvg: 2/5] Use data_url::mime::Mime instead of a String in BinaryData.mime_type
- From: Federico Mena Quintero <federico src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [librsvg: 2/5] Use data_url::mime::Mime instead of a String in BinaryData.mime_type
- Date: Wed, 17 Mar 2021 19:21:48 +0000 (UTC)
commit 6ace08acacd00db2d6e9a5b03224dcb32dcf792d
Author: Federico Mena Quintero <federico gnome org>
Date: Wed Mar 17 12:55:15 2021 -0600
Use data_url::mime::Mime instead of a String in BinaryData.mime_type
Types are good [citation needed].
src/css.rs | 9 +++++++--
src/document.rs | 14 ++++++++++----
src/io.rs | 29 +++++++++++++++++++++++------
3 files changed, 40 insertions(+), 12 deletions(-)
---
diff --git a/src/css.rs b/src/css.rs
index a577d419..2c98d648 100644
--- a/src/css.rs
+++ b/src/css.rs
@@ -78,6 +78,7 @@ use cssparser::{
CowRcStr, DeclarationListParser, DeclarationParser, Parser, ParserInput, QualifiedRuleParser,
RuleListParser, SourceLocation, ToCss, _cssparser_internal_to_lowercase,
};
+use data_url::mime::Mime;
use markup5ever::{namespace_url, ns, LocalName, Namespace, Prefix, QualName};
use selectors::attr::{AttrSelectorOperation, CaseSensitivity, NamespaceConstraint};
use selectors::matching::{ElementSelectorFlags, MatchingContext, MatchingMode, QuirksMode};
@@ -696,10 +697,10 @@ impl Stylesheet {
.and_then(|data| {
let BinaryData {
data: bytes,
- content_type,
+ mime_type,
} = data;
- if content_type.as_ref().map(String::as_ref) == Some("text/css") {
+ if is_text_css(&mime_type) {
Ok(bytes)
} else {
rsvg_log!("\"{}\" is not of type text/css; ignoring", aurl);
@@ -751,6 +752,10 @@ impl Stylesheet {
}
}
+fn is_text_css(mime_type: &Mime) -> bool {
+ mime_type.type_ == "text" && mime_type.subtype == "css"
+}
+
/// Runs the CSS cascade on the specified tree from all the stylesheets
pub fn cascade(
root: &mut Node,
diff --git a/src/document.rs b/src/document.rs
index dc106fd9..47e71ad6 100644
--- a/src/document.rs
+++ b/src/document.rs
@@ -1,5 +1,6 @@
//! Main SVG document structure.
+use data_url::mime::Mime;
use gdk_pixbuf::{PixbufLoader, PixbufLoaderExt};
use markup5ever::QualName;
use once_cell::sync::Lazy;
@@ -9,6 +10,7 @@ use std::collections::HashMap;
use std::fmt;
use std::include_str;
use std::rc::Rc;
+use std::str::FromStr;
use crate::css::{self, Origin, Stylesheet};
use crate::error::{AcquireError, AllowedUrlError, LoadingError, NodeIdError};
@@ -248,7 +250,7 @@ fn load_image(
) -> Result<SharedImageSurface, LoadingError> {
let BinaryData {
data: bytes,
- mut content_type,
+ mime_type,
} = io::acquire_data(&aurl, None)?;
if bytes.is_empty() {
@@ -260,9 +262,13 @@ fn load_image(
// Adobe Illustrator generate data: URLs without MIME-type for image
// data. We'll catch this and fall back to sniffing by unsetting the
// content_type.
- if content_type.as_deref() == Some("text/plain;charset=US-ASCII") {
- content_type = None;
- }
+ let unspecified_mime_type = Mime::from_str("text/plain;charset=US-ASCII").unwrap();
+
+ let content_type = if mime_type == unspecified_mime_type {
+ None
+ } else {
+ Some(format!("{}/{}", mime_type.type_, mime_type.subtype))
+ };
let loader = if let Some(ref content_type) = content_type {
PixbufLoader::new_with_mime_type(content_type)?
diff --git a/src/io.rs b/src/io.rs
index dbdf3dfd..bb787bbe 100644
--- a/src/io.rs
+++ b/src/io.rs
@@ -1,8 +1,10 @@
//! Utilities to acquire streams and data from from URLs.
+use data_url::{mime::Mime, DataUrl};
use gio::{Cancellable, File as GFile, FileExt, InputStream, MemoryInputStream};
use glib::{self, Bytes as GBytes, Cast};
use std::fmt;
+use std::str::FromStr;
use crate::url_resolver::AllowedUrl;
@@ -28,13 +30,21 @@ impl fmt::Display for IoError {
pub struct BinaryData {
pub data: Vec<u8>,
- pub content_type: Option<String>,
+ pub mime_type: Mime,
}
fn decode_data_uri(uri: &str) -> Result<BinaryData, IoError> {
- let data_url = data_url::DataUrl::process(uri).map_err(|_| IoError::BadDataUrl)?;
+ let data_url = DataUrl::process(uri).map_err(|_| IoError::BadDataUrl)?;
- let mime_type = data_url.mime_type().to_string();
+ let mime = data_url.mime_type();
+
+ // data_url::mime::Mime doesn't impl Clone, so do it by hand
+
+ let mime_type = Mime {
+ type_: mime.type_.clone(),
+ subtype: mime.subtype.clone(),
+ parameters: mime.parameters.clone(),
+ };
let (bytes, fragment_id) = data_url.decode_to_vec().map_err(|_| IoError::BadDataUrl)?;
@@ -49,7 +59,7 @@ fn decode_data_uri(uri: &str) -> Result<BinaryData, IoError> {
Ok(BinaryData {
data: bytes,
- content_type: Some(mime_type),
+ mime_type,
})
}
@@ -95,11 +105,18 @@ pub fn acquire_data(
let (contents, _etag) = file.load_contents(cancellable)?;
let (content_type, _uncertain) = gio::content_type_guess(Some(uri), &contents);
- let mime_type = gio::content_type_get_mime_type(&content_type).map(String::from);
+
+ let mime_type = if let Some(mime_type_str) = gio::content_type_get_mime_type(&content_type)
+ {
+ Mime::from_str(&mime_type_str)
+ .expect("gio::content_type_get_mime_type returned an invalid MIME-type!?")
+ } else {
+ Mime::from_str("application/octet-stream").unwrap()
+ };
Ok(BinaryData {
data: contents,
- content_type: mime_type.map(From::from),
+ mime_type,
})
}
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]