Merge pull request #570 from gradio-app/fixes-https-cors

Adds support for https
This commit is contained in:
Abubakar Abid 2022-02-09 00:22:34 -05:00 committed by GitHub
commit 31fbdd9e40
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 28 additions and 8 deletions

View File

@ -628,6 +628,8 @@ class Interface:
encrypt: bool = False,
cache_examples: bool = False,
favicon_path: Optional[str] = None,
ssl_keyfile: Optional[str] = None,
ssl_certfile: Optional[str] = None,
) -> Tuple[flask.Flask, str, str]:
"""
Launches the webserver that serves the UI for the interface.
@ -649,7 +651,9 @@ class Interface:
height (int): The height in pixels of the iframe element containing the interface (used if inline=True)
encrypt (bool): If True, flagged data will be encrypted by key provided by creator at launch
cache_examples (bool): If True, examples outputs will be processed and cached in a folder, and will be used if a user uses an example input.
favicon_path (str): If a path to an file (.png, .gif, or .ico) is provided, it will be used as the favicon for the web page.
favicon_path (str): If a path to a file (.png, .gif, or .ico) is provided, it will be used as the favicon for the web page.
ssl_keyfile (str): If a path to a file is provided, will use this as the private key file to create a local server running on https.
ssl_certfile (str): If a path to a file is provided, will use this as the signed certificate for https. Needs to be provided if ssl_keyfile is provided.
Returns:
app (flask.Flask): Flask app object
path_to_local_server (str): Locally accessible link
@ -691,9 +695,9 @@ class Interface:
cache_interface_examples(self)
server_port, path_to_local_server, app, server = networking.start_server(
self, server_name, server_port
self, server_name, server_port, ssl_keyfile, ssl_certfile
)
self.local_url = path_to_local_server
self.server_port = server_port
self.status = "RUNNING"
@ -719,7 +723,6 @@ class Interface:
if private_endpoint is not None:
share = True
self.share = share
if share:
try:
@ -734,10 +737,14 @@ class Interface:
if self.analytics_enabled:
utils.error_analytics(self.ip_address, "Not able to set up tunnel")
share_url = None
share = False
print(strings.en["COULD_NOT_GET_SHARE_LINK"])
else:
print(strings.en["PUBLIC_SHARE_TRUE"])
share_url = None
self.share = share
if inbrowser:
link = share_url if share else path_to_local_server
webbrowser.open(link)

View File

@ -77,6 +77,8 @@ def start_server(
interface: Interface,
server_name: Optional[str] = None,
server_port: Optional[int] = None,
ssl_keyfile: Optional[str] = None,
ssl_certfile: Optional[str] = None,
) -> Tuple[int, str, fastapi.FastAPI, threading.Thread, None]:
"""Launches a local server running the provided Interface
Parameters:
@ -84,6 +86,8 @@ def start_server(
server_name: to make app accessible on local network, set this to "0.0.0.0". Can be set by environment variable GRADIO_SERVER_NAME.
server_port: will start gradio app on this port (if available). Can be set by environment variable GRADIO_SERVER_PORT.
auth: If provided, username and password (or list of username-password tuples) required to access interface. Can also provide function that takes username and password and returns True if valid login.
ssl_keyfile: If a path to a file is provided, will use this as the private key file to create a local server running on https.
ssl_certfile: If a path to a file is provided, will use this as the signed certificate for https. Needs to be provided if ssl_keyfile is provided.
"""
server_name = server_name or LOCALHOST_NAME
# if port is not specified, search for first available port
@ -105,7 +109,14 @@ def start_server(
port = server_port
url_host_name = "localhost" if server_name == "0.0.0.0" else server_name
path_to_local_server = "http://{}:{}/".format(url_host_name, port)
if ssl_keyfile is not None:
if ssl_certfile is None:
raise ValueError("ssl_certfile must be provided if ssl_keyfile is provided.")
path_to_local_server = "https://{}:{}/".format(url_host_name, port)
else:
path_to_local_server = "http://{}:{}/".format(url_host_name, port)
auth = interface.auth
if auth is not None:
if not callable(auth):
@ -130,7 +141,8 @@ def start_server(
if interface.save_to is not None: # Used for selenium tests
interface.save_to["port"] = port
config = uvicorn.Config(app=app, port=port, host=server_name, log_level="warning")
config = uvicorn.Config(app=app, port=port, host=server_name, log_level="warning",
ssl_keyfile=ssl_keyfile, ssl_certfile=ssl_certfile)
server = Server(config=config)
server.run_in_thread()
return port, path_to_local_server, app, server
@ -163,7 +175,7 @@ def url_ok(url: str) -> bool:
try:
for _ in range(5):
time.sleep(0.500)
r = requests.head(url, timeout=3)
r = requests.head(url, timeout=3, verify=False)
if r.status_code in (200, 401, 302): # 401 or 302 if auth is set
return True
except (ConnectionError, requests.exceptions.ConnectionError):

View File

@ -7,6 +7,7 @@ MESSAGING_API_ENDPOINT = "https://api.gradio.app/gradio-messaging/en"
en = {
"RUNNING_LOCALLY": "Running on local URL: {}",
"SHARE_LINK_DISPLAY": "Running on public URL: {}",
"COULD_NOT_GET_SHARE_LINK": "\nCould not create share link, please check your internet connection.",
"COLAB_NO_LOCAL": "Cannot display local interface on google colab, public link created.",
"PUBLIC_SHARE_TRUE": "\nTo create a public link, set `share=True` in `launch()`.",
"MODEL_PUBLICLY_AVAILABLE_URL": "Model available publicly at: {} (may take up to a minute for link to be usable)",
@ -18,7 +19,7 @@ en = {
"COLAB_DEBUG_TRUE": "Colab notebook detected. This cell will run indefinitely so that you can see errors and logs. "
"To turn off, set debug=False in launch().",
"COLAB_DEBUG_FALSE": "Colab notebook detected. To show errors in colab notebook, set debug=True in launch()",
"SHARE_LINK_MESSAGE": "\nThis share link expires in 72 hours. For free permanent hosting, check out Spaces (https://huggingface.co/spaces)",
"SHARE_LINK_MESSAGE": "\nThis share link expires in 72 hours. For free permanent hosting, check out Spaces (https://www.huggingface.co/spaces)",
"PRIVATE_LINK_MESSAGE": "Since this is a private endpoint, this share link will never expire.",
"INLINE_DISPLAY_BELOW": "Interface loading below...",
"MEDIA_PERMISSIONS_IN_COLAB": "Your interface requires microphone or webcam permissions - this may cause issues in Colab. Use the External URL in case of issues.",