soiz1 commited on
Commit
618e7b0
·
verified ·
1 Parent(s): 01bfd30

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +112 -62
app.py CHANGED
@@ -1,67 +1,117 @@
1
  import gradio as gr
2
- import os, shutil, tempfile
3
- from huggingface_hub import HfApi, whoami
4
  from git import Repo
 
 
 
 
5
 
6
- api = HfApi()
7
-
8
- def create_from_repo(oauth_token: gr.OAuthToken | None,
9
- git_url, repo_type, private,
10
- space_id, port, title, description):
11
- if oauth_token is None:
12
- return "⚠️ Hugging Face にログインしてください。"
13
- token = oauth_token.token
14
- if not git_url.strip():
15
- return "Git リポジトリの URL を入力してください。"
16
- temp_dir = tempfile.mkdtemp()
17
- try:
18
- Repo.clone_from(git_url, temp_dir)
19
- if not space_id.strip():
20
- space_id = git_url.rstrip("/").split("/")[-1].replace(".git","")
21
- user = whoami(token=token)
22
- repo_id = f"{user['name']}/{space_id}"
23
- api.create_repo(repo_id=repo_id, repo_type=repo_type,
24
- private=private, token=token, exist_ok=False)
25
- if repo_type == "space":
26
- readme = []
27
- if title.strip(): readme.append(f"# {title.strip()}")
28
- if description.strip(): readme.append(f"\n{description.strip()}")
29
- if port.strip(): readme.append(f"\napp_port: {port.strip()}")
30
- if readme:
31
- with open(os.path.join(temp_dir,"README.md"),"w",encoding="utf‑8") as f:
32
- f.write("\n".join(readme))
33
- api.upload_folder(folder_path=temp_dir, repo_id=repo_id,
34
- repo_type=repo_type, token=token)
35
- return f"✅ {repo_type} を作成しました: https://huggingface.co/{repo_id}"
36
- except Exception as e:
37
- return f"❌ エラー: {e}"
38
- finally:
39
- shutil.rmtree(temp_dir)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
40
 
41
  with gr.Blocks() as demo:
42
- gr.Markdown("## Hugging Face Space / Dataset / Model を作成")
43
- login = gr.LoginButton()
44
- with gr.Column():
45
- git_url = gr.Textbox(label="Git リポジトリ URL", placeholder="https://...")
46
- repo_type = gr.Radio(["space","dataset","model"], label="タイプ", value="space")
47
- private = gr.Checkbox(label="非公開にする", value=False)
48
- space_id = gr.Textbox(label="Space ID(空欄で自動生成)", visible=True)
49
- port = gr.Textbox(label="起動ポート(README)", visible=True)
50
- title = gr.Textbox(label="スペース名", visible=True)
51
- description = gr.Textbox(label="説明文", visible=True)
52
- output = gr.Textbox(label="出力", lines=4)
53
- def toggle_spaceopts(rtype):
54
- vis = (rtype=="space")
55
- return {space_id: gr.update(visible=vis),
56
- port: gr.update(visible=vis),
57
- title: gr.update(visible=vis),
58
- description: gr.update(visible=vis)}
59
- repo_type.change(toggle_spaceopts, inputs=repo_type,
60
- outputs=[space_id, port, title, description])
61
-
62
- login.click(create_from_repo,
63
- inputs=[gr.OAuthToken(), git_url, repo_type, private,
64
- space_id, port, title, description],
65
- outputs=output)
66
-
67
- demo.launch()
 
 
 
 
 
 
 
 
 
 
 
 
 
1
  import gradio as gr
2
+ from huggingface_hub import HfApi
 
3
  from git import Repo
4
+ from slugify import slugify
5
+ import uuid
6
+ import os
7
+ import re
8
 
9
+ def extract_from_readme(readme_path):
10
+ title = None
11
+ description = None
12
+ port = None
13
+ if os.path.exists(readme_path):
14
+ with open(readme_path, encoding="utf-8") as f:
15
+ content = f.read()
16
+ match_title = re.search(r'title:\s*(.*)', content)
17
+ match_desc = re.search(r'short_description:\s*(.*)', content)
18
+ match_port = re.search(r'app_port:\s*(\d+)', content)
19
+ if match_title:
20
+ title = match_title.group(1).strip()
21
+ if match_desc:
22
+ description = match_desc.group(1).strip()
23
+ if match_port:
24
+ port = match_port.group(1).strip()
25
+ return title, description, port
26
+
27
+ def clone_and_create(profile: gr.OAuthProfile, token: gr.OAuthToken,
28
+ repo_url, repo_type, private, space_sdk, sdk_version,
29
+ space_id, space_title, space_description):
30
+ folder = str(uuid.uuid4())
31
+ Repo.clone_from(repo_url, folder)
32
+
33
+ hf_api = HfApi(token=token.token)
34
+
35
+ # 自動補完
36
+ title_from_readme, desc_from_readme, port_from_readme = extract_from_readme(os.path.join(folder, "README.md"))
37
+
38
+ final_id = slugify(space_id) if space_id else slugify(repo_url.split("/")[-1])
39
+ final_title = space_title or title_from_readme or final_id
40
+ final_description = space_description or desc_from_readme
41
+ repo_visibility = "private" if private else "public"
42
+
43
+ # スペースの場合
44
+ if repo_type == "space":
45
+ hf_api.create_repo(
46
+ repo_id=f"{profile.username}/{final_id}",
47
+ repo_type="space",
48
+ space_sdk=space_sdk,
49
+ space_sdk_version=sdk_version if sdk_version else None,
50
+ private=private
51
+ )
52
+ else:
53
+ hf_api.create_repo(
54
+ repo_id=f"{profile.username}/{final_id}",
55
+ repo_type=repo_type,
56
+ private=private
57
+ )
58
+
59
+ # README.md に補完情報追加(必要なら)
60
+ readme_path = os.path.join(folder, "README.md")
61
+ with open(readme_path, "a", encoding="utf-8") as f:
62
+ if space_title and not title_from_readme:
63
+ f.write(f"\ntitle: {space_title}")
64
+ if space_description and not desc_from_readme:
65
+ f.write(f"\nshort_description: {space_description}")
66
+ if port_from_readme:
67
+ f.write(f"\napp_port: {port_from_readme}")
68
+
69
+ # アップロード
70
+ hf_api.upload_folder(
71
+ folder_path=folder,
72
+ repo_id=f"{profile.username}/{final_id}",
73
+ repo_type=repo_type
74
+ )
75
+
76
+ # URL
77
+ return f"https://huggingface.co/{repo_type + 's' if repo_type != 'model' else 'models'}/{profile.username}/{final_id}"
78
 
79
  with gr.Blocks() as demo:
80
+ gr.Markdown("# 🚀 Gitリポジトリ Hugging Face クローンツール")
81
+ gr.LoginButton()
82
+
83
+ with gr.Row():
84
+ with gr.Column():
85
+ repo_url = gr.Textbox(label="GitリポジトリURL(GitHub等)")
86
+ repo_type = gr.Dropdown(choices=["space", "dataset", "model"], value="space", label="Hugging Faceの種類")
87
+ private = gr.Checkbox(label="非公開にする", value=False)
88
+ space_sdk = gr.Dropdown(choices=["gradio", "streamlit", "docker", "static"], label="スペースSDK", visible=True)
89
+ sdk_version = gr.Textbox(label="SDKバージョン(任意)", visible=True)
90
+ space_id = gr.Textbox(label="Hugging Face ID(空欄なら自動)")
91
+ space_title = gr.Textbox(label="スペースのタイトル(空欄ならREADMEやIDから)")
92
+ space_description = gr.Textbox(label="スペースの説明(空欄ならREADMEの内容を使用)")
93
+
94
+ with gr.Column():
95
+ output = gr.Textbox(label="作成されたHugging Face URL")
96
+
97
+ def toggle_space_fields(repo_type_val):
98
+ visible = repo_type_val == "space"
99
+ return {
100
+ space_sdk: gr.update(visible=visible),
101
+ sdk_version: gr.update(visible=visible),
102
+ space_id: gr.update(visible=True),
103
+ space_title: gr.update(visible=True),
104
+ space_description: gr.update(visible=True),
105
+ }
106
+
107
+ repo_type.change(fn=toggle_space_fields, inputs=repo_type, outputs=[space_sdk, sdk_version, space_id, space_title, space_description])
108
+
109
+ btn = gr.Button("クローンして作成!")
110
+ btn.click(
111
+ fn=clone_and_create,
112
+ inputs=[repo_url, repo_type, private, space_sdk, sdk_version, space_id, space_title, space_description],
113
+ outputs=output
114
+ )
115
+
116
+ if __name__ == "__main__":
117
+ demo.launch()