Skip to content

Commit

Permalink
Move scripts from old website to CI (#5271)
Browse files Browse the repository at this point in the history
* delete old version docs script

* script and workflow

* if merged

* syntax

* changes

* add missing demos

* hide state component

* fix html component demo

* fix model3d guide

* fix workflow

* fix issues with oauth and main

* demo notebooks

* add changeset

* demo notebook

* refactor into existing workflows

* remove assert in networking server

* add changeset

* Fix type check

* lint

---------

Co-authored-by: gradio-pr-bot <gradio-pr-bot@users.noreply.github.com>
Co-authored-by: freddyaboulton <alfonsoboulton@gmail.com>
  • Loading branch information
3 people committed Aug 30, 2023
1 parent 6466652 commit 97c3c7b
Show file tree
Hide file tree
Showing 19 changed files with 180 additions and 69 deletions.
6 changes: 6 additions & 0 deletions .changeset/silent-pens-decide.md
@@ -0,0 +1,6 @@
---
"gradio": minor
"website": minor
---

feat:Move scripts from old website to CI
11 changes: 9 additions & 2 deletions .github/workflows/build-pr.yml
@@ -1,6 +1,9 @@
name: Build PR Artifacts

on:
push:
branches:
- main
pull_request:
branches:
- main
Expand Down Expand Up @@ -35,9 +38,13 @@ jobs:
- name: Get PR Number
id: get_pr_number
run: |
python -c "import os;print(os.environ['GITHUB_REF'].split('/')[2])" > pr_number.txt
echo "PR_NUMBER=$(cat pr_number.txt)" >> $GITHUB_OUTPUT
echo "GRADIO_VERSION=$(python -c 'import requests;print(requests.get("https://pypi.org/pypi/gradio/json").json()["info"]["version"])')" >> $GITHUB_OUTPUT
if ${{ github.event_name == 'pull_request' }}; then
python -c "import os;print(os.environ['GITHUB_REF'].split('/')[2])" > pr_number.txt
echo "PR_NUMBER=$(cat pr_number.txt)" >> $GITHUB_OUTPUT
else
echo "PR_NUMBER='main'" >> $GITHUB_OUTPUT
fi
- name: Build pr package
run: |
echo ${{ steps.get_pr_number.outputs.GRADIO_VERSION }} > gradio/version.txt
Expand Down
43 changes: 0 additions & 43 deletions .github/workflows/build-version-docs.yml

This file was deleted.

14 changes: 11 additions & 3 deletions .github/workflows/deploy-pr-to-spaces.yml
Expand Up @@ -14,9 +14,6 @@ jobs:
sha: ${{ steps.set-outputs.outputs.gh_sha }}
gradio_version: ${{ steps.set-outputs.outputs.gradio_version }}
runs-on: ubuntu-latest
if: >
github.event.workflow_run.event == 'pull_request' &&
github.event.workflow_run.conclusion == 'success'
steps:
- uses: actions/checkout@v3
- name: Install Python
Expand Down Expand Up @@ -51,13 +48,24 @@ jobs:
- run: unzip all_demos.zip -d all_demos
- run: cp -R all_demos/* demo/all_demos
- name: Upload demo to spaces
if: >
github.event.workflow_run.event == 'pull_request' &&
github.event.workflow_run.conclusion == 'success'
id: upload-demo
run: |
python scripts/upload_demo_to_space.py all_demos \
gradio-pr-deploys/pr-${{ steps.set-outputs.outputs.pr_number }}-all-demos \
${{ secrets.SPACES_DEPLOY_TOKEN }} \
--gradio-version ${{ steps.set-outputs.outputs.gradio_version }} > url.txt
echo "SPACE_URL=$(cat url.txt)" >> $GITHUB_OUTPUT
- name: Upload website demos
if: >
github.event.workflow_run.event == 'push' &&
github.event.workflow_run.conclusion == 'success'
run: |
python scripts/upload_website_demos.py --AUTH_TOKEN ${{ secrets.SPACES_DEPLOY_TOKEN }} \
--WHEEL_URL https://gradio-builds.s3.amazonaws.com/${{ steps.set-outputs.outputs.gh_sha }}/ \
comment-spaces-success:
uses: "./.github/workflows/comment-queue.yml"
needs: [deploy-current-pr]
Expand Down
1 change: 1 addition & 0 deletions demo/duplicatebutton_component/run.ipynb
@@ -0,0 +1 @@
{"cells": [{"cell_type": "markdown", "id": 302934307671667531413257853548643485645, "metadata": {}, "source": ["# Gradio Demo: duplicatebutton_component"]}, {"cell_type": "code", "execution_count": null, "id": 272996653310673477252411125948039410165, "metadata": {}, "outputs": [], "source": ["!pip install -q gradio "]}, {"cell_type": "code", "execution_count": null, "id": 288918539441861185822528903084949547379, "metadata": {}, "outputs": [], "source": ["import gradio as gr \n", "\n", "with gr.Blocks() as demo:\n", " gr.DuplicateButton()\n", "\n", "demo.launch()"]}], "metadata": {}, "nbformat": 4, "nbformat_minor": 5}
6 changes: 6 additions & 0 deletions demo/duplicatebutton_component/run.py
@@ -0,0 +1,6 @@
import gradio as gr

with gr.Blocks() as demo:
gr.DuplicateButton()

demo.launch()
2 changes: 1 addition & 1 deletion demo/html_component/run.ipynb
@@ -1 +1 @@
{"cells": [{"cell_type": "markdown", "id": 302934307671667531413257853548643485645, "metadata": {}, "source": ["# Gradio Demo: html_component"]}, {"cell_type": "code", "execution_count": null, "id": 272996653310673477252411125948039410165, "metadata": {}, "outputs": [], "source": ["!pip install -q gradio "]}, {"cell_type": "code", "execution_count": null, "id": 288918539441861185822528903084949547379, "metadata": {}, "outputs": [], "source": ["import gradio as gr \n", "\n", "with gr.Blocks() as demo:\n", " gr.HTML(value=\"<p style='margin-top: 1rem, margin-bottom: 1rem'>Gradio Docs Readers: <img src='https://visitor-badge.glitch.me/badge?page_id=gradio-docs-visitor-badge' alt='visitor badge' style='display: inline-block'/></p>\")\n", "\n", "demo.launch()"]}], "metadata": {}, "nbformat": 4, "nbformat_minor": 5}
{"cells": [{"cell_type": "markdown", "id": 302934307671667531413257853548643485645, "metadata": {}, "source": ["# Gradio Demo: html_component"]}, {"cell_type": "code", "execution_count": null, "id": 272996653310673477252411125948039410165, "metadata": {}, "outputs": [], "source": ["!pip install -q gradio "]}, {"cell_type": "code", "execution_count": null, "id": 288918539441861185822528903084949547379, "metadata": {}, "outputs": [], "source": ["import gradio as gr \n", "\n", "with gr.Blocks() as demo:\n", " gr.HTML(value=\"<p style='margin-top: 1rem, margin-bottom: 1rem'>This <em>example</em> was <strong>written</strong> in <a href='https://en.wikipedia.org/wiki/HTML' _target='blank'>HTML</a> </p>\")\n", "\n", "demo.launch()"]}], "metadata": {}, "nbformat": 4, "nbformat_minor": 5}
2 changes: 1 addition & 1 deletion demo/html_component/run.py
@@ -1,6 +1,6 @@
import gradio as gr

with gr.Blocks() as demo:
gr.HTML(value="<p style='margin-top: 1rem, margin-bottom: 1rem'>Gradio Docs Readers: <img src='https://visitor-badge.glitch.me/badge?page_id=gradio-docs-visitor-badge' alt='visitor badge' style='display: inline-block'/></p>")
gr.HTML(value="<p style='margin-top: 1rem, margin-bottom: 1rem'>This <em>example</em> was <strong>written</strong> in <a href='https://en.wikipedia.org/wiki/HTML' _target='blank'>HTML</a> </p>")

demo.launch()
1 change: 1 addition & 0 deletions demo/loginbutton_component/requirements.txt
@@ -0,0 +1 @@
gradio[oauth]
1 change: 1 addition & 0 deletions demo/loginbutton_component/run.ipynb
@@ -0,0 +1 @@
{"cells": [{"cell_type": "markdown", "id": 302934307671667531413257853548643485645, "metadata": {}, "source": ["# Gradio Demo: loginbutton_component"]}, {"cell_type": "code", "execution_count": null, "id": 272996653310673477252411125948039410165, "metadata": {}, "outputs": [], "source": ["!pip install -q gradio gradio[oauth]"]}, {"cell_type": "code", "execution_count": null, "id": 288918539441861185822528903084949547379, "metadata": {}, "outputs": [], "source": ["import gradio as gr \n", "\n", "with gr.Blocks() as demo:\n", " gr.LoginButton()\n", "\n", "demo.launch()"]}], "metadata": {}, "nbformat": 4, "nbformat_minor": 5}
6 changes: 6 additions & 0 deletions demo/loginbutton_component/run.py
@@ -0,0 +1,6 @@
import gradio as gr

with gr.Blocks() as demo:
gr.LoginButton()

demo.launch()
1 change: 1 addition & 0 deletions demo/logoutbutton_component/requirements.txt
@@ -0,0 +1 @@
gradio[oauth]
1 change: 1 addition & 0 deletions demo/logoutbutton_component/run.ipynb
@@ -0,0 +1 @@
{"cells": [{"cell_type": "markdown", "id": 302934307671667531413257853548643485645, "metadata": {}, "source": ["# Gradio Demo: logoutbutton_component"]}, {"cell_type": "code", "execution_count": null, "id": 272996653310673477252411125948039410165, "metadata": {}, "outputs": [], "source": ["!pip install -q gradio gradio[oauth]"]}, {"cell_type": "code", "execution_count": null, "id": 288918539441861185822528903084949547379, "metadata": {}, "outputs": [], "source": ["import gradio as gr \n", "\n", "with gr.Blocks() as demo:\n", " gr.LogoutButton()\n", "\n", "demo.launch()"]}], "metadata": {}, "nbformat": 4, "nbformat_minor": 5}
6 changes: 6 additions & 0 deletions demo/logoutbutton_component/run.py
@@ -0,0 +1,6 @@
import gradio as gr

with gr.Blocks() as demo:
gr.LogoutButton()

demo.launch()
2 changes: 1 addition & 1 deletion gradio/ipython_ext.py
Expand Up @@ -42,7 +42,7 @@ def current_cell(self):
@property
def running_app(self) -> App:
assert self.running_demo.server
return self.running_demo.server.running_app
return self.running_demo.server.running_app # type: ignore

@property
def running_demo(self):
Expand Down
1 change: 0 additions & 1 deletion gradio/networking.py
Expand Up @@ -43,7 +43,6 @@ class Server(uvicorn.Server):
def __init__(
self, config: Config, reloader: SourceFileReloader | None = None
) -> None:
assert isinstance(config.app, App)
self.running_app = config.app
super().__init__(config)
self.reloader = reloader
Expand Down
34 changes: 17 additions & 17 deletions guides/08_other-tutorials/how-to-use-3D-model-component.md
@@ -1,6 +1,6 @@
# How to Use the 3D Model Component

Related spaces: https://huggingface.co/spaces/dawood/Model3D, https://huggingface.co/spaces/radames/PIFu-Clothed-Human-Digitization, https://huggingface.co/spaces/radames/dpt-depth-estimation-3d-obj
Related spaces: https://huggingface.co/spaces/gradio/Model3D, https://huggingface.co/spaces/gradio/PIFu-Clothed-Human-Digitization, https://huggingface.co/spaces/gradio/dpt-depth-estimation-3d-obj
Tags: VISION, IMAGE

## Introduction
Expand All @@ -9,7 +9,7 @@ Tags: VISION, IMAGE

This guide will show you how to build a demo for your 3D image model in a few lines of code; like the one below. Play around with 3D object by clicking around, dragging and zooming:

<gradio-app space="dawood/Model3D"> </gradio-app>
<gradio-app space="gradio/Model3D"> </gradio-app>

### Prerequisites

Expand All @@ -21,24 +21,28 @@ Let's take a look at how to create the minimal interface above. The prediction f

```python
import gradio as gr
import os


def load_mesh(mesh_file_name):
return mesh_file_name


demo = gr.Interface(
fn=load_mesh,
inputs=gr.Model3D(),
outputs=gr.Model3D(clear_color=[0.0, 0.0, 0.0, 0.0], label="3D Model"),
outputs=gr.Model3D(
clear_color=[0.0, 0.0, 0.0, 0.0], label="3D Model"),
examples=[
["files/Bunny.obj"],
["files/Duck.glb"],
["files/Fox.gltf"],
["files/face.obj"],
[os.path.join(os.path.dirname(__file__), "files/Bunny.obj")],
[os.path.join(os.path.dirname(__file__), "files/Duck.glb")],
[os.path.join(os.path.dirname(__file__), "files/Fox.gltf")],
[os.path.join(os.path.dirname(__file__), "files/face.obj")],
],
cache_examples=True,
)

demo.launch()
if __name__ == "__main__":
demo.launch()
```

Let's break down the code above:
Expand All @@ -55,18 +59,14 @@ Creating the Interface:
- `examples`: list of 3D model files. The 3D model component can accept _.obj_, _.glb_, & _.gltf_ file types.
- `cache_examples`: saves the predicted output for the examples, to save time on inference.

## Exploring mode complex Model3D Demos:

Below is a demo that uses the DPT model to predict the depth of an image and then uses 3D Point Cloud to create a 3D object. Take a look at the [app.py](https://huggingface.co/spaces/radames/dpt-depth-estimation-3d-obj/blob/main/app.py) file for a peek into the code and the model prediction function.
<gradio-app space="radames/dpt-depth-estimation-3d-obj"> </gradio-app>

Below is a demo that uses the PIFu model to convert an image of a clothed human into a 3D digitized model. Take a look at the [spaces.py](https://huggingface.co/spaces/radames/PIFu-Clothed-Human-Digitization/blob/main/PIFu/spaces.py) file for a peek into the code and the model prediction function.
## Exploring a more complex Model3D Demo:

<gradio-app space="radames/PIFu-Clothed-Human-Digitization"> </gradio-app>
Below is a demo that uses the DPT model to predict the depth of an image and then uses 3D Point Cloud to create a 3D object. Take a look at the [app.py](https://huggingface.co/spaces/gradio/dpt-depth-estimation-3d-obj/blob/main/app.py) file for a peek into the code and the model prediction function.
<gradio-app space="gradio/dpt-depth-estimation-3d-obj"> </gradio-app>

---

And you're done! That's all the code you need to build an interface for your Model3D model. Here are some references that you may find useful:

- Gradio's ["Getting Started" guide](https://gradio.app/getting_started/)
- The first [3D Model Demo](https://huggingface.co/spaces/dawood/Model3D) and [complete code](https://huggingface.co/spaces/dawood/Model3D/tree/main) (on Hugging Face Spaces)
- The first [3D Model Demo](https://huggingface.co/spaces/gradio/Model3D) and [complete code](https://huggingface.co/spaces/gradio/Model3D/tree/main) (on Hugging Face Spaces)
Expand Up @@ -165,11 +165,13 @@
{#if mode === "components"}
<div class="embedded-component">
{#key obj.name}
{#if obj.name !== "State"}
<gradio-app
space={"gradio/" +
obj.name.toLowerCase() +
"_component_main"}
/>
{/if}
{/key}
</div>
{/if}
Expand Down
109 changes: 109 additions & 0 deletions scripts/upload_website_demos.py
@@ -0,0 +1,109 @@
from __future__ import annotations

import argparse
import os
import pathlib
import shutil
import tempfile
import textwrap
import requests

import huggingface_hub

ROOT = os.path.abspath(os.path.join(os.path.dirname(__file__), ".."))
VERSION_TXT = os.path.abspath(os.path.join(ROOT, "gradio", "version.txt"))
DIR = os.path.dirname(__file__)
GRADIO_DEMO_DIR = os.path.abspath(os.path.join(ROOT, "demo"))

with open(VERSION_TXT) as f:
gradio_version=f.read()
gradio_version = gradio_version.strip()

# Reasoning:
# 1. all_demos includes all demos and is for testing PRs
# 2. reset_components includes media files that are only present in all_demos (only for PRs)
# 3. custom_path doesn't have .launch since the point is to show how to launch with uvicorn
# 4. The same reason as 2 for kitchen_sink_random and blocks_kitchen_sink
DEMOS_TO_SKIP = {"all_demos", "clear_components", "custom_path", "kitchen_sink_random", "blocks_kitchen_sink"}


def upload_demo_to_space(
demo_name: str,
space_id: str,
hf_token: str,
gradio_version: str | None,
gradio_wheel_url: str | None = None
):
"""Upload a demo in the demo directory to a huggingface space.
Parameters:
demo_name: The name of the demo to upload.
space_id: The id of the space to upload the demo to.
hf_token: HF api token. Need to have permission to write to space_id for this to work.
gradio_version: If not None, will set the gradio version in the created Space to the given version.
gradio_wheel_url: If not None, will install the version of gradio using the wheel url in the created Space.
"""

with tempfile.TemporaryDirectory() as tmpdir:
demo_path = pathlib.Path(GRADIO_DEMO_DIR, demo_name)
shutil.copytree(demo_path, tmpdir, dirs_exist_ok=True)
readme = pathlib.Path(tmpdir, "README.md")
readme_content = f"""
---
title: {space_id.split("/")[-1]}
emoji: 🔥
colorFrom: indigo
colorTo: indigo
sdk: gradio
sdk_version: {gradio_version}
app_file: run.py
pinned: false
hf_oauth: true
---
"""
readme.open("w").write(textwrap.dedent(readme_content))

if gradio_wheel_url:
requirements_path = os.path.join(tmpdir, "requirements.txt")
if not os.path.exists(requirements_path):
with open(os.path.join(requirements_path), "w") as f:
f.write(gradio_wheel_url)
else:
with open(os.path.join(requirements_path), "r") as f:
content = f.read()
with open(os.path.join(requirements_path), "w") as f:
f.seek(0, 0)
f.write(gradio_wheel_url + '\n' + content)

api = huggingface_hub.HfApi()
huggingface_hub.create_repo(
space_id,
space_sdk="gradio",
repo_type="space",
token=hf_token,
exist_ok=True,
)
api.upload_folder(
token=hf_token,
repo_id=space_id,
repo_type="space",
folder_path=tmpdir,
path_in_repo="",
)
return f"https://huggingface.co/spaces/{space_id}"

demos = os.listdir(GRADIO_DEMO_DIR)

demos = [demo for demo in demos if demo not in DEMOS_TO_SKIP and os.path.isdir(os.path.join(GRADIO_DEMO_DIR, demo)) and os.path.exists(os.path.join(GRADIO_DEMO_DIR, demo, "run.py"))]

if __name__ == "__main__":
parser = argparse.ArgumentParser()
parser.add_argument("--WHEEL_URL", type=str, help="aws link to gradio wheel")
parser.add_argument("--AUTH_TOKEN", type=str, help="huggingface auth token")
args = parser.parse_args()
gradio_wheel_url = args.WHEEL_URL + f"gradio-{gradio_version}-py3-none-any.whl"
if args.AUTH_TOKEN is not None:
hello_world_version = str(huggingface_hub.space_info("gradio/hello_world").cardData["sdk_version"])
for demo in demos:
if hello_world_version != gradio_version:
upload_demo_to_space(demo_name=demo, space_id="gradio/" + demo, hf_token=args.AUTH_TOKEN, gradio_version=gradio_version)
upload_demo_to_space(demo_name=demo, space_id="gradio/" + demo + "_main", hf_token=args.AUTH_TOKEN, gradio_version=gradio_version, gradio_wheel_url=gradio_wheel_url)

0 comments on commit 97c3c7b

Please sign in to comment.