We are currently solving the following issue within our repository. Here is the issue text:
--- BEGIN ISSUE ---
Video on main API page is broken
See: https://docs.streamlit.io/en/stable/api.html#streamlit.video

![](https://i.imgur.com/6eI7Bv3.png)

--- END ISSUE ---

Below are some code segments, each from a relevant file. One or more of these files may contain bugs.
--- BEGIN FILES ---
Path: `docs/api-examples-source/charts.video.py`
Content:
```
1 import streamlit as st
2 
3 VIDEO_URL = "https://vod-progressive.akamaized.net/exp=1595241944~acl=%2A%2F664785003.mp4%2A~hmac=2a26d355839498b80bbb2c43e6808bd12bc0d2e7920616a8226a1e017c270217/vimeo-prod-skyfire-std-us/01/4526/7/197634410/664785003.mp4?filename=Star+-+6962.mp4"
4 
5 st.video(VIDEO_URL)
6 
7 st.write(
8     """
9     #### Video credit:
10 
11     Creator: User _fxxu_ from _Pixabay_.
12 
13     License: Free for commercial use. No attribution required.
14     https://pixabay.com/en/service/license/
15 
16     URL:
17     https://pixabay.com/en/videos/star-long-exposure-starry-sky-sky-6962/
18 
19 """
20 )
21
```

Path: `lib/streamlit/elements/media_proto.py`
Content:
```
1 # Copyright 2018-2020 Streamlit Inc.
2 #
3 # Licensed under the Apache License, Version 2.0 (the "License");
4 # you may not use this file except in compliance with the License.
5 # You may obtain a copy of the License at
6 #
7 #    http://www.apache.org/licenses/LICENSE-2.0
8 #
9 # Unless required by applicable law or agreed to in writing, software
10 # distributed under the License is distributed on an "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 # See the License for the specific language governing permissions and
13 # limitations under the License.
14 
15 from streamlit import type_util
16 
17 import io
18 import re
19 
20 from validators import url
21 
22 from streamlit import type_util
23 from streamlit.proto.Audio_pb2 import Audio as AudioProto
24 from streamlit.proto.Video_pb2 import Video as VideoProto
25 from streamlit.media_file_manager import media_file_manager
26 
27 
28 class MediaMixin:
29     def audio(dg, data, format="audio/wav", start_time=0):
30         """Display an audio player.
31 
32         Parameters
33         ----------
34         data : str, bytes, BytesIO, numpy.ndarray, or file opened with
35                 io.open().
36             Raw audio data, filename, or a URL pointing to the file to load.
37             Numpy arrays and raw data formats must include all necessary file
38             headers to match specified file format.
39         start_time: int
40             The time from which this element should start playing.
41         format : str
42             The mime type for the audio file. Defaults to 'audio/wav'.
43             See https://tools.ietf.org/html/rfc4281 for more info.
44 
45         Example
46         -------
47         >>> audio_file = open('myaudio.ogg', 'rb')
48         >>> audio_bytes = audio_file.read()
49         >>>
50         >>> st.audio(audio_bytes, format='audio/ogg')
51 
52         .. output::
53            https://static.streamlit.io/0.25.0-2JkNY/index.html?id=Dv3M9sA7Cg8gwusgnVNTHb
54            height: 400px
55 
56         """
57         audio_proto = AudioProto()
58         coordinates = dg._get_coordinates()  # type: ignore
59         marshall_audio(coordinates, audio_proto, data, format, start_time)
60         return dg._enqueue("audio", audio_proto)  # type: ignore
61 
62     def video(dg, data, format="video/mp4", start_time=0):
63         """Display a video player.
64 
65         Parameters
66         ----------
67         data : str, bytes, BytesIO, numpy.ndarray, or file opened with
68                 io.open().
69             Raw video data, filename, or URL pointing to a video to load.
70             Includes support for YouTube URLs.
71             Numpy arrays and raw data formats must include all necessary file
72             headers to match specified file format.
73         format : str
74             The mime type for the video file. Defaults to 'video/mp4'.
75             See https://tools.ietf.org/html/rfc4281 for more info.
76         start_time: int
77             The time from which this element should start playing.
78 
79         Example
80         -------
81         >>> video_file = open('myvideo.mp4', 'rb')
82         >>> video_bytes = video_file.read()
83         >>>
84         >>> st.video(video_bytes)
85 
86         .. output::
87            https://static.streamlit.io/0.61.0-yRE1/index.html?id=LZLtVFFTf1s41yfPExzRu8
88            height: 600px
89 
90         .. note::
91            Some videos may not display if they are encoded using MP4V (which is an export option in OpenCV), as this codec is
92            not widely supported by browsers. Converting your video to H.264 will allow the video to be displayed in Streamlit.
93            See this `StackOverflow post <https://stackoverflow.com/a/49535220/2394542>`_ or this
94            `Streamlit forum post <https://discuss.streamlit.io/t/st-video-doesnt-show-opencv-generated-mp4/3193/2>`_
95            for more information.
96 
97         """
98         video_proto = VideoProto()
99         coordinates = dg._get_coordinates()  # type: ignore
100         marshall_video(coordinates, video_proto, data, format, start_time)
101         return dg._enqueue("video", video_proto)  # type: ignore
102 
103 
104 # Regular expression explained at https://regexr.com/4n2l2 Covers any youtube
105 # URL (incl. shortlinks and embed links) and extracts its code.
106 YOUTUBE_RE = re.compile(
107     # Protocol
108     r"http(?:s?):\/\/"
109     # Domain
110     r"(?:www\.)?youtu(?:be\.com|\.be)\/"
111     # Path and query string
112     r"(?P<watch>(watch\?v=)|embed\/)?(?P<code>[\w\-\_]*)(&(amp;)?[\w\?=]*)?"
113 )
114 
115 
116 def _reshape_youtube_url(url):
117     """Return whether URL is any kind of YouTube embed or watch link.  If so,
118     reshape URL into an embed link suitable for use in an iframe.
119 
120     If not a YouTube URL, return None.
121 
122     Parameters
123     ----------
124         url : str or bytes
125 
126     Example
127     -------
128     >>> print(_reshape_youtube_url('https://youtu.be/_T8LGqJtuGc'))
129 
130     .. output::
131         https://www.youtube.com/embed/_T8LGqJtuGc
132     """
133     match = YOUTUBE_RE.match(url)
134     if match:
135         return "https://www.youtube.com/embed/{code}".format(**match.groupdict())
136     return None
137 
138 
139 def _marshall_av_media(coordinates, proto, data, mimetype):
140     """Fill audio or video proto based on contents of data.
141 
142     Given a string, check if it's a url; if so, send it out without modification.
143     Otherwise assume strings are filenames and let any OS errors raise.
144 
145     Load data either from file or through bytes-processing methods into a
146     MediaFile object.  Pack proto with generated Tornado-based URL.
147     """
148     # Audio and Video methods have already checked if this is a URL by this point.
149 
150     if isinstance(data, str):
151         # Assume it's a filename or blank.  Allow OS-based file errors.
152         with open(data, "rb") as fh:
153             this_file = media_file_manager.add(fh.read(), mimetype, coordinates)
154             proto.url = this_file.url
155             return
156 
157     if data is None:
158         # Allow empty values so media players can be shown without media.
159         return
160 
161     # Assume bytes; try methods until we run out.
162     if isinstance(data, bytes):
163         pass
164     elif isinstance(data, io.BytesIO):
165         data.seek(0)
166         data = data.getvalue()
167     elif isinstance(data, io.RawIOBase) or isinstance(data, io.BufferedReader):
168         data.seek(0)
169         data = data.read()
170     elif type_util.is_type(data, "numpy.ndarray"):
171         data = data.tobytes()
172     else:
173         raise RuntimeError("Invalid binary data format: %s" % type(data))
174 
175     this_file = media_file_manager.add(data, mimetype, coordinates)
176     proto.url = this_file.url
177 
178 
179 def marshall_video(coordinates, proto, data, mimetype="video/mp4", start_time=0):
180     """Marshalls a video proto, using url processors as needed.
181 
182     Parameters
183     ----------
184     coordinates : str
185     proto : the proto to fill. Must have a string field called "data".
186     data : str, bytes, BytesIO, numpy.ndarray, or file opened with
187            io.open().
188         Raw video data or a string with a URL pointing to the video
189         to load. Includes support for YouTube URLs.
190         If passing the raw data, this must include headers and any other
191         bytes required in the actual file.
192     mimetype : str
193         The mime type for the video file. Defaults to 'video/mp4'.
194         See https://tools.ietf.org/html/rfc4281 for more info.
195     start_time : int
196         The time from which this element should start playing. (default: 0)
197     """
198 
199     proto.start_time = start_time
200 
201     # "type" distinguishes between YouTube and non-YouTube links
202     proto.type = VideoProto.Type.NATIVE
203 
204     if isinstance(data, str) and url(data):
205         youtube_url = _reshape_youtube_url(data)
206         if youtube_url:
207             proto.url = youtube_url
208             proto.type = VideoProto.Type.YOUTUBE_IFRAME
209         else:
210             proto.url = data
211 
212     else:
213         _marshall_av_media(coordinates, proto, data, mimetype)
214 
215 
216 def marshall_audio(coordinates, proto, data, mimetype="audio/wav", start_time=0):
217     """Marshalls an audio proto, using data and url processors as needed.
218 
219     Parameters
220     ----------
221     coordinates : str
222     proto : The proto to fill. Must have a string field called "url".
223     data : str, bytes, BytesIO, numpy.ndarray, or file opened with
224             io.open()
225         Raw audio data or a string with a URL pointing to the file to load.
226         If passing the raw data, this must include headers and any other bytes
227         required in the actual file.
228     mimetype : str
229         The mime type for the audio file. Defaults to "audio/wav".
230         See https://tools.ietf.org/html/rfc4281 for more info.
231     start_time : int
232         The time from which this element should start playing. (default: 0)
233     """
234 
235     proto.start_time = start_time
236 
237     if isinstance(data, str) and url(data):
238         proto.url = data
239 
240     else:
241         _marshall_av_media(coordinates, proto, data, mimetype)
242
```
--- END FILES ---

Please first localize the bug based on the issue statement, and then generate a patch according to the `git diff` format fenced by three backticks.

Here is an example:

```diff
diff --git a/examples/server_async.py b/examples/server_async.py
--- a/examples/server_async.py
+++ b/examples/server_async.py
@@ -313,4 +313,4 @@
 
 
 if __name__ == "__main__":
-    asyncio.run(run_async_server("."), debug=True)
+    asyncio.run(run_async_server(), debug=True)
diff --git a/examples/server_sync.py b/examples/server_sync.py
--- a/examples/server_sync.py
+++ b/examples/server_sync.py
@@ -313,5 +313,5 @@
 
 
 if __name__ == "__main__":
-    server = run_sync_server(".")
+    server = run_sync_server()
     server.shutdown()

```

diff --git a/docs/api-examples-source/charts.video.py b/docs/api-examples-source/charts.video.py
--- a/docs/api-examples-source/charts.video.py
+++ b/docs/api-examples-source/charts.video.py
@@ -1,6 +1,6 @@
 import streamlit as st
 
-VIDEO_URL = "https://vod-progressive.akamaized.net/exp=1595241944~acl=%2A%2F664785003.mp4%2A~hmac=2a26d355839498b80bbb2c43e6808bd12bc0d2e7920616a8226a1e017c270217/vimeo-prod-skyfire-std-us/01/4526/7/197634410/664785003.mp4?filename=Star+-+6962.mp4"
+VIDEO_URL = "https://static.streamlit.io/examples/star.mp4"
 
 st.video(VIDEO_URL)
 
diff --git a/lib/streamlit/elements/media_proto.py b/lib/streamlit/elements/media_proto.py
--- a/lib/streamlit/elements/media_proto.py
+++ b/lib/streamlit/elements/media_proto.py
@@ -84,7 +84,7 @@
         >>> st.video(video_bytes)
 
         .. output::
-           https://static.streamlit.io/0.61.0-yRE1/index.html?id=LZLtVFFTf1s41yfPExzRu8
+           https://static.streamlit.io/0.66.0-2BLtg/index.html?id=DzAouvizGRAyuLjkPpR894
            height: 600px
 
         .. note::

{"golden_diff": "diff --git a/docs/api-examples-source/charts.video.py b/docs/api-examples-source/charts.video.py\n--- a/docs/api-examples-source/charts.video.py\n+++ b/docs/api-examples-source/charts.video.py\n@@ -1,6 +1,6 @@\n import streamlit as st\n \n-VIDEO_URL = \"https://vod-progressive.akamaized.net/exp=1595241944~acl=%2A%2F664785003.mp4%2A~hmac=2a26d355839498b80bbb2c43e6808bd12bc0d2e7920616a8226a1e017c270217/vimeo-prod-skyfire-std-us/01/4526/7/197634410/664785003.mp4?filename=Star+-+6962.mp4\"\n+VIDEO_URL = \"https://static.streamlit.io/examples/star.mp4\"\n \n st.video(VIDEO_URL)\n \ndiff --git a/lib/streamlit/elements/media_proto.py b/lib/streamlit/elements/media_proto.py\n--- a/lib/streamlit/elements/media_proto.py\n+++ b/lib/streamlit/elements/media_proto.py\n@@ -84,7 +84,7 @@\n         >>> st.video(video_bytes)\n \n         .. output::\n-           https://static.streamlit.io/0.61.0-yRE1/index.html?id=LZLtVFFTf1s41yfPExzRu8\n+           https://static.streamlit.io/0.66.0-2BLtg/index.html?id=DzAouvizGRAyuLjkPpR894\n            height: 600px\n \n         .. note::\n", "issue": "Video on main API page is broken\nSee: https://docs.streamlit.io/en/stable/api.html#streamlit.video\r\n\r\n![](https://i.imgur.com/6eI7Bv3.png)\n", "before_files": [{"content": "import streamlit as st\n\nVIDEO_URL = \"https://vod-progressive.akamaized.net/exp=1595241944~acl=%2A%2F664785003.mp4%2A~hmac=2a26d355839498b80bbb2c43e6808bd12bc0d2e7920616a8226a1e017c270217/vimeo-prod-skyfire-std-us/01/4526/7/197634410/664785003.mp4?filename=Star+-+6962.mp4\"\n\nst.video(VIDEO_URL)\n\nst.write(\n    \"\"\"\n    #### Video credit:\n\n    Creator: User _fxxu_ from _Pixabay_.\n\n    License: Free for commercial use. No attribution required.\n    https://pixabay.com/en/service/license/\n\n    URL:\n    https://pixabay.com/en/videos/star-long-exposure-starry-sky-sky-6962/\n\n\"\"\"\n)\n", "path": "docs/api-examples-source/charts.video.py"}, {"content": "# Copyright 2018-2020 Streamlit Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n#    http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\nfrom streamlit import type_util\n\nimport io\nimport re\n\nfrom validators import url\n\nfrom streamlit import type_util\nfrom streamlit.proto.Audio_pb2 import Audio as AudioProto\nfrom streamlit.proto.Video_pb2 import Video as VideoProto\nfrom streamlit.media_file_manager import media_file_manager\n\n\nclass MediaMixin:\n    def audio(dg, data, format=\"audio/wav\", start_time=0):\n        \"\"\"Display an audio player.\n\n        Parameters\n        ----------\n        data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n                io.open().\n            Raw audio data, filename, or a URL pointing to the file to load.\n            Numpy arrays and raw data formats must include all necessary file\n            headers to match specified file format.\n        start_time: int\n            The time from which this element should start playing.\n        format : str\n            The mime type for the audio file. Defaults to 'audio/wav'.\n            See https://tools.ietf.org/html/rfc4281 for more info.\n\n        Example\n        -------\n        >>> audio_file = open('myaudio.ogg', 'rb')\n        >>> audio_bytes = audio_file.read()\n        >>>\n        >>> st.audio(audio_bytes, format='audio/ogg')\n\n        .. output::\n           https://static.streamlit.io/0.25.0-2JkNY/index.html?id=Dv3M9sA7Cg8gwusgnVNTHb\n           height: 400px\n\n        \"\"\"\n        audio_proto = AudioProto()\n        coordinates = dg._get_coordinates()  # type: ignore\n        marshall_audio(coordinates, audio_proto, data, format, start_time)\n        return dg._enqueue(\"audio\", audio_proto)  # type: ignore\n\n    def video(dg, data, format=\"video/mp4\", start_time=0):\n        \"\"\"Display a video player.\n\n        Parameters\n        ----------\n        data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n                io.open().\n            Raw video data, filename, or URL pointing to a video to load.\n            Includes support for YouTube URLs.\n            Numpy arrays and raw data formats must include all necessary file\n            headers to match specified file format.\n        format : str\n            The mime type for the video file. Defaults to 'video/mp4'.\n            See https://tools.ietf.org/html/rfc4281 for more info.\n        start_time: int\n            The time from which this element should start playing.\n\n        Example\n        -------\n        >>> video_file = open('myvideo.mp4', 'rb')\n        >>> video_bytes = video_file.read()\n        >>>\n        >>> st.video(video_bytes)\n\n        .. output::\n           https://static.streamlit.io/0.61.0-yRE1/index.html?id=LZLtVFFTf1s41yfPExzRu8\n           height: 600px\n\n        .. note::\n           Some videos may not display if they are encoded using MP4V (which is an export option in OpenCV), as this codec is\n           not widely supported by browsers. Converting your video to H.264 will allow the video to be displayed in Streamlit.\n           See this `StackOverflow post <https://stackoverflow.com/a/49535220/2394542>`_ or this\n           `Streamlit forum post <https://discuss.streamlit.io/t/st-video-doesnt-show-opencv-generated-mp4/3193/2>`_\n           for more information.\n\n        \"\"\"\n        video_proto = VideoProto()\n        coordinates = dg._get_coordinates()  # type: ignore\n        marshall_video(coordinates, video_proto, data, format, start_time)\n        return dg._enqueue(\"video\", video_proto)  # type: ignore\n\n\n# Regular expression explained at https://regexr.com/4n2l2 Covers any youtube\n# URL (incl. shortlinks and embed links) and extracts its code.\nYOUTUBE_RE = re.compile(\n    # Protocol\n    r\"http(?:s?):\\/\\/\"\n    # Domain\n    r\"(?:www\\.)?youtu(?:be\\.com|\\.be)\\/\"\n    # Path and query string\n    r\"(?P<watch>(watch\\?v=)|embed\\/)?(?P<code>[\\w\\-\\_]*)(&(amp;)?[\\w\\?=]*)?\"\n)\n\n\ndef _reshape_youtube_url(url):\n    \"\"\"Return whether URL is any kind of YouTube embed or watch link.  If so,\n    reshape URL into an embed link suitable for use in an iframe.\n\n    If not a YouTube URL, return None.\n\n    Parameters\n    ----------\n        url : str or bytes\n\n    Example\n    -------\n    >>> print(_reshape_youtube_url('https://youtu.be/_T8LGqJtuGc'))\n\n    .. output::\n        https://www.youtube.com/embed/_T8LGqJtuGc\n    \"\"\"\n    match = YOUTUBE_RE.match(url)\n    if match:\n        return \"https://www.youtube.com/embed/{code}\".format(**match.groupdict())\n    return None\n\n\ndef _marshall_av_media(coordinates, proto, data, mimetype):\n    \"\"\"Fill audio or video proto based on contents of data.\n\n    Given a string, check if it's a url; if so, send it out without modification.\n    Otherwise assume strings are filenames and let any OS errors raise.\n\n    Load data either from file or through bytes-processing methods into a\n    MediaFile object.  Pack proto with generated Tornado-based URL.\n    \"\"\"\n    # Audio and Video methods have already checked if this is a URL by this point.\n\n    if isinstance(data, str):\n        # Assume it's a filename or blank.  Allow OS-based file errors.\n        with open(data, \"rb\") as fh:\n            this_file = media_file_manager.add(fh.read(), mimetype, coordinates)\n            proto.url = this_file.url\n            return\n\n    if data is None:\n        # Allow empty values so media players can be shown without media.\n        return\n\n    # Assume bytes; try methods until we run out.\n    if isinstance(data, bytes):\n        pass\n    elif isinstance(data, io.BytesIO):\n        data.seek(0)\n        data = data.getvalue()\n    elif isinstance(data, io.RawIOBase) or isinstance(data, io.BufferedReader):\n        data.seek(0)\n        data = data.read()\n    elif type_util.is_type(data, \"numpy.ndarray\"):\n        data = data.tobytes()\n    else:\n        raise RuntimeError(\"Invalid binary data format: %s\" % type(data))\n\n    this_file = media_file_manager.add(data, mimetype, coordinates)\n    proto.url = this_file.url\n\n\ndef marshall_video(coordinates, proto, data, mimetype=\"video/mp4\", start_time=0):\n    \"\"\"Marshalls a video proto, using url processors as needed.\n\n    Parameters\n    ----------\n    coordinates : str\n    proto : the proto to fill. Must have a string field called \"data\".\n    data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n           io.open().\n        Raw video data or a string with a URL pointing to the video\n        to load. Includes support for YouTube URLs.\n        If passing the raw data, this must include headers and any other\n        bytes required in the actual file.\n    mimetype : str\n        The mime type for the video file. Defaults to 'video/mp4'.\n        See https://tools.ietf.org/html/rfc4281 for more info.\n    start_time : int\n        The time from which this element should start playing. (default: 0)\n    \"\"\"\n\n    proto.start_time = start_time\n\n    # \"type\" distinguishes between YouTube and non-YouTube links\n    proto.type = VideoProto.Type.NATIVE\n\n    if isinstance(data, str) and url(data):\n        youtube_url = _reshape_youtube_url(data)\n        if youtube_url:\n            proto.url = youtube_url\n            proto.type = VideoProto.Type.YOUTUBE_IFRAME\n        else:\n            proto.url = data\n\n    else:\n        _marshall_av_media(coordinates, proto, data, mimetype)\n\n\ndef marshall_audio(coordinates, proto, data, mimetype=\"audio/wav\", start_time=0):\n    \"\"\"Marshalls an audio proto, using data and url processors as needed.\n\n    Parameters\n    ----------\n    coordinates : str\n    proto : The proto to fill. Must have a string field called \"url\".\n    data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n            io.open()\n        Raw audio data or a string with a URL pointing to the file to load.\n        If passing the raw data, this must include headers and any other bytes\n        required in the actual file.\n    mimetype : str\n        The mime type for the audio file. Defaults to \"audio/wav\".\n        See https://tools.ietf.org/html/rfc4281 for more info.\n    start_time : int\n        The time from which this element should start playing. (default: 0)\n    \"\"\"\n\n    proto.start_time = start_time\n\n    if isinstance(data, str) and url(data):\n        proto.url = data\n\n    else:\n        _marshall_av_media(coordinates, proto, data, mimetype)\n", "path": "lib/streamlit/elements/media_proto.py"}], "after_files": [{"content": "import streamlit as st\n\nVIDEO_URL = \"https://static.streamlit.io/examples/star.mp4\"\n\nst.video(VIDEO_URL)\n\nst.write(\n    \"\"\"\n    #### Video credit:\n\n    Creator: User _fxxu_ from _Pixabay_.\n\n    License: Free for commercial use. No attribution required.\n    https://pixabay.com/en/service/license/\n\n    URL:\n    https://pixabay.com/en/videos/star-long-exposure-starry-sky-sky-6962/\n\n\"\"\"\n)\n", "path": "docs/api-examples-source/charts.video.py"}, {"content": "# Copyright 2018-2020 Streamlit Inc.\n#\n# Licensed under the Apache License, Version 2.0 (the \"License\");\n# you may not use this file except in compliance with the License.\n# You may obtain a copy of the License at\n#\n#    http://www.apache.org/licenses/LICENSE-2.0\n#\n# Unless required by applicable law or agreed to in writing, software\n# distributed under the License is distributed on an \"AS IS\" BASIS,\n# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n# See the License for the specific language governing permissions and\n# limitations under the License.\n\nfrom streamlit import type_util\n\nimport io\nimport re\n\nfrom validators import url\n\nfrom streamlit import type_util\nfrom streamlit.proto.Audio_pb2 import Audio as AudioProto\nfrom streamlit.proto.Video_pb2 import Video as VideoProto\nfrom streamlit.media_file_manager import media_file_manager\n\n\nclass MediaMixin:\n    def audio(dg, data, format=\"audio/wav\", start_time=0):\n        \"\"\"Display an audio player.\n\n        Parameters\n        ----------\n        data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n                io.open().\n            Raw audio data, filename, or a URL pointing to the file to load.\n            Numpy arrays and raw data formats must include all necessary file\n            headers to match specified file format.\n        start_time: int\n            The time from which this element should start playing.\n        format : str\n            The mime type for the audio file. Defaults to 'audio/wav'.\n            See https://tools.ietf.org/html/rfc4281 for more info.\n\n        Example\n        -------\n        >>> audio_file = open('myaudio.ogg', 'rb')\n        >>> audio_bytes = audio_file.read()\n        >>>\n        >>> st.audio(audio_bytes, format='audio/ogg')\n\n        .. output::\n           https://static.streamlit.io/0.25.0-2JkNY/index.html?id=Dv3M9sA7Cg8gwusgnVNTHb\n           height: 400px\n\n        \"\"\"\n        audio_proto = AudioProto()\n        coordinates = dg._get_coordinates()  # type: ignore\n        marshall_audio(coordinates, audio_proto, data, format, start_time)\n        return dg._enqueue(\"audio\", audio_proto)  # type: ignore\n\n    def video(dg, data, format=\"video/mp4\", start_time=0):\n        \"\"\"Display a video player.\n\n        Parameters\n        ----------\n        data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n                io.open().\n            Raw video data, filename, or URL pointing to a video to load.\n            Includes support for YouTube URLs.\n            Numpy arrays and raw data formats must include all necessary file\n            headers to match specified file format.\n        format : str\n            The mime type for the video file. Defaults to 'video/mp4'.\n            See https://tools.ietf.org/html/rfc4281 for more info.\n        start_time: int\n            The time from which this element should start playing.\n\n        Example\n        -------\n        >>> video_file = open('myvideo.mp4', 'rb')\n        >>> video_bytes = video_file.read()\n        >>>\n        >>> st.video(video_bytes)\n\n        .. output::\n           https://static.streamlit.io/0.66.0-2BLtg/index.html?id=DzAouvizGRAyuLjkPpR894\n           height: 600px\n\n        .. note::\n           Some videos may not display if they are encoded using MP4V (which is an export option in OpenCV), as this codec is\n           not widely supported by browsers. Converting your video to H.264 will allow the video to be displayed in Streamlit.\n           See this `StackOverflow post <https://stackoverflow.com/a/49535220/2394542>`_ or this\n           `Streamlit forum post <https://discuss.streamlit.io/t/st-video-doesnt-show-opencv-generated-mp4/3193/2>`_\n           for more information.\n\n        \"\"\"\n        video_proto = VideoProto()\n        coordinates = dg._get_coordinates()  # type: ignore\n        marshall_video(coordinates, video_proto, data, format, start_time)\n        return dg._enqueue(\"video\", video_proto)  # type: ignore\n\n\n# Regular expression explained at https://regexr.com/4n2l2 Covers any youtube\n# URL (incl. shortlinks and embed links) and extracts its code.\nYOUTUBE_RE = re.compile(\n    # Protocol\n    r\"http(?:s?):\\/\\/\"\n    # Domain\n    r\"(?:www\\.)?youtu(?:be\\.com|\\.be)\\/\"\n    # Path and query string\n    r\"(?P<watch>(watch\\?v=)|embed\\/)?(?P<code>[\\w\\-\\_]*)(&(amp;)?[\\w\\?=]*)?\"\n)\n\n\ndef _reshape_youtube_url(url):\n    \"\"\"Return whether URL is any kind of YouTube embed or watch link.  If so,\n    reshape URL into an embed link suitable for use in an iframe.\n\n    If not a YouTube URL, return None.\n\n    Parameters\n    ----------\n        url : str or bytes\n\n    Example\n    -------\n    >>> print(_reshape_youtube_url('https://youtu.be/_T8LGqJtuGc'))\n\n    .. output::\n        https://www.youtube.com/embed/_T8LGqJtuGc\n    \"\"\"\n    match = YOUTUBE_RE.match(url)\n    if match:\n        return \"https://www.youtube.com/embed/{code}\".format(**match.groupdict())\n    return None\n\n\ndef _marshall_av_media(coordinates, proto, data, mimetype):\n    \"\"\"Fill audio or video proto based on contents of data.\n\n    Given a string, check if it's a url; if so, send it out without modification.\n    Otherwise assume strings are filenames and let any OS errors raise.\n\n    Load data either from file or through bytes-processing methods into a\n    MediaFile object.  Pack proto with generated Tornado-based URL.\n    \"\"\"\n    # Audio and Video methods have already checked if this is a URL by this point.\n\n    if isinstance(data, str):\n        # Assume it's a filename or blank.  Allow OS-based file errors.\n        with open(data, \"rb\") as fh:\n            this_file = media_file_manager.add(fh.read(), mimetype, coordinates)\n            proto.url = this_file.url\n            return\n\n    if data is None:\n        # Allow empty values so media players can be shown without media.\n        return\n\n    # Assume bytes; try methods until we run out.\n    if isinstance(data, bytes):\n        pass\n    elif isinstance(data, io.BytesIO):\n        data.seek(0)\n        data = data.getvalue()\n    elif isinstance(data, io.RawIOBase) or isinstance(data, io.BufferedReader):\n        data.seek(0)\n        data = data.read()\n    elif type_util.is_type(data, \"numpy.ndarray\"):\n        data = data.tobytes()\n    else:\n        raise RuntimeError(\"Invalid binary data format: %s\" % type(data))\n\n    this_file = media_file_manager.add(data, mimetype, coordinates)\n    proto.url = this_file.url\n\n\ndef marshall_video(coordinates, proto, data, mimetype=\"video/mp4\", start_time=0):\n    \"\"\"Marshalls a video proto, using url processors as needed.\n\n    Parameters\n    ----------\n    coordinates : str\n    proto : the proto to fill. Must have a string field called \"data\".\n    data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n           io.open().\n        Raw video data or a string with a URL pointing to the video\n        to load. Includes support for YouTube URLs.\n        If passing the raw data, this must include headers and any other\n        bytes required in the actual file.\n    mimetype : str\n        The mime type for the video file. Defaults to 'video/mp4'.\n        See https://tools.ietf.org/html/rfc4281 for more info.\n    start_time : int\n        The time from which this element should start playing. (default: 0)\n    \"\"\"\n\n    proto.start_time = start_time\n\n    # \"type\" distinguishes between YouTube and non-YouTube links\n    proto.type = VideoProto.Type.NATIVE\n\n    if isinstance(data, str) and url(data):\n        youtube_url = _reshape_youtube_url(data)\n        if youtube_url:\n            proto.url = youtube_url\n            proto.type = VideoProto.Type.YOUTUBE_IFRAME\n        else:\n            proto.url = data\n\n    else:\n        _marshall_av_media(coordinates, proto, data, mimetype)\n\n\ndef marshall_audio(coordinates, proto, data, mimetype=\"audio/wav\", start_time=0):\n    \"\"\"Marshalls an audio proto, using data and url processors as needed.\n\n    Parameters\n    ----------\n    coordinates : str\n    proto : The proto to fill. Must have a string field called \"url\".\n    data : str, bytes, BytesIO, numpy.ndarray, or file opened with\n            io.open()\n        Raw audio data or a string with a URL pointing to the file to load.\n        If passing the raw data, this must include headers and any other bytes\n        required in the actual file.\n    mimetype : str\n        The mime type for the audio file. Defaults to \"audio/wav\".\n        See https://tools.ietf.org/html/rfc4281 for more info.\n    start_time : int\n        The time from which this element should start playing. (default: 0)\n    \"\"\"\n\n    proto.start_time = start_time\n\n    if isinstance(data, str) and url(data):\n        proto.url = data\n\n    else:\n        _marshall_av_media(coordinates, proto, data, mimetype)\n", "path": "lib/streamlit/elements/media_proto.py"}]}