فهرست منبع

Remove rust-encoding support

Simon Sapin 7 سال پیش
والد
کامیت
b567a51e78
7فایلهای تغییر یافته به همراه64 افزوده شده و 235 حذف شده
  1. 0 7
      Cargo.toml
  2. 0 127
      src/encoding.rs
  3. 12 68
      src/form_urlencoded.rs
  4. 7 26
      src/lib.rs
  5. 5 5
      src/parser.rs
  6. 38 0
      src/query_encoding.rs
  7. 2 2
      tests/unit.rs

+ 0 - 7
Cargo.toml

@@ -36,11 +36,7 @@ serde_json = "1.0"
 
 bencher = "0.1"
 
-[features]
-query_encoding = ["encoding"]
-
 [dependencies]
-encoding = {version = "0.2", optional = true}
 idna = { version = "0.1.0", path = "./idna" }
 matches = "0.1"
 percent-encoding = { version = "1.0.0", path = "./percent_encoding" }
@@ -49,6 +45,3 @@ serde = {version = "1.0", optional = true}
 [[bench]]
 name = "parse_url"
 harness = false
-
-[package.metadata.docs.rs]
-features = ["query_encoding"]

+ 0 - 127
src/encoding.rs

@@ -1,127 +0,0 @@
-// Copyright 2013-2014 The rust-url developers.
-//
-// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
-// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
-// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
-// option. This file may not be copied, modified, or distributed
-// except according to those terms.
-
-//! Abstraction that conditionally compiles either to rust-encoding,
-//! or to only support UTF-8.
-
-#[cfg(feature = "query_encoding")]
-extern crate encoding;
-
-use std::borrow::Cow;
-#[cfg(feature = "query_encoding")]
-use std::fmt::{self, Debug, Formatter};
-
-#[cfg(feature = "query_encoding")]
-use self::encoding::types::EncoderTrap;
-#[cfg(feature = "query_encoding")]
-pub use self::encoding::types::EncodingRef;
-
-#[cfg(feature = "query_encoding")]
-#[derive(Copy, Clone)]
-pub struct EncodingOverride {
-    /// `None` means UTF-8.
-    encoding: Option<EncodingRef>,
-}
-
-#[cfg(feature = "query_encoding")]
-impl EncodingOverride {
-    pub fn from_opt_encoding(encoding: Option<EncodingRef>) -> Self {
-        encoding.map(Self::from_encoding).unwrap_or_else(Self::utf8)
-    }
-
-    pub fn from_encoding(encoding: EncodingRef) -> Self {
-        EncodingOverride {
-            encoding: if encoding.name() == "utf-8" {
-                None
-            } else {
-                Some(encoding)
-            },
-        }
-    }
-
-    #[inline]
-    pub fn utf8() -> Self {
-        EncodingOverride { encoding: None }
-    }
-
-    /// https://encoding.spec.whatwg.org/#get-an-output-encoding
-    pub fn to_output_encoding(self) -> Self {
-        if let Some(encoding) = self.encoding {
-            if matches!(encoding.name(), "utf-16le" | "utf-16be") {
-                return Self::utf8();
-            }
-        }
-        self
-    }
-
-    pub fn name(&self) -> &'static str {
-        match self.encoding {
-            Some(encoding) => encoding.name(),
-            None => "utf-8",
-        }
-    }
-
-    pub fn encode<'a>(&self, input: Cow<'a, str>) -> Cow<'a, [u8]> {
-        match self.encoding {
-            // `encoding.encode` never returns `Err` when called with `EncoderTrap::NcrEscape`
-            Some(encoding) => Cow::Owned(encoding.encode(&input, EncoderTrap::NcrEscape).unwrap()),
-            None => encode_utf8(input),
-        }
-    }
-}
-
-#[cfg(feature = "query_encoding")]
-impl Debug for EncodingOverride {
-    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
-        write!(f, "EncodingOverride {{ encoding: ")?;
-        match self.encoding {
-            Some(e) => write!(f, "{} }}", e.name()),
-            None => write!(f, "None }}"),
-        }
-    }
-}
-
-#[cfg(not(feature = "query_encoding"))]
-#[derive(Copy, Clone, Debug)]
-pub struct EncodingOverride;
-
-#[cfg(not(feature = "query_encoding"))]
-impl EncodingOverride {
-    #[inline]
-    pub fn utf8() -> Self {
-        EncodingOverride
-    }
-
-    pub fn encode<'a>(&self, input: Cow<'a, str>) -> Cow<'a, [u8]> {
-        encode_utf8(input)
-    }
-}
-
-pub fn decode_utf8_lossy(input: Cow<[u8]>) -> Cow<str> {
-    match input {
-        Cow::Borrowed(bytes) => String::from_utf8_lossy(bytes),
-        Cow::Owned(bytes) => {
-            let raw_utf8: *const [u8];
-            match String::from_utf8_lossy(&bytes) {
-                Cow::Borrowed(utf8) => raw_utf8 = utf8.as_bytes(),
-                Cow::Owned(s) => return s.into(),
-            }
-            // from_utf8_lossy returned a borrow of `bytes` unchanged.
-            debug_assert!(raw_utf8 == &*bytes as *const [u8]);
-            // Reuse the existing `Vec` allocation.
-            unsafe { String::from_utf8_unchecked(bytes) }.into()
-        }
-    }
-}
-
-pub fn encode_utf8(input: Cow<str>) -> Cow<[u8]> {
-    match input {
-        Cow::Borrowed(s) => Cow::Borrowed(s.as_bytes()),
-        Cow::Owned(s) => Cow::Owned(s.into_bytes()),
-    }
-}

+ 12 - 68
src/form_urlencoded.rs

@@ -13,10 +13,9 @@
 //! Converts between a string (such as an URL’s query string)
 //! and a sequence of (name, value) pairs.
 
-use encoding::{decode_utf8_lossy, EncodingOverride};
 use percent_encoding::{percent_decode, percent_encode_byte};
+use query_encoding::{self, decode_utf8_lossy, EncodingOverride};
 use std::borrow::{Borrow, Cow};
-use std::fmt;
 use std::str;
 
 /// Convert a byte string in the `application/x-www-form-urlencoded` syntax
@@ -31,7 +30,7 @@ pub fn parse(input: &[u8]) -> Parse {
     Parse { input: input }
 }
 /// The return type of `parse()`.
-#[derive(Copy, Clone, Debug)]
+#[derive(Copy, Clone)]
 pub struct Parse<'a> {
     input: &'a [u8],
 }
@@ -91,7 +90,6 @@ impl<'a> Parse<'a> {
 }
 
 /// Like `Parse`, but yields pairs of `String` instead of pairs of `Cow<str>`.
-#[derive(Debug)]
 pub struct ParseIntoOwned<'a> {
     inner: Parse<'a>,
 }
@@ -161,20 +159,10 @@ impl<'a> Iterator for ByteSerialize<'a> {
 
 /// The [`application/x-www-form-urlencoded` serializer](
 /// https://url.spec.whatwg.org/#concept-urlencoded-serializer).
-#[derive(Debug)]
-pub struct Serializer<T: Target> {
+pub struct Serializer<'a, T: Target> {
     target: Option<T>,
     start_position: usize,
-    encoding: EncodingOverride,
-    custom_encoding: Option<SilentDebug<Box<dyn FnMut(&str) -> Cow<[u8]>>>>,
-}
-
-struct SilentDebug<T>(T);
-
-impl<T> fmt::Debug for SilentDebug<T> {
-    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
-        f.write_str("…")
-    }
+    encoding: EncodingOverride<'a>,
 }
 
 pub trait Target {
@@ -227,7 +215,7 @@ impl<'a> Target for ::UrlQuery<'a> {
     type Finished = &'a mut ::Url;
 }
 
-impl<T: Target> Serializer<T> {
+impl<'a, T: Target> Serializer<'a, T> {
     /// Create a new `application/x-www-form-urlencoded` serializer for the given target.
     ///
     /// If the target is non-empty,
@@ -246,8 +234,7 @@ impl<T: Target> Serializer<T> {
         Serializer {
             target: Some(target),
             start_position: start_position,
-            encoding: EncodingOverride::utf8(),
-            custom_encoding: None,
+            encoding: None,
         }
     }
 
@@ -260,18 +247,8 @@ impl<T: Target> Serializer<T> {
     }
 
     /// Set the character encoding to be used for names and values before percent-encoding.
-    #[cfg(feature = "query_encoding")]
-    pub fn encoding_override(&mut self, new: Option<::encoding::EncodingRef>) -> &mut Self {
-        self.encoding = EncodingOverride::from_opt_encoding(new).to_output_encoding();
-        self
-    }
-
-    /// Set the character encoding to be used for names and values before percent-encoding.
-    pub fn custom_encoding_override<F>(&mut self, encode: F) -> &mut Self
-    where
-        F: FnMut(&str) -> Cow<[u8]> + 'static,
-    {
-        self.custom_encoding = Some(SilentDebug(Box::new(encode)));
+    pub fn encoding_override(&mut self, new: EncodingOverride<'a>) -> &mut Self {
+        self.encoding = new;
         self
     }
 
@@ -283,7 +260,6 @@ impl<T: Target> Serializer<T> {
             string(&mut self.target),
             self.start_position,
             self.encoding,
-            &mut self.custom_encoding,
             name,
             value,
         );
@@ -312,7 +288,6 @@ impl<T: Target> Serializer<T> {
                     string,
                     self.start_position,
                     self.encoding,
-                    &mut self.custom_encoding,
                     k.as_ref(),
                     v.as_ref(),
                 );
@@ -321,26 +296,6 @@ impl<T: Target> Serializer<T> {
         self
     }
 
-    /// Add a name/value pair whose name is `_charset_`
-    /// and whose value is the character encoding’s name.
-    /// (See the `encoding_override()` method.)
-    ///
-    /// Panics if called after `.finish()`.
-    #[cfg(feature = "query_encoding")]
-    pub fn append_charset(&mut self) -> &mut Self {
-        assert!(
-            self.custom_encoding.is_none(),
-            "Cannot use both custom_encoding_override() and append_charset()"
-        );
-        {
-            let string = string(&mut self.target);
-            append_separator_if_needed(string, self.start_position);
-            string.push_str("_charset_=");
-            string.push_str(self.encoding.name());
-        }
-        self
-    }
-
     /// If this serializer was constructed with a string, take and return that string.
     ///
     /// ```rust
@@ -378,26 +333,15 @@ fn append_pair(
     string: &mut String,
     start_position: usize,
     encoding: EncodingOverride,
-    custom_encoding: &mut Option<SilentDebug<Box<dyn FnMut(&str) -> Cow<[u8]>>>>,
     name: &str,
     value: &str,
 ) {
     append_separator_if_needed(string, start_position);
-    append_encoded(name, string, encoding, custom_encoding);
+    append_encoded(name, string, encoding);
     string.push('=');
-    append_encoded(value, string, encoding, custom_encoding);
+    append_encoded(value, string, encoding);
 }
 
-fn append_encoded(
-    s: &str,
-    string: &mut String,
-    encoding: EncodingOverride,
-    custom_encoding: &mut Option<SilentDebug<Box<dyn FnMut(&str) -> Cow<[u8]>>>>,
-) {
-    let bytes = if let Some(SilentDebug(ref mut custom)) = *custom_encoding {
-        custom(s)
-    } else {
-        encoding.encode(s.into())
-    };
-    string.extend(byte_serialize(&bytes));
+fn append_encoded(s: &str, string: &mut String, encoding: EncodingOverride) {
+    string.extend(byte_serialize(&query_encoding::encode(encoding, s.into())))
 }

+ 7 - 26
src/lib.rs

@@ -115,7 +115,6 @@ extern crate serde;
 #[macro_use]
 extern crate percent_encoding;
 
-use encoding::EncodingOverride;
 use host::HostInternal;
 use parser::{to_u32, Context, Parser, SchemeType};
 use percent_encoding::{
@@ -126,7 +125,7 @@ use std::borrow::Borrow;
 use std::cmp;
 #[cfg(feature = "serde")]
 use std::error::Error;
-use std::fmt::{self, Debug, Formatter, Write};
+use std::fmt::{self, Write};
 use std::hash;
 use std::mem;
 use std::net::IpAddr;
@@ -139,13 +138,14 @@ pub use origin::{OpaqueOrigin, Origin};
 pub use parser::{ParseError, SyntaxViolation};
 pub use path_segments::PathSegmentsMut;
 pub use slicing::Position;
+pub use query_encoding::EncodingOverride;
 
-mod encoding;
 mod host;
 mod origin;
 mod parser;
 mod path_segments;
 mod slicing;
+mod query_encoding;
 
 pub mod form_urlencoded;
 #[doc(hidden)]
@@ -181,7 +181,7 @@ pub struct Url {
 #[derive(Copy, Clone)]
 pub struct ParseOptions<'a> {
     base_url: Option<&'a Url>,
-    encoding_override: encoding::EncodingOverride,
+    encoding_override: EncodingOverride<'a>,
     violation_fn: Option<&'a dyn Fn(SyntaxViolation)>,
 }
 
@@ -194,14 +194,8 @@ impl<'a> ParseOptions<'a> {
 
     /// Override the character encoding of query strings.
     /// This is a legacy concept only relevant for HTML.
-    ///
-    /// `EncodingRef` is defined in [rust-encoding](https://github.com/lifthrasiir/rust-encoding).
-    ///
-    /// This method is only available if the `query_encoding`
-    /// [feature](http://doc.crates.io/manifest.html#the-features-section]) is enabled.
-    #[cfg(feature = "query_encoding")]
-    pub fn encoding_override(mut self, new: Option<encoding::EncodingRef>) -> Self {
-        self.encoding_override = EncodingOverride::from_opt_encoding(new).to_output_encoding();
+    pub fn encoding_override(mut self, new: EncodingOverride<'a>) -> Self {
+        self.encoding_override = new;
         self
     }
 
@@ -245,19 +239,6 @@ impl<'a> ParseOptions<'a> {
     }
 }
 
-impl<'a> Debug for ParseOptions<'a> {
-    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
-        write!(
-            f,
-            "ParseOptions {{ base_url: {:?}, encoding_override: {:?}, \
-             violation_fn: {:?} }}",
-            self.base_url,
-            self.encoding_override,
-            self.violation_fn.map(|_| "…")
-        )
-    }
-}
-
 impl Url {
     /// Parse an absolute URL from a string.
     ///
@@ -384,7 +365,7 @@ impl Url {
     pub fn options<'a>() -> ParseOptions<'a> {
         ParseOptions {
             base_url: None,
-            encoding_override: EncodingOverride::utf8(),
+            encoding_override: None,
             violation_fn: None,
         }
     }

+ 5 - 5
src/parser.rs

@@ -10,12 +10,12 @@ use std::error::Error;
 use std::fmt::{self, Formatter, Write};
 use std::str;
 
-use encoding::EncodingOverride;
 use host::{Host, HostInternal};
 use percent_encoding::{
     percent_encode, utf8_percent_encode, DEFAULT_ENCODE_SET, PATH_SEGMENT_ENCODE_SET,
     QUERY_ENCODE_SET, SIMPLE_ENCODE_SET, USERINFO_ENCODE_SET,
 };
+use query_encoding::EncodingOverride;
 use Url;
 
 define_encode_set! {
@@ -274,7 +274,7 @@ impl<'i> Iterator for Input<'i> {
 pub struct Parser<'a> {
     pub serialization: String,
     pub base_url: Option<&'a Url>,
-    pub query_encoding_override: EncodingOverride,
+    pub query_encoding_override: EncodingOverride<'a>,
     pub violation_fn: Option<&'a dyn Fn(SyntaxViolation)>,
     pub context: Context,
 }
@@ -305,7 +305,7 @@ impl<'a> Parser<'a> {
         Parser {
             serialization: serialization,
             base_url: None,
-            query_encoding_override: EncodingOverride::utf8(),
+            query_encoding_override: None,
             violation_fn: None,
             context: Context::Setter,
         }
@@ -1238,9 +1238,9 @@ impl<'a> Parser<'a> {
 
         let encoding = match &self.serialization[..scheme_end as usize] {
             "http" | "https" | "file" | "ftp" | "gopher" => self.query_encoding_override,
-            _ => EncodingOverride::utf8(),
+            _ => None,
         };
-        let query_bytes = encoding.encode(query.into());
+        let query_bytes = ::query_encoding::encode(encoding, &query);
         self.serialization
             .extend(percent_encode(&query_bytes, QUERY_ENCODE_SET));
         remaining

+ 38 - 0
src/query_encoding.rs

@@ -0,0 +1,38 @@
+// Copyright 2019 The rust-url developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+use std::borrow::Cow;
+
+pub type EncodingOverride<'a> = Option<&'a dyn Fn(&str) -> Cow<[u8]>>;
+
+pub(crate) fn encode<'a>(
+    encoding_override: EncodingOverride,
+    input: &'a str,
+) -> Cow<'a, [u8]> {
+    if let Some(o) = encoding_override {
+        return o(input);
+    }
+    input.as_bytes().into()
+}
+
+pub(crate) fn decode_utf8_lossy(input: Cow<[u8]>) -> Cow<str> {
+    match input {
+        Cow::Borrowed(bytes) => String::from_utf8_lossy(bytes),
+        Cow::Owned(bytes) => {
+            let raw_utf8: *const [u8];
+            match String::from_utf8_lossy(&bytes) {
+                Cow::Borrowed(utf8) => raw_utf8 = utf8.as_bytes(),
+                Cow::Owned(s) => return s.into(),
+            }
+            // from_utf8_lossy returned a borrow of `bytes` unchanged.
+            debug_assert!(raw_utf8 == &*bytes as *const [u8]);
+            // Reuse the existing `Vec` allocation.
+            unsafe { String::from_utf8_unchecked(bytes) }.into()
+        }
+    }
+}

+ 2 - 2
tests/unit.rs

@@ -321,9 +321,9 @@ fn test_form_serialize() {
 }
 
 #[test]
-fn form_urlencoded_custom_encoding_override() {
+fn form_urlencoded_encoding_override() {
     let encoded = form_urlencoded::Serializer::new(String::new())
-        .custom_encoding_override(|s| s.as_bytes().to_ascii_uppercase().into())
+        .encoding_override(Some(&|s| s.as_bytes().to_ascii_uppercase().into()))
         .append_pair("foo", "bar")
         .finish();
     assert_eq!(encoded, "FOO=BAR");