@gradio/core 1.1.3 → 1.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +51 -0
- package/dist/src/Blocks.svelte +33 -2
- package/dist/src/_init.js +2 -2
- package/dist/src/api_docs/ApiBanner.svelte +6 -2
- package/dist/src/api_docs/ApiBanner.svelte.d.ts +1 -1
- package/dist/src/api_docs/ApiDocs.svelte +41 -25
- package/dist/src/api_docs/CodeSnippet.svelte +67 -170
- package/dist/src/api_docs/CodeSnippet.svelte.d.ts +2 -6
- package/dist/src/api_docs/CopyMarkdown.svelte +7 -2
- package/dist/src/api_docs/CopyMarkdown.svelte.d.ts +1 -1
- package/dist/src/api_docs/InstallSnippet.svelte +6 -1
- package/dist/src/api_docs/InstallSnippet.svelte.d.ts +1 -1
- package/dist/src/api_docs/ParametersSnippet.svelte +6 -1
- package/dist/src/api_docs/ParametersSnippet.svelte.d.ts +1 -1
- package/dist/src/api_docs/RecordingSnippet.svelte +6 -1
- package/dist/src/api_docs/RecordingSnippet.svelte.d.ts +1 -1
- package/dist/src/api_docs/ResponseSnippet.svelte +6 -1
- package/dist/src/api_docs/ResponseSnippet.svelte.d.ts +1 -1
- package/dist/src/api_docs/Settings.svelte +2 -7
- package/dist/src/api_docs/SettingsBanner.svelte +0 -3
- package/dist/src/api_docs/SkillSnippet.svelte +125 -0
- package/dist/src/api_docs/SkillSnippet.svelte.d.ts +20 -0
- package/dist/src/api_docs/img/skill.svg +10 -0
- package/dist/src/api_docs/utils.d.ts +0 -1
- package/dist/src/api_docs/utils.js +0 -22
- package/dist/src/dependency.d.ts +3 -1
- package/dist/src/dependency.js +39 -1
- package/dist/src/gradio_helper.js +5 -13
- package/dist/src/i18n.d.ts +1 -3
- package/dist/src/i18n.js +6 -53
- package/dist/src/init.svelte.js +81 -82
- package/package.json +49 -49
- package/src/Blocks.svelte +33 -2
- package/src/_init.ts +2 -2
- package/src/api_docs/ApiBanner.svelte +6 -2
- package/src/api_docs/ApiDocs.svelte +41 -25
- package/src/api_docs/CodeSnippet.svelte +67 -170
- package/src/api_docs/CopyMarkdown.svelte +7 -2
- package/src/api_docs/InstallSnippet.svelte +6 -1
- package/src/api_docs/ParametersSnippet.svelte +6 -1
- package/src/api_docs/RecordingSnippet.svelte +6 -1
- package/src/api_docs/ResponseSnippet.svelte +6 -1
- package/src/api_docs/Settings.svelte +2 -7
- package/src/api_docs/SettingsBanner.svelte +0 -3
- package/src/api_docs/SkillSnippet.svelte +125 -0
- package/src/api_docs/img/skill.svg +10 -0
- package/src/api_docs/utils.ts +0 -25
- package/src/dependency.ts +39 -1
- package/src/gradio_helper.ts +5 -17
- package/src/i18n.test.ts +41 -9
- package/src/i18n.ts +9 -62
- package/src/init.svelte.ts +95 -99
|
@@ -1,75 +1,78 @@
|
|
|
1
1
|
<script lang="ts">
|
|
2
|
-
import type {
|
|
2
|
+
import type { Dependency, Payload } from "../types";
|
|
3
3
|
import CopyButton from "./CopyButton.svelte";
|
|
4
|
-
import { represent_value, is_potentially_nested_file_data } from "./utils";
|
|
5
4
|
import { Block } from "@gradio/atoms";
|
|
6
5
|
import EndpointDetail from "./EndpointDetail.svelte";
|
|
7
6
|
|
|
8
|
-
interface EndpointParameter {
|
|
9
|
-
label: string;
|
|
10
|
-
type: string;
|
|
11
|
-
python_type: { type: string };
|
|
12
|
-
component: string;
|
|
13
|
-
example_input: string;
|
|
14
|
-
serializer: string;
|
|
15
|
-
}
|
|
16
|
-
|
|
17
7
|
export let dependency: Dependency;
|
|
18
|
-
export let
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
8
|
+
export let current_language:
|
|
9
|
+
| "python"
|
|
10
|
+
| "javascript"
|
|
11
|
+
| "bash"
|
|
12
|
+
| "skill"
|
|
13
|
+
| "mcp";
|
|
24
14
|
export let api_description: string | null = null;
|
|
25
15
|
export let analytics: Record<string, any>;
|
|
26
16
|
export let markdown_code_snippets: Record<string, Record<string, string>>;
|
|
17
|
+
export let code_snippets: Record<string, string>;
|
|
27
18
|
export let last_api_call: Payload | null = null;
|
|
28
19
|
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
);
|
|
37
|
-
let blob_components = ["Audio", "File", "Image", "Video"];
|
|
38
|
-
let blob_examples: any[] = endpoint_parameters.filter(
|
|
39
|
-
(param: EndpointParameter) => blob_components.includes(param.component)
|
|
40
|
-
);
|
|
20
|
+
$: markdown_code_snippets[
|
|
21
|
+
dependency.api_name as keyof typeof markdown_code_snippets
|
|
22
|
+
] = {
|
|
23
|
+
python: code_snippets.python || "",
|
|
24
|
+
javascript: code_snippets.javascript || "",
|
|
25
|
+
bash: code_snippets.bash || ""
|
|
26
|
+
};
|
|
41
27
|
|
|
42
|
-
|
|
43
|
-
|
|
28
|
+
function escape_html(text: string): string {
|
|
29
|
+
return text
|
|
30
|
+
.replace(/&/g, "&")
|
|
31
|
+
.replace(/</g, "<")
|
|
32
|
+
.replace(/>/g, ">");
|
|
33
|
+
}
|
|
44
34
|
|
|
45
|
-
|
|
35
|
+
function highlight_python(code: string): string {
|
|
36
|
+
let html = escape_html(code);
|
|
37
|
+
html = html.replace(
|
|
38
|
+
/\b(from|import|print)\b/g,
|
|
39
|
+
'<span class="kw">$1</span>'
|
|
40
|
+
);
|
|
41
|
+
html = html.replace(
|
|
42
|
+
/(Client\()("[^"]*")(\))/g,
|
|
43
|
+
'$1<span class="str">$2</span>$3'
|
|
44
|
+
);
|
|
45
|
+
html = html.replace(
|
|
46
|
+
/(api_name=)("[^"]*")/g,
|
|
47
|
+
'$1<span class="api-name">$2</span>'
|
|
48
|
+
);
|
|
49
|
+
return html;
|
|
50
|
+
}
|
|
46
51
|
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
52
|
+
function highlight_javascript(code: string): string {
|
|
53
|
+
let html = escape_html(code);
|
|
54
|
+
html = html.replace(
|
|
55
|
+
/\b(import|from|const|await)\b/g,
|
|
56
|
+
'<span class="kw">$1</span>'
|
|
57
|
+
);
|
|
58
|
+
html = html.replace(
|
|
59
|
+
/(Client\.connect\()("[^"]*")(\))/g,
|
|
60
|
+
'$1<span class="str">$2</span>$3'
|
|
61
|
+
);
|
|
62
|
+
html = html.replace(
|
|
63
|
+
/(\.predict\()("[^"]*")/g,
|
|
64
|
+
'$1<span class="api-name">$2</span>'
|
|
65
|
+
);
|
|
66
|
+
return html;
|
|
67
|
+
}
|
|
51
68
|
|
|
52
|
-
function
|
|
53
|
-
|
|
54
|
-
is_most_recently_used &&
|
|
55
|
-
actual_data &&
|
|
56
|
-
actual_data[index] !== undefined
|
|
57
|
-
) {
|
|
58
|
-
return actual_data[index];
|
|
59
|
-
}
|
|
60
|
-
return param.parameter_has_default !== undefined &&
|
|
61
|
-
param.parameter_has_default
|
|
62
|
-
? param.parameter_default
|
|
63
|
-
: param.example_input;
|
|
69
|
+
function highlight_bash(code: string): string {
|
|
70
|
+
return escape_html(code);
|
|
64
71
|
}
|
|
65
72
|
|
|
66
|
-
$:
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
python: python_code?.innerText || "",
|
|
70
|
-
javascript: js_code?.innerText || "",
|
|
71
|
-
bash: bash_post_code?.innerText || ""
|
|
72
|
-
};
|
|
73
|
+
$: python_html = highlight_python(code_snippets.python || "");
|
|
74
|
+
$: js_html = highlight_javascript(code_snippets.javascript || "");
|
|
75
|
+
$: bash_html = highlight_bash(code_snippets.bash || "");
|
|
73
76
|
</script>
|
|
74
77
|
|
|
75
78
|
<div class="container">
|
|
@@ -84,37 +87,9 @@
|
|
|
84
87
|
<Block>
|
|
85
88
|
<code>
|
|
86
89
|
<div class="copy">
|
|
87
|
-
<CopyButton code={
|
|
88
|
-
</div>
|
|
89
|
-
<div bind:this={python_code}>
|
|
90
|
-
<pre><span class="highlight">from</span> gradio_client <span
|
|
91
|
-
class="highlight">import</span
|
|
92
|
-
> Client{#if has_file_path}, handle_file{/if}
|
|
93
|
-
|
|
94
|
-
client = Client(<span class="token string">"{space_id || root}"</span
|
|
95
|
-
>{#if username !== null}, auth=("{username}", **password**){/if})
|
|
96
|
-
result = client.<span class="highlight">predict</span
|
|
97
|
-
>(<!--
|
|
98
|
-
-->{#each endpoint_parameters as param, i}<!--
|
|
99
|
-
-->
|
|
100
|
-
{param.parameter_name
|
|
101
|
-
? param.parameter_name + "="
|
|
102
|
-
: ""}<span
|
|
103
|
-
class:recent-value={is_most_recently_used &&
|
|
104
|
-
actual_data?.[i] !== undefined}
|
|
105
|
-
>{represent_value(
|
|
106
|
-
getParameterValue(param, i),
|
|
107
|
-
param.python_type.type,
|
|
108
|
-
"py"
|
|
109
|
-
)}</span
|
|
110
|
-
>,{/each}<!--
|
|
111
|
-
|
|
112
|
-
-->
|
|
113
|
-
api_name=<span class="api-name">"/{dependency.api_name}"</span><!--
|
|
114
|
-
-->
|
|
115
|
-
)
|
|
116
|
-
<span class="highlight">print</span>(result)</pre>
|
|
90
|
+
<CopyButton code={code_snippets.python || ""} />
|
|
117
91
|
</div>
|
|
92
|
+
<pre>{@html python_html}</pre>
|
|
118
93
|
</code>
|
|
119
94
|
</Block>
|
|
120
95
|
</div>
|
|
@@ -122,53 +97,9 @@ result = client.<span class="highlight">predict</span
|
|
|
122
97
|
<Block>
|
|
123
98
|
<code>
|
|
124
99
|
<div class="copy">
|
|
125
|
-
<CopyButton code={
|
|
126
|
-
</div>
|
|
127
|
-
<div bind:this={js_code}>
|
|
128
|
-
<pre>import { Client } from "@gradio/client";
|
|
129
|
-
{#each blob_examples as { component, example_input }, i}<!--
|
|
130
|
-
-->
|
|
131
|
-
const response_{i} = await fetch("{example_input.url}");
|
|
132
|
-
const example{component} = await response_{i}.blob();
|
|
133
|
-
{/each}<!--
|
|
134
|
-
-->
|
|
135
|
-
const client = await Client.connect(<span class="token string"
|
|
136
|
-
>"{space_id || root}"</span
|
|
137
|
-
>{#if username !== null}, {auth: ["{username}", **password**]}{/if});
|
|
138
|
-
const result = await client.predict(<span class="api-name"
|
|
139
|
-
>"/{dependency.api_name}"</span
|
|
140
|
-
>, { <!--
|
|
141
|
-
-->{#each endpoint_parameters as param, i}<!--
|
|
142
|
-
-->{#if blob_components.includes(param.component)}<!--
|
|
143
|
-
-->
|
|
144
|
-
<span
|
|
145
|
-
class="example-inputs"
|
|
146
|
-
>{param.parameter_name}: example{param.component}</span
|
|
147
|
-
>, <!--
|
|
148
|
-
--><span class="desc"><!--
|
|
149
|
-
--></span
|
|
150
|
-
><!--
|
|
151
|
-
-->{:else}<!--
|
|
152
|
-
-->
|
|
153
|
-
<span
|
|
154
|
-
class="example-inputs {is_most_recently_used &&
|
|
155
|
-
actual_data?.[i] !== undefined
|
|
156
|
-
? 'recent-value'
|
|
157
|
-
: ''}"
|
|
158
|
-
>{param.parameter_name}: {represent_value(
|
|
159
|
-
getParameterValue(param, i),
|
|
160
|
-
param.python_type.type,
|
|
161
|
-
"js"
|
|
162
|
-
)}</span
|
|
163
|
-
>, <!--
|
|
164
|
-
--><!--
|
|
165
|
-
-->{/if}
|
|
166
|
-
{/each}
|
|
167
|
-
});
|
|
168
|
-
|
|
169
|
-
console.log(result.data);
|
|
170
|
-
</pre>
|
|
100
|
+
<CopyButton code={code_snippets.javascript || ""} />
|
|
171
101
|
</div>
|
|
102
|
+
<pre>{@html js_html}</pre>
|
|
172
103
|
</code>
|
|
173
104
|
</Block>
|
|
174
105
|
</div>
|
|
@@ -176,29 +107,9 @@ result = client.<span class="highlight">predict</span
|
|
|
176
107
|
<Block>
|
|
177
108
|
<code>
|
|
178
109
|
<div class="copy">
|
|
179
|
-
<CopyButton code={
|
|
180
|
-
</div>
|
|
181
|
-
|
|
182
|
-
<div bind:this={bash_post_code}>
|
|
183
|
-
<pre>curl -X POST {normalised_root}{normalised_api_prefix}/call/{dependency.api_name} -s -H "Content-Type: application/json" -d '{"{"}
|
|
184
|
-
"data": [{#each endpoint_parameters as param, i}
|
|
185
|
-
<!--
|
|
186
|
-
--><span
|
|
187
|
-
class={is_most_recently_used && actual_data?.[i] !== undefined
|
|
188
|
-
? "recent-value"
|
|
189
|
-
: ""}
|
|
190
|
-
>{represent_value(
|
|
191
|
-
getParameterValue(param, i),
|
|
192
|
-
param.python_type.type,
|
|
193
|
-
"bash"
|
|
194
|
-
)}</span
|
|
195
|
-
>{#if i < endpoint_parameters.length - 1},
|
|
196
|
-
{/if}
|
|
197
|
-
{/each}
|
|
198
|
-
]{"}"}' \
|
|
199
|
-
| awk -F'"' '{"{"} print $4{"}"}' \
|
|
200
|
-
| read EVENT_ID; curl -N {normalised_root}{normalised_api_prefix}/call/{dependency.api_name}/$EVENT_ID</pre>
|
|
110
|
+
<CopyButton code={code_snippets.bash || ""} />
|
|
201
111
|
</div>
|
|
112
|
+
<pre>{@html bash_html}</pre>
|
|
202
113
|
</code>
|
|
203
114
|
</Block>
|
|
204
115
|
</div>
|
|
@@ -212,11 +123,6 @@ result = client.<span class="highlight">predict</span
|
|
|
212
123
|
tab-size: 2;
|
|
213
124
|
}
|
|
214
125
|
|
|
215
|
-
.token.string {
|
|
216
|
-
display: contents;
|
|
217
|
-
color: var(--color-accent-base);
|
|
218
|
-
}
|
|
219
|
-
|
|
220
126
|
code {
|
|
221
127
|
position: relative;
|
|
222
128
|
display: block;
|
|
@@ -238,21 +144,12 @@ result = client.<span class="highlight">predict</span
|
|
|
238
144
|
margin-bottom: var(--size-3);
|
|
239
145
|
}
|
|
240
146
|
|
|
241
|
-
.
|
|
242
|
-
color: var(--body-text-color-subdued);
|
|
243
|
-
}
|
|
244
|
-
|
|
245
|
-
.api-name {
|
|
147
|
+
:global(.api-name) {
|
|
246
148
|
color: var(--color-accent);
|
|
247
149
|
}
|
|
248
150
|
|
|
249
|
-
.
|
|
250
|
-
color:
|
|
251
|
-
background: #fff4e6;
|
|
252
|
-
border: 1px solid #ffd9b3;
|
|
253
|
-
border-radius: var(--radius-sm);
|
|
254
|
-
padding: 1px 4px;
|
|
255
|
-
font-weight: var(--weight-medium);
|
|
151
|
+
:global(.str) {
|
|
152
|
+
color: var(--color-accent-base);
|
|
256
153
|
}
|
|
257
154
|
|
|
258
155
|
.hidden {
|
|
@@ -10,7 +10,12 @@
|
|
|
10
10
|
import { represent_value } from "./utils";
|
|
11
11
|
import type { Dependency } from "../types";
|
|
12
12
|
|
|
13
|
-
export let current_language:
|
|
13
|
+
export let current_language:
|
|
14
|
+
| "python"
|
|
15
|
+
| "javascript"
|
|
16
|
+
| "bash"
|
|
17
|
+
| "skill"
|
|
18
|
+
| "mcp";
|
|
14
19
|
export let space_id: string | null;
|
|
15
20
|
export let root: string;
|
|
16
21
|
export let api_count: number;
|
|
@@ -362,7 +367,7 @@ Read the documentation above so I can ask questions about it.`
|
|
|
362
367
|
}
|
|
363
368
|
|
|
364
369
|
async function copyMarkdown(
|
|
365
|
-
current_language: "python" | "javascript" | "bash" | "mcp"
|
|
370
|
+
current_language: "python" | "javascript" | "bash" | "skill" | "mcp"
|
|
366
371
|
): Promise<void> {
|
|
367
372
|
try {
|
|
368
373
|
if (!markdown_content[current_language]) {
|
|
@@ -2,7 +2,12 @@
|
|
|
2
2
|
import CopyButton from "./CopyButton.svelte";
|
|
3
3
|
import { Block } from "@gradio/atoms";
|
|
4
4
|
|
|
5
|
-
export let current_language:
|
|
5
|
+
export let current_language:
|
|
6
|
+
| "python"
|
|
7
|
+
| "javascript"
|
|
8
|
+
| "bash"
|
|
9
|
+
| "skill"
|
|
10
|
+
| "mcp";
|
|
6
11
|
|
|
7
12
|
let py_install = "pip install gradio_client";
|
|
8
13
|
let js_install = "npm i -D @gradio/client";
|
|
@@ -5,7 +5,12 @@
|
|
|
5
5
|
export let is_running: boolean;
|
|
6
6
|
export let endpoint_returns: any;
|
|
7
7
|
export let js_returns: any;
|
|
8
|
-
export let current_language:
|
|
8
|
+
export let current_language:
|
|
9
|
+
| "python"
|
|
10
|
+
| "javascript"
|
|
11
|
+
| "bash"
|
|
12
|
+
| "skill"
|
|
13
|
+
| "mcp";
|
|
9
14
|
</script>
|
|
10
15
|
|
|
11
16
|
<h4>
|
|
@@ -9,7 +9,12 @@
|
|
|
9
9
|
export let short_root: string;
|
|
10
10
|
export let root: string;
|
|
11
11
|
export let api_prefix = "";
|
|
12
|
-
export let current_language:
|
|
12
|
+
export let current_language:
|
|
13
|
+
| "python"
|
|
14
|
+
| "javascript"
|
|
15
|
+
| "bash"
|
|
16
|
+
| "skill"
|
|
17
|
+
| "mcp";
|
|
13
18
|
export let username: string | null;
|
|
14
19
|
|
|
15
20
|
let python_code: HTMLElement;
|
|
@@ -4,7 +4,12 @@
|
|
|
4
4
|
export let is_running: boolean;
|
|
5
5
|
export let endpoint_returns: any;
|
|
6
6
|
export let js_returns: any;
|
|
7
|
-
export let current_language:
|
|
7
|
+
export let current_language:
|
|
8
|
+
| "python"
|
|
9
|
+
| "javascript"
|
|
10
|
+
| "bash"
|
|
11
|
+
| "skill"
|
|
12
|
+
| "mcp";
|
|
8
13
|
</script>
|
|
9
14
|
|
|
10
15
|
<h4>
|
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
import { BaseCheckbox as Checkbox } from "@gradio/checkbox";
|
|
7
7
|
import { language_choices, changeLocale } from "../i18n";
|
|
8
8
|
import { locale, _ } from "svelte-i18n";
|
|
9
|
+
import { get } from "svelte/store";
|
|
9
10
|
import record from "./img/record.svg";
|
|
10
11
|
|
|
11
12
|
let {
|
|
@@ -52,15 +53,9 @@
|
|
|
52
53
|
};
|
|
53
54
|
});
|
|
54
55
|
|
|
55
|
-
let current_locale: string = $state("en");
|
|
56
|
+
let current_locale: string = $state(get(locale) ?? "en");
|
|
56
57
|
let current_theme: "light" | "dark" | "system" = $state("system");
|
|
57
58
|
|
|
58
|
-
locale.subscribe((value) => {
|
|
59
|
-
if (value) {
|
|
60
|
-
current_locale = value;
|
|
61
|
-
}
|
|
62
|
-
});
|
|
63
|
-
|
|
64
59
|
function handleLanguageChange(value: string): void {
|
|
65
60
|
const new_locale = value;
|
|
66
61
|
changeLocale(new_locale);
|
|
@@ -2,11 +2,8 @@
|
|
|
2
2
|
import { _ } from "svelte-i18n";
|
|
3
3
|
import settings_logo from "./img/settings-logo.svg";
|
|
4
4
|
import Clear from "./img/clear.svelte";
|
|
5
|
-
import { setupi18n } from "../i18n";
|
|
6
5
|
|
|
7
6
|
let { root, onclose }: { root: string; onclose?: () => void } = $props();
|
|
8
|
-
|
|
9
|
-
setupi18n();
|
|
10
7
|
</script>
|
|
11
8
|
|
|
12
9
|
<h2>
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
<script lang="ts">
|
|
2
|
+
import { Block } from "@gradio/atoms";
|
|
3
|
+
import CopyButton from "./CopyButton.svelte";
|
|
4
|
+
|
|
5
|
+
export let space_id: string | null;
|
|
6
|
+
|
|
7
|
+
$: effective_space_id = space_id || "";
|
|
8
|
+
$: skill_id = effective_space_id.replace("/", "-");
|
|
9
|
+
$: install_gradio = "pip install --upgrade gradio";
|
|
10
|
+
$: install_cmd_claude = `gradio skills add ${effective_space_id} --claude`;
|
|
11
|
+
$: install_cmd_cursor = `gradio skills add ${effective_space_id} --cursor`;
|
|
12
|
+
$: install_cmd_codex = `gradio skills add ${effective_space_id} --codex`;
|
|
13
|
+
|
|
14
|
+
$: skill_preview = `---
|
|
15
|
+
name: ${skill_id}
|
|
16
|
+
description: Use the ${effective_space_id} Gradio Space via API. Provides Python, JavaScript, and cURL usage examples.
|
|
17
|
+
---
|
|
18
|
+
|
|
19
|
+
# ${effective_space_id}
|
|
20
|
+
|
|
21
|
+
This skill describes how to use the ${effective_space_id} Gradio Space programmatically.
|
|
22
|
+
|
|
23
|
+
## API Endpoints
|
|
24
|
+
...`;
|
|
25
|
+
</script>
|
|
26
|
+
|
|
27
|
+
<div class="skill-content">
|
|
28
|
+
<p class="padded">1. Make sure you are using the latest version of Gradio:</p>
|
|
29
|
+
<Block>
|
|
30
|
+
<code>
|
|
31
|
+
<div class="copy">
|
|
32
|
+
<CopyButton code={install_gradio} />
|
|
33
|
+
</div>
|
|
34
|
+
<div>
|
|
35
|
+
<pre>$ {install_gradio}</pre>
|
|
36
|
+
</div>
|
|
37
|
+
</code>
|
|
38
|
+
</Block>
|
|
39
|
+
|
|
40
|
+
<p class="padded">
|
|
41
|
+
2. Install the usage of this Space as a Skill for your coding agent by
|
|
42
|
+
running this in your terminal:
|
|
43
|
+
</p>
|
|
44
|
+
<Block>
|
|
45
|
+
<code>
|
|
46
|
+
<div class="copy">
|
|
47
|
+
<CopyButton code={install_cmd_claude} />
|
|
48
|
+
</div>
|
|
49
|
+
<div>
|
|
50
|
+
<pre>$ {install_cmd_claude}</pre>
|
|
51
|
+
</div>
|
|
52
|
+
</code>
|
|
53
|
+
</Block>
|
|
54
|
+
<p class="hint">
|
|
55
|
+
Instead of <span class="inline-code">--claude</span>, you can use
|
|
56
|
+
<span class="inline-code">--cursor</span>,
|
|
57
|
+
<span class="inline-code">--codex</span>, or
|
|
58
|
+
<span class="inline-code">--opencode</span>. Combine flags to install for
|
|
59
|
+
multiple agents. Use <span class="inline-code">--global</span> to install user-level
|
|
60
|
+
instead of per-project.
|
|
61
|
+
</p>
|
|
62
|
+
|
|
63
|
+
<p class="padded">
|
|
64
|
+
3. This will add a skill to your coding agent that describes how to use this
|
|
65
|
+
Space via Python, JavaScript, and cURL API. The skill will look like this:
|
|
66
|
+
</p>
|
|
67
|
+
<Block>
|
|
68
|
+
<code>
|
|
69
|
+
<div class="copy">
|
|
70
|
+
<CopyButton code={skill_preview} />
|
|
71
|
+
</div>
|
|
72
|
+
<div>
|
|
73
|
+
<pre>{skill_preview}</pre>
|
|
74
|
+
</div>
|
|
75
|
+
</code>
|
|
76
|
+
</Block>
|
|
77
|
+
</div>
|
|
78
|
+
|
|
79
|
+
<style>
|
|
80
|
+
.skill-content {
|
|
81
|
+
margin-top: var(--size-2);
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
p.padded {
|
|
85
|
+
padding: 15px 0px;
|
|
86
|
+
font-size: var(--text-lg);
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
.hint {
|
|
90
|
+
margin-top: var(--size-2);
|
|
91
|
+
color: var(--body-text-color);
|
|
92
|
+
opacity: 0.8;
|
|
93
|
+
font-size: var(--text-md);
|
|
94
|
+
line-height: 1.6;
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
.inline-code {
|
|
98
|
+
display: inline;
|
|
99
|
+
font-family: var(--font-mono);
|
|
100
|
+
font-size: var(--text-md);
|
|
101
|
+
background: var(--background-fill-secondary);
|
|
102
|
+
padding: 1px 4px;
|
|
103
|
+
border-radius: var(--radius-sm);
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
code pre {
|
|
107
|
+
overflow-x: auto;
|
|
108
|
+
color: var(--body-text-color);
|
|
109
|
+
font-family: var(--font-mono);
|
|
110
|
+
tab-size: 2;
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
code {
|
|
114
|
+
position: relative;
|
|
115
|
+
display: block;
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
.copy {
|
|
119
|
+
position: absolute;
|
|
120
|
+
top: 0;
|
|
121
|
+
right: 0;
|
|
122
|
+
margin-top: -5px;
|
|
123
|
+
margin-right: -5px;
|
|
124
|
+
}
|
|
125
|
+
</style>
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
<svg xmlns="http://www.w3.org/2000/svg" viewBox="14 22 122 106" style="background-color: #ffffff;">
|
|
2
|
+
<rect x="22" y="28" width="106" height="94" rx="8" fill="none" stroke="#374151" stroke-width="6"/>
|
|
3
|
+
<rect x="22" y="28" width="106" height="20" rx="8" fill="#374151" fill-opacity="0.08"/>
|
|
4
|
+
<circle cx="38" cy="38" r="4" fill="#ff5f57"/>
|
|
5
|
+
<circle cx="52" cy="38" r="4" fill="#febc2e"/>
|
|
6
|
+
<circle cx="66" cy="38" r="4" fill="#28c840"/>
|
|
7
|
+
<text x="38" y="76" fill="#374151" font-family="monospace" font-size="22" font-weight="bold">>_</text>
|
|
8
|
+
<rect x="38" y="88" width="50" height="4" rx="2" fill="#374151" fill-opacity="0.35"/>
|
|
9
|
+
<rect x="38" y="100" width="35" height="4" rx="2" fill="#374151" fill-opacity="0.2"/>
|
|
10
|
+
</svg>
|
package/src/api_docs/utils.ts
CHANGED
|
@@ -47,31 +47,6 @@ export function represent_value(
|
|
|
47
47
|
return stringify_except_file_function(value);
|
|
48
48
|
}
|
|
49
49
|
|
|
50
|
-
export function is_potentially_nested_file_data(obj: any): boolean {
|
|
51
|
-
if (typeof obj === "object" && obj !== null) {
|
|
52
|
-
if (obj.hasOwnProperty("url") && obj.hasOwnProperty("meta")) {
|
|
53
|
-
if (
|
|
54
|
-
typeof obj.meta === "object" &&
|
|
55
|
-
obj.meta !== null &&
|
|
56
|
-
obj.meta._type === "gradio.FileData"
|
|
57
|
-
) {
|
|
58
|
-
return true;
|
|
59
|
-
}
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
if (typeof obj === "object" && obj !== null) {
|
|
63
|
-
for (let key in obj) {
|
|
64
|
-
if (typeof obj[key] === "object") {
|
|
65
|
-
let result = is_potentially_nested_file_data(obj[key]);
|
|
66
|
-
if (result) {
|
|
67
|
-
return true;
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
}
|
|
71
|
-
}
|
|
72
|
-
return false;
|
|
73
|
-
}
|
|
74
|
-
|
|
75
50
|
function simplify_file_data(obj: any): any {
|
|
76
51
|
if (typeof obj === "object" && obj !== null && !Array.isArray(obj)) {
|
|
77
52
|
if (
|
package/src/dependency.ts
CHANGED
|
@@ -205,8 +205,10 @@ export class DependencyManager {
|
|
|
205
205
|
get_state_cb: GetStateCallback;
|
|
206
206
|
rerender_cb: RerenderCallback;
|
|
207
207
|
log_cb: LogCallback;
|
|
208
|
+
on_connection_lost_cb: () => void;
|
|
208
209
|
|
|
209
210
|
loading_stati = new LoadingStatus();
|
|
211
|
+
connection_lost = false;
|
|
210
212
|
|
|
211
213
|
constructor(
|
|
212
214
|
dependencies: IDependency[],
|
|
@@ -226,13 +228,15 @@ export class DependencyManager {
|
|
|
226
228
|
duration?: number | null,
|
|
227
229
|
visible?: boolean
|
|
228
230
|
) => void,
|
|
229
|
-
add_to_api_calls: (payload: Payload) => void
|
|
231
|
+
add_to_api_calls: (payload: Payload) => void,
|
|
232
|
+
on_connection_lost_cb: () => void
|
|
230
233
|
) {
|
|
231
234
|
this.add_to_api_calls = add_to_api_calls;
|
|
232
235
|
this.log_cb = log_cb;
|
|
233
236
|
this.update_state_cb = update_state_cb;
|
|
234
237
|
this.get_state_cb = get_state_cb;
|
|
235
238
|
this.rerender_cb = rerender_cb;
|
|
239
|
+
this.on_connection_lost_cb = on_connection_lost_cb;
|
|
236
240
|
this.client = client;
|
|
237
241
|
this.reload(
|
|
238
242
|
dependencies,
|
|
@@ -318,6 +322,7 @@ export class DependencyManager {
|
|
|
318
322
|
* @returns a value if there is no backend fn, a 'submission' if there is a backend fn, or null if there is no dependency
|
|
319
323
|
*/
|
|
320
324
|
async dispatch(event_meta: DispatchFunction | DispatchEvent): Promise<void> {
|
|
325
|
+
if (this.connection_lost) return;
|
|
321
326
|
let deps: Dependency[] | undefined;
|
|
322
327
|
if (event_meta.type === "fn") {
|
|
323
328
|
const dep = this.dependencies_by_fn.get(event_meta.fn_index!);
|
|
@@ -484,6 +489,19 @@ export class DependencyManager {
|
|
|
484
489
|
});
|
|
485
490
|
this.update_loading_stati_state();
|
|
486
491
|
} else if (result.stage === "error") {
|
|
492
|
+
if (result.broken || result.session_not_found) {
|
|
493
|
+
if (!this.connection_lost) {
|
|
494
|
+
this.connection_lost = true;
|
|
495
|
+
this.on_connection_lost_cb();
|
|
496
|
+
}
|
|
497
|
+
this.loading_stati.update({
|
|
498
|
+
status: "complete",
|
|
499
|
+
fn_index: dep.id,
|
|
500
|
+
stream_state: null
|
|
501
|
+
});
|
|
502
|
+
this.update_loading_stati_state();
|
|
503
|
+
break submit_loop;
|
|
504
|
+
}
|
|
487
505
|
if (Array.isArray(result?.message)) {
|
|
488
506
|
result.message.forEach((m: ValidationError, i) => {
|
|
489
507
|
this.update_state_cb(
|
|
@@ -806,6 +824,26 @@ export class DependencyManager {
|
|
|
806
824
|
});
|
|
807
825
|
this.update_loading_stati_state();
|
|
808
826
|
this.submissions.delete(id);
|
|
827
|
+
// Need to trigger any dependencies that are waiting for this one to complete
|
|
828
|
+
const { failure, all } = this.dependencies_by_fn
|
|
829
|
+
.get(id)
|
|
830
|
+
?.get_triggers() || { failure: [], all: [] };
|
|
831
|
+
failure.forEach((dep_id) => {
|
|
832
|
+
this.dispatch({
|
|
833
|
+
type: "fn",
|
|
834
|
+
fn_index: dep_id,
|
|
835
|
+
event_data: null,
|
|
836
|
+
target_id: id
|
|
837
|
+
});
|
|
838
|
+
});
|
|
839
|
+
all.forEach((dep_id) => {
|
|
840
|
+
this.dispatch({
|
|
841
|
+
type: "fn",
|
|
842
|
+
fn_index: dep_id,
|
|
843
|
+
event_data: null,
|
|
844
|
+
target_id: id
|
|
845
|
+
});
|
|
846
|
+
});
|
|
809
847
|
}
|
|
810
848
|
}
|
|
811
849
|
}
|