Repository: pydantic/pydantic

Issue:
AnyUrl does not recognize fragment without query string
### Checks

* [x] I added a descriptive title to this issue
* [x] I have searched (google, github) for similar issues and couldn't find anything
* [x] I have read and followed [the docs](https://pydantic-docs.helpmanual.io/) and still think this is a bug

<!-- Sorry to sound so draconian, but every second saved replying to issues is time spend improving pydantic :-) -->

# Bug


Output of `python -c "import pydantic.utils; print(pydantic.utils.version_info())"`:
```
             pydantic version: 1.7.3
            pydantic compiled: True
                 install path: /Users/andwhite/Projects/lipy-sso_trunk/build/lipy-sso/environments/development-venv/lib/python3.7/site-packages/pydantic
               python version: 3.7.7 (default, Mar 10 2020, 16:11:21)  [Clang 11.0.0 (clang-1100.0.33.12)]
                     platform: Darwin-19.6.0-x86_64-i386-64bit
     optional deps. installed: ['typing-extensions']
```
<!-- or if you're using pydantic prior to v1.3, manually include: OS, python version and pydantic version -->

<!-- Please read the [docs](https://pydantic-docs.helpmanual.io/) and search through issues to
confirm your bug hasn't already been reported. -->

<!-- Where possible please include a self-contained code snippet describing your bug: -->

RFC3986 indicates that a URI with a fragment but not a query is valid, but pydantic does not parse this correctly, instead treating the fragment as part of the path:

```py
from pydantic import AnyUrl, BaseModel


class Model(BaseModel):
    v: AnyUrl


def test_url_fragment_without_query():
    url = Model(v='https://pydantic-docs.helpmanual.io/usage/types/#constrained-types').v
    assert url.query is None
    assert url.fragment == 'constrainted-types'
```

Pytest output:
```
=========================================== test session starts ===========================================
platform darwin -- Python 3.7.7, pytest-5.3.5, py-1.8.1, pluggy-0.13.1
hypothesis profile 'default' -> database=DirectoryBasedExampleDatabase('/Users/andwhite/Projects/lipy-sso_trunk/lipy-sso/.hypothesis/examples')
rootdir: /Users/andwhite/Projects/lipy-sso_trunk/lipy-sso, inifile: setup.cfg
plugins: xdist-1.29.0, requests-mock-1.8.0, html-2.0.1, forked-0.2, lipy-config-base-21.0.8, hypothesis-4.40.0, metadata-1.8.0, cov-2.8.1, lipy-sso-2.1.0
collected 1 item                                                                                          

repro.py F                                                                                          [100%]

================================================ FAILURES =================================================
_____________________________________ test_url_fragment_without_query _____________________________________

    def test_url_fragment_without_query():
        url = Model(v='https://pydantic-docs.helpmanual.io/usage/types/#constrained-types').v
        assert url.query is None
>       assert url.fragment == 'constrainted-types'
E       AssertionError: assert None == 'constrainted-types'
E        +  where None = AnyUrl('https://pydantic-docs.helpmanual.io/usage/types/#constrained-types', scheme='https', host='pydantic-docs.helpmanual.io', tld='io', host_type='domain', path='/usage/types/#constrained-types').fragment

repro.py:11: AssertionError
============================================ 1 failed in 0.13s ============================================
```


Discussion:

Resolving patch:
diff --git a/pydantic/networks.py b/pydantic/networks.py
--- a/pydantic/networks.py
+++ b/pydantic/networks.py
@@ -61,7 +61,7 @@ def url_regex() -> Pattern[str]:
             r'(?P<domain>[^\s/:?#]+)'  # domain, validation occurs later
             r')?'
             r'(?::(?P<port>\d+))?'  # port
-            r'(?P<path>/[^\s?]*)?'  # path
+            r'(?P<path>/[^\s?#]*)?'  # path
             r'(?:\?(?P<query>[^\s#]+))?'  # query
             r'(?:#(?P<fragment>\S+))?',  # fragment
             re.IGNORECASE,


Test patch:
diff --git a/tests/test_networks.py b/tests/test_networks.py
--- a/tests/test_networks.py
+++ b/tests/test_networks.py
@@ -199,6 +199,15 @@ def test_at_in_path():
     assert url.path == '/@handle'
 
 
+def test_fragment_without_query():
+    url = validate_url('https://pydantic-docs.helpmanual.io/usage/types/#constrained-types')
+    assert url.scheme == 'https'
+    assert url.host == 'pydantic-docs.helpmanual.io'
+    assert url.path == '/usage/types/'
+    assert url.query is None
+    assert url.fragment == 'constrained-types'
+
+
 @pytest.mark.parametrize(
     'value',
     [