LCOV - code coverage report
Current view: top level - boost/url - url_view_base.hpp (source / functions) Hit Total Coverage
Test: coverage_filtered.info Lines: 84 84 100.0 %
Date: 2024-03-13 19:32:03 Functions: 26 27 96.3 %

          Line data    Source code
       1             : //
       2             : // Copyright (c) 2019 Vinnie Falco (vinnie.falco@gmail.com)
       3             : // Copyright (c) 2022 Alan de Freitas (alandefreitas@gmail.com)
       4             : //
       5             : // Distributed under the Boost Software License, Version 1.0. (See accompanying
       6             : // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
       7             : //
       8             : // Official repository: https://github.com/boostorg/url
       9             : //
      10             : 
      11             : #ifndef BOOST_URL_URL_VIEW_BASE_HPP
      12             : #define BOOST_URL_URL_VIEW_BASE_HPP
      13             : 
      14             : #include <boost/url/detail/config.hpp>
      15             : #include <boost/url/authority_view.hpp>
      16             : #include <boost/url/host_type.hpp>
      17             : #include <boost/url/ipv4_address.hpp>
      18             : #include <boost/url/ipv6_address.hpp>
      19             : #include <boost/url/params_view.hpp>
      20             : #include <boost/url/params_encoded_view.hpp>
      21             : #include <boost/url/pct_string_view.hpp>
      22             : #include <boost/url/scheme.hpp>
      23             : #include <boost/url/segments_encoded_view.hpp>
      24             : #include <boost/url/segments_view.hpp>
      25             : #include <boost/url/detail/url_impl.hpp>
      26             : #include <boost/url/grammar/string_token.hpp>
      27             : #include <boost/assert.hpp>
      28             : #include <cstddef>
      29             : #include <cstdint>
      30             : #include <iosfwd>
      31             : #include <memory>
      32             : #include <string>
      33             : #include <utility>
      34             : 
      35             : namespace boost {
      36             : namespace urls {
      37             : 
      38             : #ifndef BOOST_URL_DOCS
      39             : namespace detail {
      40             : struct pattern;
      41             : }
      42             : #endif
      43             : 
      44             : 
      45             : /** Common functionality for containers
      46             : 
      47             :     This base class is used by the library
      48             :     to provide common member functions for
      49             :     containers. This cannot be instantiated
      50             :     directly; Instead, use one of the
      51             :     containers or functions:
      52             : 
      53             :     @par Containers
      54             :         @li @ref url
      55             :         @li @ref url_view
      56             :         @li @ref static_url
      57             : 
      58             :     @par Functions
      59             :         @li @ref parse_absolute_uri
      60             :         @li @ref parse_origin_form
      61             :         @li @ref parse_relative_ref
      62             :         @li @ref parse_uri
      63             :         @li @ref parse_uri_reference
      64             : */
      65             : class BOOST_URL_DECL
      66             :     url_view_base
      67             :     : private detail::parts_base
      68             : {
      69             :     detail::url_impl impl_;
      70             :     detail::url_impl const* pi_;
      71             : 
      72             :     friend class url;
      73             :     friend class url_base;
      74             :     friend class url_view;
      75             :     friend class static_url_base;
      76             :     friend class params_base;
      77             :     friend class params_encoded_base;
      78             :     friend class params_encoded_ref;
      79             :     friend class params_encoded_view;
      80             :     friend class params_ref;
      81             :     friend class params_view;
      82             :     friend class segments_base;
      83             :     friend class segments_encoded_base;
      84             :     friend class segments_encoded_ref;
      85             :     friend class segments_encoded_view;
      86             :     friend class segments_ref;
      87             :     friend class segments_view;
      88             :     friend struct detail::pattern;
      89             : 
      90             :     struct shared_impl;
      91             : 
      92             :     url_view_base() noexcept;
      93             : 
      94             :     explicit url_view_base(
      95             :         detail::url_impl const&) noexcept;
      96             : 
      97             :     ~url_view_base() = default;
      98             : 
      99             :     url_view_base(
     100             :         url_view_base const& o) noexcept
     101             :         : impl_(o.impl_)
     102             :         , pi_(o.pi_)
     103             :     {
     104             :         if (pi_ == &o.impl_)
     105             :             pi_ = &impl_;
     106             :     }
     107             : 
     108             :     url_view_base& operator=(
     109             :         url_view_base const&) = delete;
     110             : 
     111             : #ifndef BOOST_URL_DOCS
     112             : public:
     113             : #endif
     114             :     std::size_t
     115             :     digest(std::size_t = 0) const noexcept;
     116             : 
     117             : public:
     118             :     //--------------------------------------------
     119             :     //
     120             :     // Observers
     121             :     //
     122             :     //--------------------------------------------
     123             : 
     124             :     /** Return the maximum number of characters possible
     125             : 
     126             :         This represents the largest number
     127             :         of characters that are theoretically
     128             :         possible to represent in a url,
     129             :         not including any null terminator.
     130             :         In practice the actual possible size
     131             :         may be lower than this number.
     132             : 
     133             :         @par Complexity
     134             :         Constant.
     135             : 
     136             :         @par Exception Safety
     137             :         Throws nothing.
     138             :     */
     139             :     static
     140             :     constexpr
     141             :     std::size_t
     142        8396 :     max_size() noexcept
     143             :     {
     144        8396 :         return BOOST_URL_MAX_SIZE;
     145             :     }
     146             : 
     147             :     /** Return the number of characters in the url
     148             : 
     149             :         This function returns the number of
     150             :         characters in the url's encoded string,
     151             :         not including any null terminator,
     152             :         if present.
     153             : 
     154             :         @par Example
     155             :         @code
     156             :         assert( url_view( "file:///Program%20Files" ).size() == 23 );
     157             :         @endcode
     158             : 
     159             :         @par Complexity
     160             :         Constant.
     161             : 
     162             :         @par Exception Safety
     163             :         Throws nothing.
     164             :     */
     165             :     std::size_t
     166       40682 :     size() const noexcept
     167             :     {
     168       40682 :         return pi_->offset(id_end);
     169             :     }
     170             : 
     171             :     /** Return true if the url is empty
     172             : 
     173             :         The empty string matches the
     174             :         <em>relative-ref</em> grammar.
     175             : 
     176             :         @par Example
     177             :         @code
     178             :         assert( url_view( "" ).empty() );
     179             :         @endcode
     180             : 
     181             :         @par Complexity
     182             :         Constant.
     183             : 
     184             :         @par Exception Safety
     185             :         Throws nothing.
     186             : 
     187             :         @par BNF
     188             :         @code
     189             :         relative-ref  = relative-part [ "?" query ] [ "#" fragment ]
     190             : 
     191             :         relative-part = "//" authority path-abempty
     192             :                       / path-absolute
     193             :                       / path-noscheme
     194             :                       / path-empty
     195             :         @endcode
     196             : 
     197             :         @par Specification
     198             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-4.2"
     199             :             >4.2.  Relative Reference (rfc3986)</a>
     200             :     */
     201             :     bool
     202          10 :     empty() const noexcept
     203             :     {
     204          10 :         return pi_->offset(id_end) == 0;
     205             :     }
     206             : 
     207             :     /** Return a pointer to the url's character buffer
     208             : 
     209             :         This function returns a pointer to
     210             :         the first character of the url, which
     211             :         is not guaranteed to be null-terminated.
     212             : 
     213             :         @par Complexity
     214             :         Constant.
     215             : 
     216             :         @par Exception Safety
     217             :         Throws nothing.
     218             :     */
     219             :     char const*
     220        4816 :     data() const noexcept
     221             :     {
     222        4816 :         return pi_->cs_;
     223             :     }
     224             : 
     225             :     /** Return the url string
     226             : 
     227             :         This function returns the entire url,
     228             :         which may contain percent escapes.
     229             : 
     230             :         @par Example
     231             :         @code
     232             :         assert( url_view( "http://www.example.com" ).buffer() == "http://www.example.com" );
     233             :         @endcode
     234             : 
     235             :         @par Complexity
     236             :         Constant.
     237             : 
     238             :         @par Exception Safety
     239             :         Throws nothing.
     240             :     */
     241             :     core::string_view
     242        1257 :     buffer() const noexcept
     243             :     {
     244        1257 :         return core::string_view(
     245        1257 :             data(), size());
     246             :     }
     247             : 
     248             :     /** Return the URL as a core::string_view
     249             : 
     250             :         @par Complexity
     251             :         Constant.
     252             : 
     253             :         @par Exception Safety
     254             :         Throws nothing.
     255             : 
     256             :     */
     257         250 :     operator core::string_view() const noexcept
     258             :     {
     259         250 :         return buffer();
     260             :     }
     261             : 
     262             :     /** Return a shared, persistent copy of the url
     263             : 
     264             :         This function returns a read-only copy of
     265             :         the url, with shared lifetime. The returned
     266             :         value owns (persists) the underlying string.
     267             :         The algorithm used to create the value
     268             :         minimizes the number of individual memory
     269             :         allocations, making it more efficient than
     270             :         when using direct standard library functions.
     271             : 
     272             :         @par Example
     273             :         @code
     274             :         std::shared_ptr< url_view const > sp;
     275             :         {
     276             :             std::string s( "http://example.com" );
     277             :             url_view u( s );                        // u references characters in s
     278             : 
     279             :             assert( u.data() == s.data() );         // same buffer
     280             : 
     281             :             sp = u.persist();
     282             : 
     283             :             assert( sp->data() != s.data() );       // different buffer
     284             :             assert( sp->buffer() == s);             // same contents
     285             : 
     286             :             // s is destroyed and thus u
     287             :             // becomes invalid, but sp remains valid.
     288             :         }
     289             :         @endcode
     290             : 
     291             :         @par Complexity
     292             :         Linear in `this->size()`.
     293             : 
     294             :         @par Exception Safety
     295             :         Calls to allocate may throw.
     296             :     */
     297             :     std::shared_ptr<
     298             :         url_view const> persist() const;
     299             : 
     300             :     //--------------------------------------------
     301             :     //
     302             :     // Scheme
     303             :     //
     304             :     //--------------------------------------------
     305             : 
     306             :     /** Return true a scheme is present
     307             : 
     308             :         This function returns true if this
     309             :         contains a scheme.
     310             : 
     311             :         @par Example
     312             :         @code
     313             :         assert( url_view( "http://www.example.com" ).has_scheme() );
     314             :         @endcode
     315             : 
     316             :         @par Complexity
     317             :         Constant.
     318             : 
     319             :         @par Exception Safety
     320             :         Throws nothing.
     321             : 
     322             :         @par BNF
     323             :         @code
     324             :         URI             = scheme ":" hier-part [ "?" query ] [ "#" fragment ]
     325             : 
     326             :         absolute-URI    = scheme ":" hier-part [ "?" query ]
     327             : 
     328             :         scheme          = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." )
     329             :         @endcode
     330             : 
     331             :         @par Specification
     332             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.1"
     333             :             >3.1. Scheme (rfc3986)</a>
     334             : 
     335             :         @see
     336             :             @ref scheme,
     337             :             @ref scheme_id.
     338             :     */
     339             :     bool
     340             :     has_scheme() const noexcept;
     341             : 
     342             :     /** Return the scheme
     343             : 
     344             :         This function returns the scheme if it
     345             :         exists, without a trailing colon (':').
     346             :         Otherwise it returns an empty string.
     347             :         Note that schemes are case-insensitive,
     348             :         and the canonical form is lowercased.
     349             : 
     350             :         @par Example
     351             :         @code
     352             :         assert( url_view( "http://www.example.com" ).scheme() == "http" );
     353             :         @endcode
     354             : 
     355             :         @par Exception Safety
     356             :         Throws nothing.
     357             : 
     358             :         @par BNF
     359             :         @code
     360             :         scheme          = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." )
     361             : 
     362             :         URI             = scheme ":" hier-part [ "?" query ] [ "#" fragment ]
     363             : 
     364             :         absolute-URI    = scheme ":" hier-part [ "?" query ]
     365             :         @endcode
     366             : 
     367             :         @par Specification
     368             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.1"
     369             :             >3.1. Scheme (rfc3986)</a>
     370             : 
     371             :         @see
     372             :             @ref has_scheme,
     373             :             @ref scheme_id.
     374             :     */
     375             :     core::string_view
     376             :     scheme() const noexcept;
     377             : 
     378             :     /** Return the scheme
     379             : 
     380             :         This function returns a value which
     381             :         depends on the scheme in the url:
     382             : 
     383             :         @li If the scheme is a well-known
     384             :         scheme, corresponding value from
     385             :         the enumeration @ref urls::scheme
     386             :         is returned.
     387             : 
     388             :         @li If a scheme is present but is not
     389             :         a well-known scheme, the value
     390             :         returned is @ref urls::scheme::unknown.
     391             : 
     392             :         @li Otherwise, if the scheme is absent
     393             :         the value returned is
     394             :         @ref urls::scheme::none.
     395             : 
     396             :         @par Example
     397             :         @code
     398             :         assert( url_view( "wss://www.example.com/crypto.cgi" ).scheme_id() == scheme::wss );
     399             :         @endcode
     400             : 
     401             :         @par Complexity
     402             :         Constant.
     403             : 
     404             :         @par Exception Safety
     405             :         Throws nothing.
     406             : 
     407             :         @par BNF
     408             :         @code
     409             :         URI             = scheme ":" hier-part [ "?" query ] [ "#" fragment ]
     410             : 
     411             :         absolute-URI    = scheme ":" hier-part [ "?" query ]
     412             : 
     413             :         scheme          = ALPHA *( ALPHA / DIGIT / "+" / "-" / "." )
     414             :         @endcode
     415             : 
     416             :         @par Specification
     417             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.1"
     418             :             >3.1. Scheme (rfc3986)</a>
     419             : 
     420             :         @see
     421             :             @ref has_scheme,
     422             :             @ref scheme.
     423             :     */
     424             :     urls::scheme
     425             :     scheme_id() const noexcept;
     426             : 
     427             :     //--------------------------------------------
     428             :     //
     429             :     // Authority
     430             :     //
     431             :     //--------------------------------------------
     432             : 
     433             :     /** Return true if an authority is present
     434             : 
     435             :         This function returns true if the url
     436             :         contains an authority. The presence of
     437             :         an authority is denoted by a double
     438             :         slash ("//") at the beginning or after
     439             :         the scheme.
     440             : 
     441             :         @par Example
     442             :         @code
     443             :         assert( url_view( "http://www.example.com/index.htm" ).has_authority() );
     444             :         @endcode
     445             : 
     446             :         @par Complexity
     447             :         Constant.
     448             : 
     449             :         @par Exception Safety
     450             :         Throws nothing.
     451             : 
     452             :         @par BNF
     453             :         @code
     454             :         authority       = [ userinfo "@" ] host [ ":" port ]
     455             : 
     456             :         URI             = scheme ":" hier-part [ "?" query ] [ "#" fragment ]
     457             : 
     458             :         absolute-URI    = scheme ":" hier-part [ "?" query ]
     459             : 
     460             :         URI-reference   = URI / relative-ref
     461             : 
     462             :         relative-ref    = relative-part [ "?" query ] [ "#" fragment ]
     463             : 
     464             :         hier-part       = "//" authority path-abempty
     465             :                         ; (more...)
     466             : 
     467             :         relative-part   = "//" authority path-abempty
     468             :                         ; (more...)
     469             : 
     470             :         @endcode
     471             : 
     472             :         @par Specification
     473             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2"
     474             :             >3.2. Authority (rfc3986)</a>
     475             : 
     476             :         @see
     477             :             @ref authority,
     478             :             @ref encoded_authority.
     479             :     */
     480             :     bool
     481        4791 :     has_authority() const noexcept
     482             :     {
     483        4791 :         return pi_->len(id_user) > 0;
     484             :     }
     485             : 
     486             :     /** Return the authority
     487             : 
     488             :         This function returns the authority as
     489             :         an @ref authority_view.
     490             : 
     491             :         @par Example
     492             :         @code
     493             :         authority_view a = url_view( "https://www.example.com:8080/index.htm" ).authority();
     494             :         @endcode
     495             : 
     496             :         @par Complexity
     497             :         Constant.
     498             : 
     499             :         @par Exception Safety
     500             :         Throws nothing.
     501             : 
     502             :         @par BNF
     503             :         @code
     504             :         authority   = [ userinfo "@" ] host [ ":" port ]
     505             :         @endcode
     506             : 
     507             :         @par Specification
     508             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2"
     509             :             >3.2. Authority (rfc3986)</a>
     510             : 
     511             :         @see
     512             :             @ref encoded_authority,
     513             :             @ref has_authority.
     514             :     */
     515             :     authority_view
     516             :     authority() const noexcept;
     517             : 
     518             :     /** Return the authority.
     519             : 
     520             :         If present, this function returns a
     521             :         string representing the authority (which
     522             :         may be empty).
     523             :         Otherwise it returns an empty string.
     524             :         The returned string may contain
     525             :         percent escapes.
     526             : 
     527             :         @par Example
     528             :         @code
     529             :         assert( url_view( "file://Network%20Drive/My%2DFiles" ).encoded_authority() == "Network%20Drive" );
     530             :         @endcode
     531             : 
     532             :         @par Complexity
     533             :         Constant.
     534             : 
     535             :         @par Exception Safety
     536             :         Throws nothing.
     537             : 
     538             :         @par BNF
     539             :         @code
     540             :         authority   = [ userinfo "@" ] host [ ":" port ]
     541             :         @endcode
     542             : 
     543             :         @par Specification
     544             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2"
     545             :             >3.2. Authority (rfc3986)</a>
     546             : 
     547             :         @see
     548             :             @ref authority,
     549             :             @ref has_authority.
     550             :     */
     551             :     pct_string_view
     552             :     encoded_authority() const noexcept;
     553             : 
     554             :     //--------------------------------------------
     555             :     //
     556             :     // Userinfo
     557             :     //
     558             :     //--------------------------------------------
     559             : 
     560             :     /** Return true if a userinfo is present
     561             : 
     562             :         This function returns true if this
     563             :         contains a userinfo.
     564             : 
     565             :         @par Example
     566             :         @code
     567             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).has_userinfo() );
     568             :         @endcode
     569             : 
     570             :         @par Complexity
     571             :         Constant.
     572             : 
     573             :         @par Exception Safety
     574             :         Throws nothing.
     575             : 
     576             :         @par BNF
     577             :         @code
     578             :         userinfo    = user [ ":" [ password ] ]
     579             : 
     580             :         authority   = [ userinfo "@" ] host [ ":" port ]
     581             :         @endcode
     582             : 
     583             :         @par Specification
     584             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     585             :             >3.2.1. User Information (rfc3986)</a>
     586             : 
     587             :         @see
     588             :             @ref has_password,
     589             :             @ref encoded_password,
     590             :             @ref encoded_user,
     591             :             @ref encoded_userinfo,
     592             :             @ref password,
     593             :             @ref user,
     594             :             @ref userinfo.
     595             : 
     596             :     */
     597             :     bool
     598             :     has_userinfo() const noexcept;
     599             : 
     600             :     /** Return true if a password is present
     601             : 
     602             :         This function returns true if the
     603             :         userinfo is present and contains
     604             :         a password.
     605             : 
     606             :         @par Example
     607             :         @code
     608             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).has_password() );
     609             :         @endcode
     610             : 
     611             :         @par Complexity
     612             :         Constant.
     613             : 
     614             :         @par Exception Safety
     615             :         Throws nothing.
     616             : 
     617             :         @par BNF
     618             :         @code
     619             :         userinfo    = user [ ":" [ password ] ]
     620             : 
     621             :         user        = *( unreserved / pct-encoded / sub-delims )
     622             :         password    = *( unreserved / pct-encoded / sub-delims / ":" )
     623             :         @endcode
     624             : 
     625             :         @par Specification
     626             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     627             :             >3.2.1. User Information (rfc3986)</a>
     628             : 
     629             :         @see
     630             :             @ref has_userinfo,
     631             :             @ref encoded_password,
     632             :             @ref encoded_user,
     633             :             @ref encoded_userinfo,
     634             :             @ref password,
     635             :             @ref user,
     636             :             @ref userinfo.
     637             :     */
     638             :     bool
     639             :     has_password() const noexcept;
     640             : 
     641             :     /** Return the userinfo
     642             : 
     643             :         If present, this function returns a
     644             :         string representing the userinfo (which
     645             :         may be empty).
     646             :         Otherwise it returns an empty string.
     647             :         Any percent-escapes in the string are
     648             :         decoded first.
     649             : 
     650             :         @note
     651             :         This function uses the string token
     652             :         return type customization. Depending on
     653             :         the token passed, the return type and
     654             :         behavior of the function can be different.
     655             :         See @ref string_token::return_string
     656             :         for more information.
     657             : 
     658             :         @par Example
     659             :         @code
     660             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).userinfo() == "jane-doe:pass" );
     661             :         @endcode
     662             : 
     663             :         @par Complexity
     664             :         Linear in `this->userinfo().size()`.
     665             : 
     666             :         @par Exception Safety
     667             :         Calls to allocate may throw.
     668             : 
     669             :         @return When called with no arguments,
     670             :         a value of type `std::string` is
     671             :         returned. Otherwise, the return type
     672             :         and meaning depends on the string token
     673             :         passed to the function.
     674             : 
     675             :         @par BNF
     676             :         @code
     677             :         userinfo    = user [ ":" [ password ] ]
     678             : 
     679             :         authority   = [ userinfo "@" ] host [ ":" port ]
     680             :         @endcode
     681             : 
     682             :         @par Specification
     683             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     684             :             >3.2.1. User Information (rfc3986)</a>
     685             : 
     686             :         @see
     687             :             @ref has_password,
     688             :             @ref has_userinfo,
     689             :             @ref encoded_password,
     690             :             @ref encoded_user,
     691             :             @ref encoded_userinfo,
     692             :             @ref password,
     693             :             @ref user.
     694             :     */
     695             :     template<BOOST_URL_STRTOK_TPARAM>
     696             :     BOOST_URL_STRTOK_RETURN
     697          34 :     userinfo(
     698             :         BOOST_URL_STRTOK_ARG(token)) const
     699             :     {
     700          34 :         encoding_opts opt;
     701          34 :         opt.space_as_plus = false;
     702          68 :         return encoded_userinfo().decode(
     703          68 :             opt, std::move(token));
     704             :     }
     705             : 
     706             :     /** Return the userinfo
     707             : 
     708             :         If present, this function returns a
     709             :         string representing the userinfo (which
     710             :         may be empty).
     711             :         Otherwise it returns an empty string.
     712             :         The returned string may contain
     713             :         percent escapes.
     714             : 
     715             :         @par Example
     716             :         @code
     717             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).encoded_userinfo() == "jane%2Ddoe:pass" );
     718             :         @endcode
     719             : 
     720             :         @par Complexity
     721             :         Constant.
     722             : 
     723             :         @par Exception Safety
     724             :         Throws nothing
     725             : 
     726             :         @par BNF
     727             :         @code
     728             :         userinfo    = user [ ":" [ password ] ]
     729             : 
     730             :         authority   = [ userinfo "@" ] host [ ":" port ]
     731             :         @endcode
     732             : 
     733             :         @par Specification
     734             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     735             :             >3.2.1. User Information (rfc3986)</a>
     736             : 
     737             :         @see
     738             :             @ref has_password,
     739             :             @ref has_userinfo,
     740             :             @ref encoded_password,
     741             :             @ref encoded_user,
     742             :             @ref password,
     743             :             @ref user,
     744             :             @ref userinfo.
     745             :     */
     746             :     pct_string_view
     747             :     encoded_userinfo() const noexcept;
     748             : 
     749             :     //--------------------------------------------
     750             : 
     751             :     /** Return the user
     752             : 
     753             :         If present, this function returns a
     754             :         string representing the user (which
     755             :         may be empty).
     756             :         Otherwise it returns an empty string.
     757             :         Any percent-escapes in the string are
     758             :         decoded first.
     759             : 
     760             :         @par Example
     761             :         @code
     762             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).user() == "jane-doe" );
     763             :         @endcode
     764             : 
     765             :         @par Complexity
     766             :         Linear in `this->user().size()`.
     767             : 
     768             :         @par Exception Safety
     769             :         Calls to allocate may throw.
     770             : 
     771             :         @par BNF
     772             :         @code
     773             :         userinfo    = user [ ":" [ password ] ]
     774             : 
     775             :         user        = *( unreserved / pct-encoded / sub-delims )
     776             :         password    = *( unreserved / pct-encoded / sub-delims / ":" )
     777             :         @endcode
     778             : 
     779             :         @par Specification
     780             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     781             :             >3.2.1. User Information (rfc3986)</a>
     782             : 
     783             :         @see
     784             :             @ref has_password,
     785             :             @ref has_userinfo,
     786             :             @ref encoded_password,
     787             :             @ref encoded_user,
     788             :             @ref encoded_userinfo,
     789             :             @ref password,
     790             :             @ref userinfo.
     791             :     */
     792             :     template<BOOST_URL_STRTOK_TPARAM>
     793             :     BOOST_URL_STRTOK_RETURN
     794          55 :     user(
     795             :         BOOST_URL_STRTOK_ARG(token)) const
     796             :     {
     797          55 :         encoding_opts opt;
     798          55 :         opt.space_as_plus = false;
     799         110 :         return encoded_user().decode(
     800         110 :             opt, std::move(token));
     801             :     }
     802             : 
     803             :     /** Return the user
     804             : 
     805             :         If present, this function returns a
     806             :         string representing the user (which
     807             :         may be empty).
     808             :         Otherwise it returns an empty string.
     809             :         The returned string may contain
     810             :         percent escapes.
     811             : 
     812             :         @par Example
     813             :         @code
     814             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).encoded_user() == "jane%2Ddoe" );
     815             :         @endcode
     816             : 
     817             :         @par Complexity
     818             :         Constant.
     819             : 
     820             :         @par Exception Safety
     821             :         Throws nothing.
     822             : 
     823             :         @par BNF
     824             :         @code
     825             :         userinfo    = user [ ":" [ password ] ]
     826             : 
     827             :         user        = *( unreserved / pct-encoded / sub-delims )
     828             :         password    = *( unreserved / pct-encoded / sub-delims / ":" )
     829             :         @endcode
     830             : 
     831             :         @par Specification
     832             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     833             :             >3.2.1. User Information (rfc3986)</a>
     834             : 
     835             :         @see
     836             :             @ref has_password,
     837             :             @ref has_userinfo,
     838             :             @ref encoded_password,
     839             :             @ref encoded_userinfo,
     840             :             @ref password,
     841             :             @ref user,
     842             :             @ref userinfo.
     843             :     */
     844             :     pct_string_view
     845             :     encoded_user() const noexcept;
     846             : 
     847             :     /** Return the password
     848             : 
     849             :         If present, this function returns a
     850             :         string representing the password (which
     851             :         may be an empty string).
     852             :         Otherwise it returns an empty string.
     853             :         Any percent-escapes in the string are
     854             :         decoded first.
     855             : 
     856             :         @par Example
     857             :         @code
     858             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).password() == "pass" );
     859             :         @endcode
     860             : 
     861             :         @par Complexity
     862             :         Linear in `this->password().size()`.
     863             : 
     864             :         @par Exception Safety
     865             :         Calls to allocate may throw.
     866             : 
     867             :         @par BNF
     868             :         @code
     869             :         userinfo    = user [ ":" [ password ] ]
     870             : 
     871             :         user        = *( unreserved / pct-encoded / sub-delims )
     872             :         password    = *( unreserved / pct-encoded / sub-delims / ":" )
     873             :         @endcode
     874             : 
     875             :         @par Specification
     876             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     877             :             >3.2.1. User Information (rfc3986)</a>
     878             : 
     879             :         @see
     880             :             @ref has_password,
     881             :             @ref has_userinfo,
     882             :             @ref encoded_password,
     883             :             @ref encoded_user,
     884             :             @ref encoded_userinfo,
     885             :             @ref user,
     886             :             @ref userinfo.
     887             :     */
     888             :     template<BOOST_URL_STRTOK_TPARAM>
     889             :     BOOST_URL_STRTOK_RETURN
     890          25 :     password(
     891             :         BOOST_URL_STRTOK_ARG(token)) const
     892             :     {
     893          25 :         encoding_opts opt;
     894          25 :         opt.space_as_plus = false;
     895          50 :         return encoded_password().decode(
     896          50 :             opt, std::move(token));
     897             :     }
     898             : 
     899             :     /** Return the password
     900             : 
     901             :         This function returns the password portion
     902             :         of the userinfo as a percent-encoded string.
     903             : 
     904             :         @par Example
     905             :         @code
     906             :         assert( url_view( "http://jane%2Ddoe:pass@example.com" ).encoded_password() == "pass" );
     907             :         @endcode
     908             : 
     909             :         @par Complexity
     910             :         Constant.
     911             : 
     912             :         @par Exception Safety
     913             :         Throws nothing.
     914             : 
     915             :         @par BNF
     916             :         @code
     917             :         userinfo    = user [ ":" [ password ] ]
     918             : 
     919             :         user        = *( unreserved / pct-encoded / sub-delims )
     920             :         password    = *( unreserved / pct-encoded / sub-delims / ":" )
     921             :         @endcode
     922             : 
     923             :         @par Specification
     924             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.1"
     925             :             >3.2.1. User Information (rfc3986)</a>
     926             : 
     927             :         @see
     928             :             @ref has_password,
     929             :             @ref has_userinfo,
     930             :             @ref encoded_user,
     931             :             @ref encoded_userinfo,
     932             :             @ref password,
     933             :             @ref user,
     934             :             @ref userinfo.
     935             :     */
     936             :     pct_string_view
     937             :     encoded_password() const noexcept;
     938             : 
     939             :     //--------------------------------------------
     940             :     //
     941             :     // Host
     942             :     //
     943             :     //--------------------------------------------
     944             : 
     945             :     /** Return the host type
     946             : 
     947             :         This function returns one of the
     948             :         following constants representing the
     949             :         type of host present.
     950             : 
     951             :         @li @ref host_type::ipv4
     952             :         @li @ref host_type::ipv6
     953             :         @li @ref host_type::ipvfuture
     954             :         @li @ref host_type::name
     955             :         @li @ref host_type::none
     956             : 
     957             :         When @ref has_authority is false, the
     958             :         host type is @ref host_type::none.
     959             : 
     960             :         @par Example
     961             :         @code
     962             :         assert( url_view( "https://192.168.0.1/local.htm" ).host_type() == host_type::ipv4 );
     963             :         @endcode
     964             : 
     965             :         @par Complexity
     966             :         Constant.
     967             : 
     968             :         @par Exception Safety
     969             :         Throws nothing.
     970             : 
     971             :         @par Specification
     972             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
     973             :             >3.2.2. Host (rfc3986)</a>
     974             :     */
     975             :     urls::host_type
     976         439 :     host_type() const noexcept
     977             :     {
     978         439 :         return pi_->host_type_;
     979             :     }
     980             : 
     981             :     /** Return the host
     982             : 
     983             :         This function returns the host portion
     984             :         of the authority as a string, or the
     985             :         empty string if there is no authority.
     986             :         Any percent-escapes in the string are
     987             :         decoded first.
     988             : 
     989             :         @par Example
     990             :         @code
     991             :         assert( url_view( "https://www%2droot.example.com/" ).host() == "www-root.example.com" );
     992             :         @endcode
     993             : 
     994             :         @par Complexity
     995             :         Linear in `this->host().size()`.
     996             : 
     997             :         @par Exception Safety
     998             :         Calls to allocate may throw.
     999             : 
    1000             :         @par BNF
    1001             :         @code
    1002             :         host        = IP-literal / IPv4address / reg-name
    1003             : 
    1004             :         IP-literal  = "[" ( IPv6address / IPvFuture  ) "]"
    1005             : 
    1006             :         reg-name    = *( unreserved / pct-encoded / "-" / ".")
    1007             :         @endcode
    1008             : 
    1009             :         @par Specification
    1010             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1011             :             >3.2.2. Host (rfc3986)</a>
    1012             :     */
    1013             :     template<BOOST_URL_STRTOK_TPARAM>
    1014             :     BOOST_URL_STRTOK_RETURN
    1015          65 :     host(
    1016             :         BOOST_URL_STRTOK_ARG(token)) const
    1017             :     {
    1018          65 :         encoding_opts opt;
    1019          65 :         opt.space_as_plus = false;
    1020         130 :         return encoded_host().decode(
    1021         130 :             opt, std::move(token));
    1022             :     }
    1023             : 
    1024             :     /** Return the host
    1025             : 
    1026             :         This function returns the host portion
    1027             :         of the authority as a string, or the
    1028             :         empty string if there is no authority.
    1029             :         The returned string may contain
    1030             :         percent escapes.
    1031             : 
    1032             :         @par Example
    1033             :         @code
    1034             :         assert( url_view( "https://www%2droot.example.com/" ).encoded_host() == "www%2droot.example.com" );
    1035             :         @endcode
    1036             : 
    1037             :         @par Complexity
    1038             :         Constant.
    1039             : 
    1040             :         @par Exception Safety
    1041             :         Throws nothing.
    1042             : 
    1043             :         @par BNF
    1044             :         @code
    1045             :         host        = IP-literal / IPv4address / reg-name
    1046             : 
    1047             :         IP-literal  = "[" ( IPv6address / IPvFuture  ) "]"
    1048             : 
    1049             :         reg-name    = *( unreserved / pct-encoded / "-" / ".")
    1050             :         @endcode
    1051             : 
    1052             :         @par Specification
    1053             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1054             :             >3.2.2. Host (rfc3986)</a>
    1055             :     */
    1056             :     pct_string_view
    1057             :     encoded_host() const noexcept;
    1058             : 
    1059             :     /** Return the host
    1060             : 
    1061             :         The value returned by this function
    1062             :         depends on the type of host returned
    1063             :         from the function @ref host_type.
    1064             : 
    1065             :         @li If the type is @ref host_type::ipv4,
    1066             :         then the IPv4 address string is returned.
    1067             : 
    1068             :         @li If the type is @ref host_type::ipv6,
    1069             :         then the IPv6 address string is returned,
    1070             :         without any enclosing brackets.
    1071             : 
    1072             :         @li If the type is @ref host_type::ipvfuture,
    1073             :         then the IPvFuture address string is returned,
    1074             :         without any enclosing brackets.
    1075             : 
    1076             :         @li If the type is @ref host_type::name,
    1077             :         then the host name string is returned.
    1078             :         Any percent-escapes in the string are
    1079             :         decoded first.
    1080             : 
    1081             :         @li If the type is @ref host_type::none,
    1082             :         then an empty string is returned.
    1083             : 
    1084             :         @par Example
    1085             :         @code
    1086             :         assert( url_view( "https://[1::6:c0a8:1]/" ).host_address() == "1::6:c0a8:1" );
    1087             :         @endcode
    1088             : 
    1089             :         @par Complexity
    1090             :         Linear in `this->host_address().size()`.
    1091             : 
    1092             :         @par Exception Safety
    1093             :         Calls to allocate may throw.
    1094             : 
    1095             :         @par BNF
    1096             :         @code
    1097             :         host        = IP-literal / IPv4address / reg-name
    1098             : 
    1099             :         IP-literal  = "[" ( IPv6address / IPvFuture  ) "]"
    1100             : 
    1101             :         reg-name    = *( unreserved / pct-encoded / "-" / ".")
    1102             :         @endcode
    1103             : 
    1104             :         @par Specification
    1105             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1106             :             >3.2.2. Host (rfc3986)</a>
    1107             :     */
    1108             :     template<BOOST_URL_STRTOK_TPARAM>
    1109             :     BOOST_URL_STRTOK_RETURN
    1110          98 :     host_address(
    1111             :         BOOST_URL_STRTOK_ARG(token)) const
    1112             :     {
    1113          98 :         encoding_opts opt;
    1114          98 :         opt.space_as_plus = false;
    1115         196 :         return encoded_host_address().decode(
    1116         196 :             opt, std::move(token));
    1117             :     }
    1118             : 
    1119             :     /** Return the host
    1120             : 
    1121             :         The value returned by this function
    1122             :         depends on the type of host returned
    1123             :         from the function @ref host_type.
    1124             : 
    1125             :         @li If the type is @ref host_type::ipv4,
    1126             :         then the IPv4 address string is returned.
    1127             : 
    1128             :         @li If the type is @ref host_type::ipv6,
    1129             :         then the IPv6 address string is returned,
    1130             :         without any enclosing brackets.
    1131             : 
    1132             :         @li If the type is @ref host_type::ipvfuture,
    1133             :         then the IPvFuture address string is returned,
    1134             :         without any enclosing brackets.
    1135             : 
    1136             :         @li If the type is @ref host_type::name,
    1137             :         then the host name string is returned.
    1138             :         Any percent-escapes in the string are
    1139             :         decoded first.
    1140             : 
    1141             :         @li If the type is @ref host_type::none,
    1142             :         then an empty string is returned.
    1143             :         The returned string may contain
    1144             :         percent escapes.
    1145             : 
    1146             :         @par Example
    1147             :         @code
    1148             :         assert( url_view( "https://www%2droot.example.com/" ).encoded_host_address() == "www%2droot.example.com" );
    1149             :         @endcode
    1150             : 
    1151             :         @par Complexity
    1152             :         Constant.
    1153             : 
    1154             :         @par Exception Safety
    1155             :         Throws nothing.
    1156             : 
    1157             :         @par BNF
    1158             :         @code
    1159             :         host        = IP-literal / IPv4address / reg-name
    1160             : 
    1161             :         IP-literal  = "[" ( IPv6address / IPvFuture  ) "]"
    1162             : 
    1163             :         reg-name    = *( unreserved / pct-encoded / "-" / ".")
    1164             :         @endcode
    1165             : 
    1166             :         @par Specification
    1167             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1168             :             >3.2.2. Host (rfc3986)</a>
    1169             :     */
    1170             :     pct_string_view
    1171             :     encoded_host_address() const noexcept;
    1172             : 
    1173             :     /** Return the host IPv4 address
    1174             : 
    1175             :         If the host type is @ref host_type::ipv4,
    1176             :         this function returns the address as
    1177             :         a value of type @ref ipv4_address.
    1178             :         Otherwise, if the host type is not an IPv4
    1179             :         address, it returns a default-constructed
    1180             :         value which is equal to the unspecified
    1181             :         address "0.0.0.0".
    1182             : 
    1183             :         @par Example
    1184             :         @code
    1185             :         assert( url_view( "http://127.0.0.1/index.htm?user=win95" ).host_ipv4_address() == ipv4_address( "127.0.0.1" ) );
    1186             :         @endcode
    1187             : 
    1188             :         @par Complexity
    1189             :         Constant.
    1190             : 
    1191             :         @par Exception Safety
    1192             :         Throws nothing.
    1193             : 
    1194             :         @par BNF
    1195             :         @code
    1196             :         IPv4address = dec-octet "." dec-octet "." dec-octet "." dec-octet
    1197             : 
    1198             :         dec-octet   = DIGIT                 ; 0-9
    1199             :                     / %x31-39 DIGIT         ; 10-99
    1200             :                     / "1" 2DIGIT            ; 100-199
    1201             :                     / "2" %x30-34 DIGIT     ; 200-249
    1202             :                     / "25" %x30-35          ; 250-255
    1203             :         @endcode
    1204             : 
    1205             :         @par Specification
    1206             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1207             :             >3.2.2. Host (rfc3986)</a>
    1208             :     */
    1209             :     ipv4_address
    1210             :     host_ipv4_address() const noexcept;
    1211             : 
    1212             :     /** Return the host IPv6 address
    1213             : 
    1214             :         If the host type is @ref host_type::ipv6,
    1215             :         this function returns the address as
    1216             :         a value of type @ref ipv6_address.
    1217             :         Otherwise, if the host type is not an IPv6
    1218             :         address, it returns a default-constructed
    1219             :         value which is equal to the unspecified
    1220             :         address "0:0:0:0:0:0:0:0".
    1221             : 
    1222             :         @par Example
    1223             :         @code
    1224             :         assert( url_view( "ftp://[::1]/" ).host_ipv6_address() == ipv6_address( "::1" ) );
    1225             :         @endcode
    1226             : 
    1227             :         @par Complexity
    1228             :         Constant.
    1229             : 
    1230             :         @par Exception Safety
    1231             :         Throws nothing.
    1232             : 
    1233             :         @par BNF
    1234             :         @code
    1235             :         IPv6address =                            6( h16 ":" ) ls32
    1236             :                     /                       "::" 5( h16 ":" ) ls32
    1237             :                     / [               h16 ] "::" 4( h16 ":" ) ls32
    1238             :                     / [ *1( h16 ":" ) h16 ] "::" 3( h16 ":" ) ls32
    1239             :                     / [ *2( h16 ":" ) h16 ] "::" 2( h16 ":" ) ls32
    1240             :                     / [ *3( h16 ":" ) h16 ] "::"    h16 ":"   ls32
    1241             :                     / [ *4( h16 ":" ) h16 ] "::"              ls32
    1242             :                     / [ *5( h16 ":" ) h16 ] "::"              h16
    1243             :                     / [ *6( h16 ":" ) h16 ] "::"
    1244             : 
    1245             :         ls32        = ( h16 ":" h16 ) / IPv4address
    1246             :                     ; least-significant 32 bits of address
    1247             : 
    1248             :         h16         = 1*4HEXDIG
    1249             :                     ; 16 bits of address represented in hexadecimal
    1250             :         @endcode
    1251             : 
    1252             :         @par Specification
    1253             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1254             :             >3.2.2. Host (rfc3986)</a>
    1255             :     */
    1256             :     ipv6_address
    1257             :     host_ipv6_address() const noexcept;
    1258             : 
    1259             :     /** Return the host IPvFuture address
    1260             : 
    1261             :         If the host type is @ref host_type::ipvfuture,
    1262             :         this function returns the address as
    1263             :         a string.
    1264             :         Otherwise, if the host type is not an
    1265             :         IPvFuture address, it returns an
    1266             :         empty string.
    1267             : 
    1268             :         @par Example
    1269             :         @code
    1270             :         assert( url_view( "http://[v1fe.d:9]/index.htm" ).host_ipvfuture() == "v1fe.d:9" );
    1271             :         @endcode
    1272             : 
    1273             :         @par Complexity
    1274             :         Constant.
    1275             : 
    1276             :         @par Exception Safety
    1277             :         Throws nothing.
    1278             : 
    1279             :         @par BNF
    1280             :         @code
    1281             :         IPvFuture  = "v" 1*HEXDIG "." 1*( unreserved / sub-delims / ":" )
    1282             :         @endcode
    1283             : 
    1284             :         @par Specification
    1285             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1286             :             >3.2.2. Host (rfc3986)</a>
    1287             :     */
    1288             :     core::string_view
    1289             :     host_ipvfuture() const noexcept;
    1290             : 
    1291             :     /** Return the host name
    1292             : 
    1293             :         If the host type is @ref host_type::name,
    1294             :         this function returns the name as
    1295             :         a string. Otherwise an empty string is returned.
    1296             :         Any percent-escapes in the string are
    1297             :         decoded first.
    1298             : 
    1299             :         @par Example
    1300             :         @code
    1301             :         assert( url_view( "https://www%2droot.example.com/" ).host_name() == "www-root.example.com" );
    1302             :         @endcode
    1303             : 
    1304             :         @par Complexity
    1305             :         Linear in `this->host_name().size()`.
    1306             : 
    1307             :         @par Exception Safety
    1308             :         Calls to allocate may throw.
    1309             : 
    1310             :         @par BNF
    1311             :         @code
    1312             :         host        = IP-literal / IPv4address / reg-name
    1313             : 
    1314             :         IP-literal  = "[" ( IPv6address / IPvFuture  ) "]"
    1315             : 
    1316             :         reg-name    = *( unreserved / pct-encoded / "-" / ".")
    1317             :         @endcode
    1318             : 
    1319             :         @par Specification
    1320             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1321             :             >3.2.2. Host (rfc3986)</a>
    1322             :     */
    1323             :     template<BOOST_URL_STRTOK_TPARAM>
    1324             :     BOOST_URL_STRTOK_RETURN
    1325          93 :     host_name(
    1326             :         BOOST_URL_STRTOK_ARG(token)) const
    1327             :     {
    1328          93 :         encoding_opts opt;
    1329          93 :         opt.space_as_plus = false;
    1330         186 :         return encoded_host_name().decode(
    1331         186 :             opt, std::move(token));
    1332             :     }
    1333             : 
    1334             :     /** Return the host name
    1335             : 
    1336             :         If the host type is @ref host_type::name,
    1337             :         this function returns the name as
    1338             :         a string.
    1339             :         Otherwise, if the host type is not an
    1340             :         name, it returns an empty string.
    1341             :         The returned string may contain
    1342             :         percent escapes.
    1343             : 
    1344             :         @par Example
    1345             :         @code
    1346             :         assert( url_view( "https://www%2droot.example.com/" ).encoded_host_name() == "www%2droot.example.com" );
    1347             :         @endcode
    1348             : 
    1349             :         @par Complexity
    1350             :         Constant.
    1351             : 
    1352             :         @par Exception Safety
    1353             :         Throws nothing.
    1354             : 
    1355             :         @par BNF
    1356             :         @code
    1357             :         host        = IP-literal / IPv4address / reg-name
    1358             : 
    1359             :         IP-literal  = "[" ( IPv6address / IPvFuture  ) "]"
    1360             : 
    1361             :         reg-name    = *( unreserved / pct-encoded / "-" / ".")
    1362             :         @endcode
    1363             : 
    1364             :         @par Specification
    1365             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    1366             :             >3.2.2. Host (rfc3986)</a>
    1367             :     */
    1368             :     pct_string_view
    1369             :     encoded_host_name() const noexcept;
    1370             : 
    1371             :     /** Return the IPv6 Zone ID
    1372             : 
    1373             :         If the host type is @ref host_type::ipv6,
    1374             :         this function returns the Zone ID as
    1375             :         a string. Otherwise an empty string is returned.
    1376             :         Any percent-escapes in the string are
    1377             :         decoded first.
    1378             : 
    1379             :         @par Example
    1380             :         @code
    1381             :         assert( url_view( "http://[fe80::1%25eth0]/" ).zone_id() == "eth0" );
    1382             :         @endcode
    1383             : 
    1384             :         @par Complexity
    1385             :         Linear in `this->encoded_zone_id().size()`.
    1386             : 
    1387             :         @par Exception Safety
    1388             :         Calls to allocate may throw.
    1389             : 
    1390             :         @par BNF
    1391             :         @code
    1392             :         host        = IP-literal / IPv4address / reg-name
    1393             : 
    1394             :         IP-literal = "[" ( IPv6address / IPv6addrz / IPvFuture  ) "]"
    1395             : 
    1396             :         ZoneID = 1*( unreserved / pct-encoded )
    1397             : 
    1398             :         IPv6addrz = IPv6address "%25" ZoneID
    1399             :         @endcode
    1400             : 
    1401             :         @par Specification
    1402             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc6874"
    1403             :             >Representing IPv6 Zone Identifiers in Address Literals and Uniform Resource Identifiers</a>
    1404             :     */
    1405             :     template<BOOST_URL_STRTOK_TPARAM>
    1406             :     BOOST_URL_STRTOK_RETURN
    1407           5 :     zone_id(
    1408             :         BOOST_URL_STRTOK_ARG(token)) const
    1409             :     {
    1410           5 :         encoding_opts opt;
    1411           5 :         opt.space_as_plus = false;
    1412          10 :         return encoded_zone_id().decode(
    1413          10 :             opt, std::move(token));
    1414             :     }
    1415             : 
    1416             :     /** Return the IPv6 Zone ID
    1417             : 
    1418             :         If the host type is @ref host_type::ipv6,
    1419             :         this function returns the Zone ID as
    1420             :         a string. Otherwise an empty string is returned.
    1421             :         The returned string may contain
    1422             :         percent escapes.
    1423             : 
    1424             :         @par Example
    1425             :         @code
    1426             :         assert( url_view( "http://[fe80::1%25eth0]/" ).encoded_zone_id() == "eth0" );
    1427             :         @endcode
    1428             : 
    1429             :         @par Complexity
    1430             :         Constant.
    1431             : 
    1432             :         @par Exception Safety
    1433             :         Throws nothing.
    1434             : 
    1435             :         @par BNF
    1436             :         @code
    1437             :         host        = IP-literal / IPv4address / reg-name
    1438             : 
    1439             :         IP-literal = "[" ( IPv6address / IPv6addrz / IPvFuture  ) "]"
    1440             : 
    1441             :         ZoneID = 1*( unreserved / pct-encoded )
    1442             : 
    1443             :         IPv6addrz = IPv6address "%25" ZoneID
    1444             :         @endcode
    1445             : 
    1446             :         @par Specification
    1447             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc6874"
    1448             :             >Representing IPv6 Zone Identifiers in Address Literals and Uniform Resource Identifiers</a>
    1449             :     */
    1450             :     pct_string_view
    1451             :     encoded_zone_id() const noexcept;
    1452             : 
    1453             :     //--------------------------------------------
    1454             :     //
    1455             :     // Port
    1456             :     //
    1457             :     //--------------------------------------------
    1458             : 
    1459             :     /** Return true if a port is present
    1460             : 
    1461             :         This function returns true if an
    1462             :         authority is present and contains a port.
    1463             : 
    1464             :         @par Example
    1465             :         @code
    1466             :         assert( url_view( "wss://www.example.com:443" ).has_port() );
    1467             :         @endcode
    1468             : 
    1469             :         @par Complexity
    1470             :         Constant.
    1471             : 
    1472             :         @par Exception Safety
    1473             :         Throws nothing.
    1474             : 
    1475             :         @par BNF
    1476             :         @code
    1477             :         authority   = [ userinfo "@" ] host [ ":" port ]
    1478             : 
    1479             :         port        = *DIGIT
    1480             :         @endcode
    1481             : 
    1482             :         @par Specification
    1483             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.3"
    1484             :             >3.2.3. Port (rfc3986)</a>
    1485             : 
    1486             :         @see
    1487             :             @ref encoded_host_and_port,
    1488             :             @ref port,
    1489             :             @ref port_number.
    1490             :     */
    1491             :     bool
    1492             :     has_port() const noexcept;
    1493             : 
    1494             :     /** Return the port
    1495             : 
    1496             :         If present, this function returns a
    1497             :         string representing the port (which
    1498             :         may be empty).
    1499             :         Otherwise it returns an empty string.
    1500             : 
    1501             :         @par Example
    1502             :         @code
    1503             :         assert( url_view( "http://localhost.com:8080" ).port() == "8080" );
    1504             :         @endcode
    1505             : 
    1506             :         @par Complexity
    1507             :         Constant.
    1508             : 
    1509             :         @par Exception Safety
    1510             :         Throws nothing.
    1511             : 
    1512             :         @par BNF
    1513             :         @code
    1514             :         port        = *DIGIT
    1515             :         @endcode
    1516             : 
    1517             :         @par Specification
    1518             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.3"
    1519             :             >3.2.3. Port (rfc3986)</a>
    1520             : 
    1521             :         @see
    1522             :             @ref encoded_host_and_port,
    1523             :             @ref has_port,
    1524             :             @ref port_number.
    1525             :     */
    1526             :     core::string_view
    1527             :     port() const noexcept;
    1528             : 
    1529             :     /** Return the port
    1530             : 
    1531             :         If a port is present and the numerical
    1532             :         value is representable, it is returned
    1533             :         as an unsigned integer. Otherwise, the
    1534             :         number zero is returned.
    1535             : 
    1536             :         @par Example
    1537             :         @code
    1538             :         assert( url_view( "http://localhost.com:8080" ).port_number() == 8080 );
    1539             :         @endcode
    1540             : 
    1541             :         @par Complexity
    1542             :         Constant.
    1543             : 
    1544             :         @par Exception Safety
    1545             :         Throws nothing.
    1546             : 
    1547             :         @par BNF
    1548             :         @code
    1549             :         port        = *DIGIT
    1550             :         @endcode
    1551             : 
    1552             :         @par Specification
    1553             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.3"
    1554             :             >3.2.3. Port (rfc3986)</a>
    1555             : 
    1556             :         @see
    1557             :             @ref encoded_host_and_port,
    1558             :             @ref has_port,
    1559             :             @ref port.
    1560             :     */
    1561             :     std::uint16_t
    1562             :     port_number() const noexcept;
    1563             : 
    1564             :     //--------------------------------------------
    1565             :     //
    1566             :     // Path
    1567             :     //
    1568             :     //--------------------------------------------
    1569             : 
    1570             :     /** Return true if the path is absolute
    1571             : 
    1572             :         This function returns true if the path
    1573             :         begins with a forward slash ('/').
    1574             : 
    1575             :         @par Example
    1576             :         @code
    1577             :         assert( url_view( "/path/to/file.txt" ).is_path_absolute() );
    1578             :         @endcode
    1579             : 
    1580             :         @par Complexity
    1581             :         Constant.
    1582             : 
    1583             :         @par Exception Safety
    1584             :         Throws nothing.
    1585             : 
    1586             :         @par BNF
    1587             :         @code
    1588             :         path          = path-abempty    ; begins with "/" or is empty
    1589             :                       / path-absolute   ; begins with "/" but not "//"
    1590             :                       / path-noscheme   ; begins with a non-colon segment
    1591             :                       / path-rootless   ; begins with a segment
    1592             :                       / path-empty      ; zero characters
    1593             : 
    1594             :         path-abempty  = *( "/" segment )
    1595             :         path-absolute = "/" [ segment-nz *( "/" segment ) ]
    1596             :         path-noscheme = segment-nz-nc *( "/" segment )
    1597             :         path-rootless = segment-nz *( "/" segment )
    1598             :         path-empty    = 0<pchar>
    1599             :         @endcode
    1600             : 
    1601             :         @par Specification
    1602             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.3"
    1603             :             >3.3.  Path (rfc3986)</a>
    1604             : 
    1605             :         @see
    1606             :             @ref encoded_path,
    1607             :             @ref encoded_segments.
    1608             :             @ref path,
    1609             :             @ref segments.
    1610             :     */
    1611             :     bool
    1612        1542 :     is_path_absolute() const noexcept
    1613             :     {
    1614             :         return
    1615        2671 :             pi_->len(id_path) > 0 &&
    1616        2671 :             pi_->cs_[pi_->offset(id_path)] == '/';
    1617             :     }
    1618             : 
    1619             :     /** Return the path
    1620             : 
    1621             :         This function returns the path as a
    1622             :         string. The path may be empty.
    1623             :         Any percent-escapes in the string are
    1624             :         decoded first.
    1625             : 
    1626             :         @par Example
    1627             :         @code
    1628             :         assert( url_view( "file:///Program%20Files/Games/config.ini" ).path() == "/Program Files/Games/config.ini" );
    1629             :         @endcode
    1630             : 
    1631             :         @par Complexity
    1632             :         Linear in `this->path().size()`.
    1633             : 
    1634             :         @par Exception Safety
    1635             :         Calls to allocate may throw.
    1636             : 
    1637             :         @par BNF
    1638             :         @code
    1639             :         path          = path-abempty    ; begins with "/" or is empty
    1640             :                       / path-absolute   ; begins with "/" but not "//"
    1641             :                       / path-noscheme   ; begins with a non-colon segment
    1642             :                       / path-rootless   ; begins with a segment
    1643             :                       / path-empty      ; zero characters
    1644             : 
    1645             :         path-abempty  = *( "/" segment )
    1646             :         path-absolute = "/" [ segment-nz *( "/" segment ) ]
    1647             :         path-noscheme = segment-nz-nc *( "/" segment )
    1648             :         path-rootless = segment-nz *( "/" segment )
    1649             :         path-empty    = 0<pchar>
    1650             :         @endcode
    1651             : 
    1652             :         @par Specification
    1653             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.3"
    1654             :             >3.3. Path (rfc3986)</a>
    1655             : 
    1656             :         @see
    1657             :             @ref is_path_absolute,
    1658             :             @ref encoded_path,
    1659             :             @ref encoded_segments.
    1660             :             @ref segments.
    1661             :     */
    1662             :     template<BOOST_URL_STRTOK_TPARAM>
    1663             :     BOOST_URL_STRTOK_RETURN
    1664          15 :     path(
    1665             :         BOOST_URL_STRTOK_ARG(token)) const
    1666             :     {
    1667          15 :         encoding_opts opt;
    1668          15 :         opt.space_as_plus = false;
    1669          30 :         return encoded_path().decode(
    1670          30 :             opt, std::move(token));
    1671             :     }
    1672             : 
    1673             :     /** Return the path
    1674             : 
    1675             :         This function returns the path as a
    1676             :         string. The path may be empty.
    1677             :         Any percent-escapes in the string are
    1678             :         decoded first.
    1679             : 
    1680             :         @par Example
    1681             :         @code
    1682             :         assert( url_view( "file:///Program%20Files/Games/config.ini" ).encoded_path() == "/Program%20Files/Games/config.ini" );
    1683             :         @endcode
    1684             : 
    1685             :         @par Complexity
    1686             :         Constant.
    1687             : 
    1688             :         @par Exception Safety
    1689             :         Throws nothing.
    1690             : 
    1691             :         @par BNF
    1692             :         @code
    1693             :         path          = path-abempty    ; begins with "/" or is empty
    1694             :                       / path-absolute   ; begins with "/" but not "//"
    1695             :                       / path-noscheme   ; begins with a non-colon segment
    1696             :                       / path-rootless   ; begins with a segment
    1697             :                       / path-empty      ; zero characters
    1698             : 
    1699             :         path-abempty  = *( "/" segment )
    1700             :         path-absolute = "/" [ segment-nz *( "/" segment ) ]
    1701             :         path-noscheme = segment-nz-nc *( "/" segment )
    1702             :         path-rootless = segment-nz *( "/" segment )
    1703             :         path-empty    = 0<pchar>
    1704             :         @endcode
    1705             : 
    1706             :         @par Specification
    1707             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.3"
    1708             :             >3.3. Path (rfc3986)</a>
    1709             : 
    1710             :         @see
    1711             :             @ref is_path_absolute,
    1712             :             @ref encoded_segments.
    1713             :             @ref path,
    1714             :             @ref segments.
    1715             :     */
    1716             :     pct_string_view
    1717             :     encoded_path() const noexcept;
    1718             : 
    1719             :     /** Return the path as a container of segments
    1720             : 
    1721             :         This function returns a bidirectional
    1722             :         view of strings over the path.
    1723             :         The returned view references the same
    1724             :         underlying character buffer; ownership
    1725             :         is not transferred.
    1726             :         Any percent-escapes in strings returned
    1727             :         when iterating the view are decoded first.
    1728             : 
    1729             :         @par Example
    1730             :         @code
    1731             :         segments_view sv = url_view( "/path/to/file.txt" ).segments();
    1732             :         @endcode
    1733             : 
    1734             :         @par Complexity
    1735             :         Constant.
    1736             : 
    1737             :         @par Exception Safety
    1738             :         Throws nothing.
    1739             : 
    1740             :         @par BNF
    1741             :         @code
    1742             :         path          = [ "/" ] segment *( "/" segment )
    1743             :         @endcode
    1744             : 
    1745             :         @par Specification
    1746             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.3"
    1747             :             >3.3. Path (rfc3986)</a>
    1748             : 
    1749             :         @see
    1750             :             @ref is_path_absolute,
    1751             :             @ref encoded_path,
    1752             :             @ref encoded_segments.
    1753             :             @ref path,
    1754             :             @ref segments_view.
    1755             :     */
    1756             :     segments_view
    1757             :     segments() const noexcept;
    1758             : 
    1759             :     /** Return the path as a container of segments
    1760             : 
    1761             :         This function returns a bidirectional
    1762             :         view of strings over the path.
    1763             :         The returned view references the same
    1764             :         underlying character buffer; ownership
    1765             :         is not transferred.
    1766             :         Strings returned when iterating the
    1767             :         range may contain percent escapes.
    1768             : 
    1769             :         @par Example
    1770             :         @code
    1771             :         segments_encoded_view sv = url_view( "/path/to/file.txt" ).encoded_segments();
    1772             :         @endcode
    1773             : 
    1774             :         @par Complexity
    1775             :         Constant.
    1776             : 
    1777             :         @par Exception Safety
    1778             :         Throws nothing.
    1779             : 
    1780             :         @par BNF
    1781             :         @code
    1782             :         path          = path-abempty    ; begins with "/" or is empty
    1783             :                       / path-absolute   ; begins with "/" but not "//"
    1784             :                       / path-noscheme   ; begins with a non-colon segment
    1785             :                       / path-rootless   ; begins with a segment
    1786             :                       / path-empty      ; zero characters
    1787             : 
    1788             :         path-abempty  = *( "/" segment )
    1789             :         path-absolute = "/" [ segment-nz *( "/" segment ) ]
    1790             :         path-noscheme = segment-nz-nc *( "/" segment )
    1791             :         path-rootless = segment-nz *( "/" segment )
    1792             :         path-empty    = 0<pchar>
    1793             :         @endcode
    1794             : 
    1795             :         @par Specification
    1796             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.3"
    1797             :             >3.3. Path (rfc3986)</a>
    1798             : 
    1799             :         @see
    1800             :             @ref is_path_absolute,
    1801             :             @ref encoded_path,
    1802             :             @ref path,
    1803             :             @ref segments,
    1804             :             @ref segments_encoded_view.
    1805             :     */
    1806             :     segments_encoded_view
    1807             :     encoded_segments() const noexcept;
    1808             : 
    1809             :     //--------------------------------------------
    1810             :     //
    1811             :     // Query
    1812             :     //
    1813             :     //--------------------------------------------
    1814             : 
    1815             :     /** Return true if a query is present
    1816             : 
    1817             :         This function returns true if this
    1818             :         contains a query. An empty query is
    1819             :         distinct from having no query.
    1820             : 
    1821             :         @par Example
    1822             :         @code
    1823             :         assert( url_view( "/sql?id=42&col=name&page-size=20" ).has_query() );
    1824             :         @endcode
    1825             : 
    1826             :         @par Complexity
    1827             :         Constant.
    1828             : 
    1829             :         @par Exception Safety
    1830             :         Throws nothing.
    1831             : 
    1832             :         @par BNF
    1833             :         @code
    1834             :         query           = *( pchar / "/" / "?" )
    1835             : 
    1836             :         query-param     = key [ "=" value ]
    1837             :         query-params    = [ query-param ] *( "&" query-param )
    1838             :         @endcode
    1839             : 
    1840             :         @par Specification
    1841             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4
    1842             :             >3.4.  Query (rfc3986)</a>
    1843             :         @li <a href="https://en.wikipedia.org/wiki/Query_string"
    1844             :             >Query string (Wikipedia)</a>
    1845             : 
    1846             :         @see
    1847             :             @ref encoded_params,
    1848             :             @ref encoded_query,
    1849             :             @ref params,
    1850             :             @ref query.
    1851             :     */
    1852             :     bool
    1853             :     has_query() const noexcept;
    1854             : 
    1855             :     /** Return the query
    1856             : 
    1857             :         If this contains a query, it is returned
    1858             :         as a string (which may be empty).
    1859             :         Otherwise, an empty string is returned.
    1860             :         Any percent-escapes in the string are
    1861             :         decoded first.
    1862             :         <br>
    1863             :         When plus signs appear in the query
    1864             :         portion of the url, they are converted
    1865             :         to spaces automatically upon decoding.
    1866             :         This behavior can be changed by setting
    1867             :         decode options.
    1868             : 
    1869             :         @par Example
    1870             :         @code
    1871             :         assert( url_view( "/sql?id=42&name=jane%2Ddoe&page+size=20" ).query() == "id=42&name=jane-doe&page size=20" );
    1872             :         @endcode
    1873             : 
    1874             :         @par Complexity
    1875             :         Linear in `this->query().size()`.
    1876             : 
    1877             :         @par Exception Safety
    1878             :         Calls to allocate may throw.
    1879             : 
    1880             :         @par BNF
    1881             :         @code
    1882             :         query           = *( pchar / "/" / "?" )
    1883             : 
    1884             :         query-param     = key [ "=" value ]
    1885             :         query-params    = [ query-param ] *( "&" query-param )
    1886             :         @endcode
    1887             : 
    1888             :         @par Specification
    1889             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4
    1890             :             >3.4.  Query (rfc3986)</a>
    1891             :         @li <a href="https://en.wikipedia.org/wiki/Query_string"
    1892             :             >Query string (Wikipedia)</a>
    1893             : 
    1894             :         @see
    1895             :             @ref encoded_params,
    1896             :             @ref encoded_query,
    1897             :             @ref has_query,
    1898             :             @ref params.
    1899             :     */
    1900             :     template<BOOST_URL_STRTOK_TPARAM>
    1901             :     BOOST_URL_STRTOK_RETURN
    1902          29 :     query(
    1903             :         BOOST_URL_STRTOK_ARG(token)) const
    1904             :     {
    1905             :         // When interacting with the query as
    1906             :         // an intact string, we do not treat
    1907             :         // the plus sign as an encoded space.
    1908          29 :         encoding_opts opt;
    1909          29 :         opt.space_as_plus = false;
    1910          58 :         return encoded_query().decode(
    1911          58 :             opt, std::move(token));
    1912             :     }
    1913             : 
    1914             :     /** Return the query
    1915             : 
    1916             :         If this contains a query, it is returned
    1917             :         as a string (which may be empty).
    1918             :         Otherwise, an empty string is returned.
    1919             :         The returned string may contain
    1920             :         percent escapes.
    1921             : 
    1922             :         @par Example
    1923             :         @code
    1924             :         assert( url_view( "/sql?id=42&name=jane%2Ddoe&page+size=20" ).encoded_query() == "id=42&name=jane%2Ddoe&page+size=20" );
    1925             :         @endcode
    1926             : 
    1927             :         @par Complexity
    1928             :         Constant.
    1929             : 
    1930             :         @par Exception Safety
    1931             :         Throws nothing.
    1932             : 
    1933             :         @par BNF
    1934             :         @code
    1935             :         query           = *( pchar / "/" / "?" )
    1936             : 
    1937             :         query-param     = key [ "=" value ]
    1938             :         query-params    = [ query-param ] *( "&" query-param )
    1939             :         @endcode
    1940             : 
    1941             :         @par Specification
    1942             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4
    1943             :             >3.4.  Query (rfc3986)</a>
    1944             :         @li <a href="https://en.wikipedia.org/wiki/Query_string"
    1945             :             >Query string (Wikipedia)</a>
    1946             : 
    1947             :         @see
    1948             :             @ref encoded_params,
    1949             :             @ref has_query,
    1950             :             @ref params,
    1951             :             @ref query.
    1952             :     */
    1953             :     pct_string_view
    1954             :     encoded_query() const noexcept;
    1955             : 
    1956             :     /** Return the query as a container of parameters
    1957             : 
    1958             :         This function returns a bidirectional
    1959             :         view of key/value pairs over the query.
    1960             :         The returned view references the same
    1961             :         underlying character buffer; ownership
    1962             :         is not transferred.
    1963             :         Any percent-escapes in strings returned
    1964             :         when iterating the view are decoded first.
    1965             : 
    1966             :         @par Example
    1967             :         @code
    1968             :         params_view pv = url_view( "/sql?id=42&name=jane%2Ddoe&page+size=20" ).params();
    1969             :         @endcode
    1970             : 
    1971             :         @par Complexity
    1972             :         Constant.
    1973             : 
    1974             :         @par Exception Safety
    1975             :         Throws nothing.
    1976             : 
    1977             :         @par BNF
    1978             :         @code
    1979             :         query           = *( pchar / "/" / "?" )
    1980             : 
    1981             :         query-param     = key [ "=" value ]
    1982             :         query-params    = [ query-param ] *( "&" query-param )
    1983             :         @endcode
    1984             : 
    1985             :         @par Specification
    1986             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4
    1987             :             >3.4.  Query (rfc3986)</a>
    1988             :         @li <a href="https://en.wikipedia.org/wiki/Query_string"
    1989             :             >Query string (Wikipedia)</a>
    1990             : 
    1991             :         @see
    1992             :             @ref encoded_params,
    1993             :             @ref encoded_query,
    1994             :             @ref has_query,
    1995             :             @ref query.
    1996             :     */
    1997             :     params_view
    1998             :     params() const noexcept;
    1999             : 
    2000             :     params_view
    2001             :     params(encoding_opts opt) const noexcept;
    2002             : 
    2003             :     /** Return the query as a container of parameters
    2004             : 
    2005             :         This function returns a bidirectional
    2006             :         view of key/value pairs over the query.
    2007             :         The returned view references the same
    2008             :         underlying character buffer; ownership
    2009             :         is not transferred.
    2010             :         Strings returned when iterating the
    2011             :         range may contain percent escapes.
    2012             : 
    2013             :         @par Example
    2014             :         @code
    2015             :         params_encoded_view pv = url_view( "/sql?id=42&name=jane%2Ddoe&page+size=20" ).encoded_params();
    2016             :         @endcode
    2017             : 
    2018             :         @par Complexity
    2019             :         Constant.
    2020             : 
    2021             :         @par Exception Safety
    2022             :         Throws nothing.
    2023             : 
    2024             :         @par Specification
    2025             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4"
    2026             :             >3.4. Query (rfc3986)</a>
    2027             : 
    2028             :         @par BNF
    2029             :         @code
    2030             :         query           = *( pchar / "/" / "?" )
    2031             : 
    2032             :         query-param     = key [ "=" value ]
    2033             :         query-params    = [ query-param ] *( "&" query-param )
    2034             :         @endcode
    2035             : 
    2036             :         @par Specification
    2037             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4
    2038             :             >3.4.  Query (rfc3986)</a>
    2039             :         @li <a href="https://en.wikipedia.org/wiki/Query_string"
    2040             :             >Query string (Wikipedia)</a>
    2041             : 
    2042             :         @see
    2043             :             @ref encoded_query,
    2044             :             @ref has_query,
    2045             :             @ref params,
    2046             :             @ref query.
    2047             :     */
    2048             :     params_encoded_view
    2049             :     encoded_params() const noexcept;
    2050             : 
    2051             :     //--------------------------------------------
    2052             :     //
    2053             :     // Fragment
    2054             :     //
    2055             :     //--------------------------------------------
    2056             : 
    2057             :     /** Return true if a fragment is present
    2058             : 
    2059             :         This function returns true if the url
    2060             :         contains a fragment.
    2061             :         An empty fragment is distinct from
    2062             :         no fragment.
    2063             : 
    2064             :         @par Example
    2065             :         @code
    2066             :         assert( url_view( "http://www.example.com/index.htm#anchor" ).has_fragment() );
    2067             :         @endcode
    2068             : 
    2069             :         @par Complexity
    2070             :         Constant.
    2071             : 
    2072             :         @par Exception Safety
    2073             :         Throws nothing.
    2074             : 
    2075             :         @par BNF
    2076             :         @code
    2077             :         URI           = scheme ":" hier-part [ "?" query ] [ "#" fragment ]
    2078             : 
    2079             :         relative-ref  = relative-part [ "?" query ] [ "#" fragment ]
    2080             :         @endcode
    2081             : 
    2082             :         @par Specification
    2083             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.5"
    2084             :             >3.5. Fragment (rfc3986)</a>
    2085             : 
    2086             :         @see
    2087             :             @ref encoded_fragment,
    2088             :             @ref fragment.
    2089             :     */
    2090             :     bool
    2091             :     has_fragment() const noexcept;
    2092             : 
    2093             :     /** Return the fragment
    2094             : 
    2095             :         This function calculates the fragment
    2096             :         of the url, with percent escapes decoded
    2097             :         and without the leading pound sign ('#')
    2098             :         whose presence indicates that the url
    2099             :         contains a fragment.
    2100             : 
    2101             :         <br>
    2102             : 
    2103             :         This function accepts an optional
    2104             :         <em>StringToken</em> parameter which
    2105             :         controls the return type and behavior
    2106             :         of the function:
    2107             : 
    2108             :         @li When called with no arguments,
    2109             :         the return type of the function is
    2110             :         `std::string`. Otherwise
    2111             : 
    2112             :         @li When called with a string token,
    2113             :         the behavior and return type of the
    2114             :         function depends on the type of string
    2115             :         token being passed.
    2116             : 
    2117             :         @par Example
    2118             :         @code
    2119             :         assert( url_view( "http://www.example.com/index.htm#a%2D1" ).fragment() == "a-1" );
    2120             :         @endcode
    2121             : 
    2122             :         @par Complexity
    2123             :         Linear in `this->fragment().size()`.
    2124             : 
    2125             :         @par Exception Safety
    2126             :         Calls to allocate may throw.
    2127             :         String tokens may throw exceptions.
    2128             : 
    2129             :         @param token An optional string token to
    2130             :         use. If this parameter is omitted, the
    2131             :         function returns a new `std::string`.
    2132             : 
    2133             :         @par BNF
    2134             :         @code
    2135             :         fragment        = *( pchar / "/" / "?" )
    2136             : 
    2137             :         fragment-part   = [ "#" fragment ]
    2138             :         @endcode
    2139             : 
    2140             :         @par Specification
    2141             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.5"
    2142             :             >3.5. Fragment (rfc3986)</a>
    2143             : 
    2144             :         @see
    2145             :             @ref encoded_fragment,
    2146             :             @ref has_fragment.
    2147             :     */
    2148             :     template<BOOST_URL_STRTOK_TPARAM>
    2149             :     BOOST_URL_STRTOK_RETURN
    2150          17 :     fragment(
    2151             :         BOOST_URL_STRTOK_ARG(token)) const
    2152             :     {
    2153          17 :         encoding_opts opt;
    2154          17 :         opt.space_as_plus = false;
    2155          34 :         return encoded_fragment().decode(
    2156          34 :             opt, std::move(token));
    2157             :     }
    2158             : 
    2159             :     /** Return the fragment
    2160             : 
    2161             :         This function returns the fragment as a
    2162             :         string with percent-escapes.
    2163             :         Ownership is not transferred; the
    2164             :         string returned references the underlying
    2165             :         character buffer, which must remain valid
    2166             :         or else undefined behavior occurs.
    2167             : 
    2168             :         @par Example
    2169             :         @code
    2170             :         assert( url_view( "http://www.example.com/index.htm#a%2D1" ).encoded_fragment() == "a%2D1" );
    2171             :         @endcode
    2172             : 
    2173             :         @par Complexity
    2174             :         Constant.
    2175             : 
    2176             :         @par Exception Safety
    2177             :         Throws nothing.
    2178             : 
    2179             :         @par BNF
    2180             :         @code
    2181             :         fragment        = *( pchar / "/" / "?" )
    2182             : 
    2183             :         pchar           = unreserved / pct-encoded / sub-delims / ":" / "@"
    2184             :         @endcode
    2185             : 
    2186             :         @par Specification
    2187             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.5"
    2188             :             >3.5. Fragment (rfc3986)</a>
    2189             : 
    2190             :         @see
    2191             :             @ref fragment,
    2192             :             @ref has_fragment.
    2193             :     */
    2194             :     pct_string_view
    2195             :     encoded_fragment() const noexcept;
    2196             : 
    2197             :     //--------------------------------------------
    2198             :     //
    2199             :     // Compound Fields
    2200             :     //
    2201             :     //--------------------------------------------
    2202             : 
    2203             :     /** Return the host and port
    2204             : 
    2205             :         If an authority is present, this
    2206             :         function returns the host and optional
    2207             :         port as a string, which may be empty.
    2208             :         Otherwise it returns an empty string.
    2209             :         The returned string may contain
    2210             :         percent escapes.
    2211             : 
    2212             :         @par Example
    2213             :         @code
    2214             :         assert( url_view( "http://www.example.com:8080/index.htm" ).encoded_host_and_port() == "www.example.com:8080" );
    2215             :         @endcode
    2216             : 
    2217             :         @par Complexity
    2218             :         Constant.
    2219             : 
    2220             :         @par Exception Safety
    2221             :         Throws nothing.
    2222             : 
    2223             :         @par BNF
    2224             :         @code
    2225             :         authority   = [ userinfo "@" ] host [ ":" port ]
    2226             :         @endcode
    2227             : 
    2228             :         @par Specification
    2229             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.2"
    2230             :             >3.2.2.  Host (rfc3986)</a>
    2231             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.2.3"
    2232             :             >3.2.3. Port (rfc3986)</a>
    2233             : 
    2234             :         @see
    2235             :             @ref has_port,
    2236             :             @ref port,
    2237             :             @ref port_number.
    2238             :     */
    2239             :     pct_string_view
    2240             :     encoded_host_and_port() const noexcept;
    2241             : 
    2242             :     /** Return the origin
    2243             : 
    2244             :         If an authority is present, this
    2245             :         function returns the scheme and
    2246             :         authority portion of the url.
    2247             :         Otherwise, an empty string is
    2248             :         returned.
    2249             :         The returned string may contain
    2250             :         percent escapes.
    2251             : 
    2252             :         @par Example
    2253             :         @code
    2254             :         assert( url_view( "http://www.example.com:8080/index.htm?text=none#h1" ).encoded_origin() == "http://www.example.com:8080" );
    2255             :         @endcode
    2256             : 
    2257             :         @par Complexity
    2258             :         Constant.
    2259             : 
    2260             :         @par Exception Safety
    2261             :         Throws nothing.
    2262             : 
    2263             :         @see
    2264             :             @ref encoded_resource,
    2265             :             @ref encoded_target.
    2266             :     */
    2267             :     pct_string_view
    2268             :     encoded_origin() const noexcept;
    2269             : 
    2270             :     /** Return the resource
    2271             : 
    2272             :         This function returns the resource, which
    2273             :         is the portion of the url that includes
    2274             :         only the path, query, and fragment.
    2275             :         The returned string may contain
    2276             :         percent escapes.
    2277             : 
    2278             :         @par Example
    2279             :         @code
    2280             :         assert( url_view( "http://www.example.com/index.html?query#frag" ).encoded_resource() == "/index.html?query#frag" );
    2281             :         @endcode
    2282             : 
    2283             :         @par Complexity
    2284             :         Constant.
    2285             : 
    2286             :         @par Exception Safety
    2287             :         Throws nothing.
    2288             : 
    2289             :         @par Specification
    2290             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.3"
    2291             :             >3.3. Path (rfc3986)</a>
    2292             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4"
    2293             :             >3.4. Query (rfc3986)</a>
    2294             : 
    2295             :         @see
    2296             :             @ref encoded_origin,
    2297             :             @ref encoded_target.
    2298             :     */
    2299             :     pct_string_view
    2300             :     encoded_resource() const noexcept;
    2301             : 
    2302             :     /** Return the target
    2303             : 
    2304             :         This function returns the target, which
    2305             :         is the portion of the url that includes
    2306             :         only the path and query.
    2307             :         The returned string may contain
    2308             :         percent escapes.
    2309             : 
    2310             :         @par Example
    2311             :         @code
    2312             :         assert( url_view( "http://www.example.com/index.html?query#frag" ).encoded_target() == "/index.html?query" );
    2313             :         @endcode
    2314             : 
    2315             :         @par Complexity
    2316             :         Constant.
    2317             : 
    2318             :         @par Exception Safety
    2319             :         Throws nothing.
    2320             : 
    2321             :         @par Specification
    2322             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.3"
    2323             :             >3.3. Path (rfc3986)</a>
    2324             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-3.4"
    2325             :             >3.4. Query (rfc3986)</a>
    2326             : 
    2327             :         @see
    2328             :             @ref encoded_origin,
    2329             :             @ref encoded_resource.
    2330             :     */
    2331             :     pct_string_view
    2332             :     encoded_target() const noexcept;
    2333             : 
    2334             :     //--------------------------------------------
    2335             :     //
    2336             :     // Comparison
    2337             :     //
    2338             :     //--------------------------------------------
    2339             : 
    2340             :     /** Return the result of comparing this with another url
    2341             : 
    2342             :         This function compares two URLs
    2343             :         according to Syntax-Based comparison
    2344             :         algorithm.
    2345             : 
    2346             :         @par Complexity
    2347             :         Linear in `min( u0.size(), u1.size() )`
    2348             : 
    2349             :         @par Exception Safety
    2350             :         Throws nothing.
    2351             : 
    2352             :         @par Specification
    2353             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2"
    2354             :             >6.2.2 Syntax-Based Normalization (rfc3986)</a>
    2355             : 
    2356             :         @return -1 if `*this < other`, 0 if
    2357             :             `this == other`, and 1 if `this > other`.
    2358             :     */
    2359             :     int
    2360             :     compare(url_view_base const& other) const noexcept;
    2361             : 
    2362             :     /** Return the result of comparing two URLs
    2363             : 
    2364             :         The URLs are compared component by
    2365             :         component as if they were first
    2366             :         normalized.
    2367             : 
    2368             :         @par Example
    2369             :         @code
    2370             :         url_view u0( "http://www.a.com/index.htm" );
    2371             :         url_view u1( "http://www.a.com/index.htm" );
    2372             :         assert( u0 == u1 );
    2373             :         @endcode
    2374             : 
    2375             :         @par Effects
    2376             :         @code
    2377             :         url a(u0);
    2378             :         a.normalize();
    2379             :         url b(u1);
    2380             :         b.normalize();
    2381             :         return std::make_tuple(
    2382             :                    a.scheme(),
    2383             :                    a.user(),
    2384             :                    a.password(),
    2385             :                    a.host(),
    2386             :                    a.port(),
    2387             :                    a.path(),
    2388             :                    a.query(),
    2389             :                    a.fragment()) ==
    2390             :                std::make_tuple(
    2391             :                    b.scheme(),
    2392             :                    b.user(),
    2393             :                    b.password(),
    2394             :                    b.host(),
    2395             :                    b.port(),
    2396             :                    b.path(),
    2397             :                    b.query(),
    2398             :                    b.fragment());
    2399             :         @endcode
    2400             : 
    2401             :         @par Complexity
    2402             :         Linear in `min( u0.size(), u1.size() )`
    2403             : 
    2404             :         @par Exception Safety
    2405             :         Throws nothing
    2406             : 
    2407             :         @return `true` if `u0 == u1`
    2408             : 
    2409             :         @par Specification
    2410             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2"
    2411             :             >6.2.2 Syntax-Based Normalization (rfc3986)</a>
    2412             :     */
    2413             :     friend
    2414             :     bool
    2415          73 :     operator==(
    2416             :         url_view_base const& u0,
    2417             :         url_view_base const& u1) noexcept
    2418             :     {
    2419          73 :         return u0.compare(u1) == 0;
    2420             :     }
    2421             : 
    2422             :     /** Return the result of comparing two URLs
    2423             : 
    2424             :         The URLs are compared component by
    2425             :         component as if they were first
    2426             :         normalized.
    2427             : 
    2428             :         @par Example
    2429             :         @code
    2430             :         url_view u0( "http://www.a.com/index.htm" );
    2431             :         url_view u1( "http://www.b.com/index.htm" );
    2432             :         assert( u0 != u1 );
    2433             :         @endcode
    2434             : 
    2435             :         @par Effects
    2436             :         @code
    2437             :         url a(u0);
    2438             :         a.normalize();
    2439             :         url b(u1);
    2440             :         b.normalize();
    2441             :         return std::make_tuple(
    2442             :                    a.scheme(),
    2443             :                    a.user(),
    2444             :                    a.password(),
    2445             :                    a.host(),
    2446             :                    a.port(),
    2447             :                    a.path(),
    2448             :                    a.query(),
    2449             :                    a.fragment()) !=
    2450             :                std::make_tuple(
    2451             :                    b.scheme(),
    2452             :                    b.user(),
    2453             :                    b.password(),
    2454             :                    b.host(),
    2455             :                    b.port(),
    2456             :                    b.path(),
    2457             :                    b.query(),
    2458             :                    b.fragment());
    2459             :         @endcode
    2460             : 
    2461             :         @par Complexity
    2462             :         Linear in `min( u0.size(), u1.size() )`
    2463             : 
    2464             :         @par Exception Safety
    2465             :         Throws nothing
    2466             : 
    2467             :         @return `true` if `u0 != u1`
    2468             : 
    2469             :         @par Specification
    2470             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2"
    2471             :             >6.2.2 Syntax-Based Normalization (rfc3986)</a>
    2472             :     */
    2473             :     friend
    2474             :     bool
    2475          25 :     operator!=(
    2476             :         url_view_base const& u0,
    2477             :         url_view_base const& u1) noexcept
    2478             :     {
    2479          25 :         return ! (u0 == u1);
    2480             :     }
    2481             : 
    2482             :     /** Return the result of comparing two URLs
    2483             : 
    2484             :         The URLs are compared component by
    2485             :         component as if they were first
    2486             :         normalized.
    2487             : 
    2488             :         @par Example
    2489             :         @code
    2490             :         url_view u0( "http://www.a.com/index.htm" );
    2491             :         url_view u1( "http://www.b.com/index.htm" );
    2492             :         assert( u0 < u1 );
    2493             :         @endcode
    2494             : 
    2495             :         @par Effects
    2496             :         @code
    2497             :         url a(u0);
    2498             :         a.normalize();
    2499             :         url b(u1);
    2500             :         b.normalize();
    2501             :         return std::make_tuple(
    2502             :                    a.scheme(),
    2503             :                    a.user(),
    2504             :                    a.password(),
    2505             :                    a.host(),
    2506             :                    a.port(),
    2507             :                    a.path(),
    2508             :                    a.query(),
    2509             :                    a.fragment()) <
    2510             :                std::make_tuple(
    2511             :                    b.scheme(),
    2512             :                    b.user(),
    2513             :                    b.password(),
    2514             :                    b.host(),
    2515             :                    b.port(),
    2516             :                    b.path(),
    2517             :                    b.query(),
    2518             :                    b.fragment());
    2519             :         @endcode
    2520             : 
    2521             :         @par Complexity
    2522             :         Linear in `min( u0.size(), u1.size() )`
    2523             : 
    2524             :         @par Exception Safety
    2525             :         Throws nothing
    2526             : 
    2527             :         @return `true` if `u0 < u1`
    2528             : 
    2529             :         @par Specification
    2530             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2"
    2531             :             >6.2.2 Syntax-Based Normalization (rfc3986)</a>
    2532             :     */
    2533             :     friend
    2534             :     bool
    2535          23 :     operator<(
    2536             :         url_view_base const& u0,
    2537             :         url_view_base const& u1) noexcept
    2538             :     {
    2539          23 :         return u0.compare(u1) < 0;
    2540             :     }
    2541             : 
    2542             :     /** Return the result of comparing two URLs
    2543             : 
    2544             :         The URLs are compared component by
    2545             :         component as if they were first
    2546             :         normalized.
    2547             : 
    2548             :         @par Example
    2549             :         @code
    2550             :         url_view u0( "http://www.b.com/index.htm" );
    2551             :         url_view u1( "http://www.b.com/index.htm" );
    2552             :         assert( u0 <= u1 );
    2553             :         @endcode
    2554             : 
    2555             :         @par Effects
    2556             :         @code
    2557             :         url a(u0);
    2558             :         a.normalize();
    2559             :         url b(u1);
    2560             :         b.normalize();
    2561             :         return std::make_tuple(
    2562             :                    a.scheme(),
    2563             :                    a.user(),
    2564             :                    a.password(),
    2565             :                    a.host(),
    2566             :                    a.port(),
    2567             :                    a.path(),
    2568             :                    a.query(),
    2569             :                    a.fragment()) <=
    2570             :                std::make_tuple(
    2571             :                    b.scheme(),
    2572             :                    b.user(),
    2573             :                    b.password(),
    2574             :                    b.host(),
    2575             :                    b.port(),
    2576             :                    b.path(),
    2577             :                    b.query(),
    2578             :                    b.fragment());
    2579             :         @endcode
    2580             : 
    2581             :         @par Complexity
    2582             :         Linear in `min( u0.size(), u1.size() )`
    2583             : 
    2584             :         @par Exception Safety
    2585             :         Throws nothing
    2586             : 
    2587             :         @return `true` if `u0 <= u1`
    2588             : 
    2589             :         @par Specification
    2590             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2"
    2591             :             >6.2.2 Syntax-Based Normalization (rfc3986)</a>
    2592             :     */
    2593             :     friend
    2594             :     bool
    2595          23 :     operator<=(
    2596             :         url_view_base const& u0,
    2597             :         url_view_base const& u1) noexcept
    2598             :     {
    2599          23 :         return u0.compare(u1) <= 0;
    2600             :     }
    2601             : 
    2602             :     /** Return the result of comparing two URLs
    2603             : 
    2604             :         The URLs are compared component by
    2605             :         component as if they were first
    2606             :         normalized.
    2607             : 
    2608             :         @par Example
    2609             :         @code
    2610             :         url_view u0( "http://www.b.com/index.htm" );
    2611             :         url_view u1( "http://www.a.com/index.htm" );
    2612             :         assert( u0 > u1 );
    2613             :         @endcode
    2614             : 
    2615             :         @par Effects
    2616             :         @code
    2617             :         url a(u0);
    2618             :         a.normalize();
    2619             :         url b(u1);
    2620             :         b.normalize();
    2621             :         return std::make_tuple(
    2622             :                    a.scheme(),
    2623             :                    a.user(),
    2624             :                    a.password(),
    2625             :                    a.host(),
    2626             :                    a.port(),
    2627             :                    a.path(),
    2628             :                    a.query(),
    2629             :                    a.fragment()) >
    2630             :                std::make_tuple(
    2631             :                    b.scheme(),
    2632             :                    b.user(),
    2633             :                    b.password(),
    2634             :                    b.host(),
    2635             :                    b.port(),
    2636             :                    b.path(),
    2637             :                    b.query(),
    2638             :                    b.fragment());
    2639             :         @endcode
    2640             : 
    2641             :         @par Complexity
    2642             :         Linear in `min( u0.size(), u1.size() )`
    2643             : 
    2644             :         @par Exception Safety
    2645             :         Throws nothing
    2646             : 
    2647             :         @return `true` if `u0 > u1`
    2648             : 
    2649             :         @par Specification
    2650             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2"
    2651             :             >6.2.2 Syntax-Based Normalization (rfc3986)</a>
    2652             :     */
    2653             :     friend
    2654             :     bool
    2655          23 :     operator>(
    2656             :         url_view_base const& u0,
    2657             :         url_view_base const& u1) noexcept
    2658             :     {
    2659          23 :         return u0.compare(u1) > 0;
    2660             :     }
    2661             : 
    2662             :     /** Return the result of comparing two URLs
    2663             : 
    2664             :         The URLs are compared component by
    2665             :         component as if they were first
    2666             :         normalized.
    2667             : 
    2668             :         @par Example
    2669             :         @code
    2670             :         url_view u0( "http://www.a.com/index.htm" );
    2671             :         url_view u1( "http://www.a.com/index.htm" );
    2672             :         assert( u0 >= u1 );
    2673             :         @endcode
    2674             : 
    2675             :         @par Effects
    2676             :         @code
    2677             :         url a(u0);
    2678             :         a.normalize();
    2679             :         url b(u1);
    2680             :         b.normalize();
    2681             :         return std::make_tuple(
    2682             :                    a.scheme(),
    2683             :                    a.user(),
    2684             :                    a.password(),
    2685             :                    a.host(),
    2686             :                    a.port(),
    2687             :                    a.path(),
    2688             :                    a.query(),
    2689             :                    a.fragment()) >=
    2690             :                std::make_tuple(
    2691             :                    b.scheme(),
    2692             :                    b.user(),
    2693             :                    b.password(),
    2694             :                    b.host(),
    2695             :                    b.port(),
    2696             :                    b.path(),
    2697             :                    b.query(),
    2698             :                    b.fragment());
    2699             :         @endcode
    2700             : 
    2701             :         @par Complexity
    2702             :         Linear in `min( u0.size(), u1.size() )`
    2703             : 
    2704             :         @par Exception Safety
    2705             :         Throws nothing
    2706             : 
    2707             :         @return `true` if `u0 >= u1`
    2708             : 
    2709             :         @par Specification
    2710             :         @li <a href="https://datatracker.ietf.org/doc/html/rfc3986#section-6.2.2"
    2711             :             >6.2.2 Syntax-Based Normalization (rfc3986)</a>
    2712             :     */
    2713             :     friend
    2714             :     bool
    2715          23 :     operator>=(
    2716             :         url_view_base const& u0,
    2717             :         url_view_base const& u1) noexcept
    2718             :     {
    2719          23 :         return u0.compare(u1) >= 0;
    2720             :     }
    2721             : 
    2722             :     friend
    2723             :     std::ostream&
    2724           5 :     operator<<(
    2725             :         std::ostream& os,
    2726             :         url_view_base const& u)
    2727             :     {
    2728           5 :         return os << u.buffer();
    2729             :     }
    2730             : 
    2731             : private:
    2732             :     //--------------------------------------------
    2733             :     //
    2734             :     // implementation
    2735             :     //
    2736             :     //--------------------------------------------
    2737             :     static
    2738             :     int
    2739             :     segments_compare(
    2740             :         segments_encoded_view seg0,
    2741             :         segments_encoded_view seg1) noexcept;
    2742             : };
    2743             : 
    2744             : //------------------------------------------------
    2745             : 
    2746             : /** Format the url to the output stream
    2747             : 
    2748             :     This function serializes the url to
    2749             :     the specified output stream. Any
    2750             :     percent-escapes are emitted as-is;
    2751             :     no decoding is performed.
    2752             : 
    2753             :     @par Example
    2754             :     @code
    2755             :     url_view u( "http://www.example.com/index.htm" );
    2756             :     std::stringstream ss;
    2757             :     ss << u;
    2758             :     assert( ss.str() == "http://www.example.com/index.htm" );
    2759             :     @endcode
    2760             : 
    2761             :     @par Effects
    2762             :     @code
    2763             :     return os << u.buffer();
    2764             :     @endcode
    2765             : 
    2766             :     @par Complexity
    2767             :     Linear in `u.buffer().size()`
    2768             : 
    2769             :     @par Exception Safety
    2770             :     Basic guarantee.
    2771             : 
    2772             :     @return A reference to the output stream, for chaining
    2773             : 
    2774             :     @param os The output stream to write to.
    2775             : 
    2776             :     @param u The url to write.
    2777             : */
    2778             : std::ostream&
    2779             : operator<<(
    2780             :     std::ostream& os,
    2781             :     url_view_base const& u);
    2782             : 
    2783             : } // urls
    2784             : } // boost
    2785             : 
    2786             : #endif

Generated by: LCOV version 1.15