littlebird13 commited on
Commit
51882e5
1 Parent(s): fe90cb9

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +230 -191
app.py CHANGED
@@ -1,54 +1,59 @@
1
  # Copyright (c) Alibaba, Inc. and its affiliates.
2
  import os
 
 
 
 
3
 
4
  import gradio as gr
5
  import modelscope_studio.components.antd as antd
6
  import modelscope_studio.components.base as ms
7
  from PIL import Image
8
- import secrets
9
- import tempfile
10
- from http import HTTPStatus
11
  from urllib3.exceptions import HTTPError
12
 
13
- from pathlib import Path
14
-
15
 
16
  import dashscope
17
  from dashscope import MultiModalConversation
18
- API_KEY = os.environ['API_KEY']
19
- BASE_URL = os.environ['DASHSCOPE_HTTP_BASE_URL']
20
  dashscope.api_key = API_KEY
21
- dashscope.base_http_api_url = BASE_URL
22
 
23
  is_modelscope_studio = os.getenv('MODELSCOPE_ENVIRONMENT') == 'studio'
24
 
 
25
  def get_text(text: str, cn_text: str):
26
  if is_modelscope_studio:
27
  return cn_text
28
  return text
29
 
 
30
  def resolve_image(filename):
31
  return os.path.join(os.path.dirname(__file__), filename)
32
 
 
33
  DEMO_LIST = [
34
- {
35
- "description": "Evaluate the integral of the functions graphed using the formula for circles: ",
36
- "image": resolve_image("./examples/1.webp")
37
- },
38
- {
39
- "description": "请解答这道题",
40
- "image": resolve_image("./examples/5.png")
41
- },
42
- {
43
- "description": "图片中的滤液E是什么化学物质?",
44
- "image": resolve_image("./examples/3.png")
45
- },
46
- {
47
- "description": "How many pelicans are there in the picture",
48
- "image": resolve_image("./examples/6.png")
49
- },
 
50
  ]
51
 
 
52
  def process_image(image, shouldConvert=False):
53
  # 获取上传文件的目录
54
  uploaded_file_dir = os.environ.get("GRADIO_TEMP_DIR") or str(
@@ -69,114 +74,131 @@ def process_image(image, shouldConvert=False):
69
 
70
  return filename
71
 
72
- if __name__ == "__main__":
73
-
74
- def on_clear():
75
- return {
76
- input: gr.update(value=None),
77
- **{
78
- item: gr.update(value=None)
79
- for item in input_image
80
- },
81
- }
82
-
83
- with gr.Blocks() as demo:
84
- with ms.Application() as app:
85
- with antd.ConfigProvider(
86
- locale="zh_CN" if is_modelscope_studio else None,
87
- theme=dict(token=dict(colorPrimary="#a855f7"))):
88
- with antd.Card(elem_style=dict(marginBottom=12),
89
- styles=dict(body=dict(padding=4))):
90
- with antd.Flex(elem_style=dict(width="100%"),
91
- justify="center",
92
- align="center",
93
- gap=14):
94
- with ms.Div(elem_style=dict(flexShrink=0)):
95
- antd.Image(
96
- resolve_image("./cutelogo.jpg"),
97
- preview=False,
98
- height=60,
99
- width=60)
100
- with ms.Div():
101
- antd.Typography.Title(
102
- "QVQ-72B-Preview",
103
- elem_style=dict(margin=0, fontSize=24),
104
- level=1)
105
- with ms.AutoLoading():
106
- with antd.Row(gutter=[8, 8], align="stretch"):
107
- with antd.Col(xs=24, md=8):
 
 
 
 
 
 
 
108
  with antd.Space(direction="vertical",
109
- elem_style=dict(width="100%")):
110
- with antd.Space(direction="vertical",
111
- elem_style=dict(width="100%"),
112
- elem_id="input-container"):
113
- with ms.Fragment():
114
- input_image = gr.Image(
115
- type="pil",
116
- label="Upload",
117
- sources=["upload"]),
118
- input = antd.Input.Textarea(
119
- placeholder=get_text("Ask a question", "输入一个问题"),
120
- auto_size=dict(maxRows=6, minRows=2),
121
- allow_clear=True)
122
-
123
- with antd.Flex(align="center",
124
- justify="space-between"):
125
- antd.Typography.Text(
126
- get_text("Warning: This model only supports single-turn dialogue.", "注:当前模型只支持单轮对话,如需中文回答,提示词加“用中文回答”"), type="warning")
127
- tour_btn = antd.Button(get_text("Tour", "使用指引"),
128
- variant="filled",
129
- color="default")
130
-
131
- with antd.Row(gutter=8):
132
- with antd.Col(span=12):
133
- clear_btn = antd.Button(get_text("Clear", "清除"),
134
- block=True)
135
- with antd.Col(span=12):
136
- submit_btn = antd.Button(
137
- get_text("Submit", "提交"),
138
- type="primary",
139
- block=True,
140
- elem_id="submit-btn")
141
-
142
- antd.Divider(get_text("Example", "示例"))
143
-
144
- with antd.Flex(gap="small", wrap=True):
145
- for item in DEMO_LIST:
146
-
147
- def bind_on_example(_item):
148
- def on_example():
149
- return gr.update(
150
- value=_item[
151
- 'description']
152
- ), gr.update(
153
- value=_item['image'])
154
-
155
- return on_example
156
-
157
- with antd.Card(
158
- hoverable=True,
159
- elem_style=dict(
160
- width="100%")) as example:
161
- if "description" in item:
162
- antd.Typography.Text(
163
- item["description"])
164
- if "image" in item:
165
- antd.Image(item["image"],
166
- preview=False)
167
- example.click(
168
- fn=bind_on_example(item),
169
- outputs=[input, input_image[0]])
170
-
171
- with antd.Col(xs=24, md=16):
172
- with antd.Card(title=get_text("Answer", "答案"),
173
- elem_style=dict(height="100%"),
174
- elem_id="output-container"):
175
- with ms.Slot("extra"):
176
- cancel_btn = antd.Button(get_text("Stop", "停止"),
177
- block=True, disabled=True)
 
 
 
 
 
 
 
 
 
178
  output = gr.Markdown(
179
  show_copy_button=True,
 
180
  latex_delimiters=[{
181
  "left": '$$',
182
  "right": '$$',
@@ -194,66 +216,83 @@ if __name__ == "__main__":
194
  "right": '\\]',
195
  "display": True
196
  }])
197
- with antd.Tour(props=dict(open=False)) as tour:
198
- antd.Tour.Step(
199
- title=get_text("Step 1", "步骤 1"),
200
- description=get_text("Upload image and enter text", "传入图片和文本"),
201
- get_target=
202
- "() => document.querySelector('#input-container')")
203
- antd.Tour.Step(
204
- title=get_text("Step 2","步骤 2"),
205
- description=get_text("Click submit button", "点击提交按钮"),
206
- get_target=
207
- "() => document.querySelector('#submit-btn')")
208
- antd.Tour.Step(
209
- title=get_text("Step 3","步骤 3"),
210
- description=get_text("Wait for result", "等待结果返回"),
211
- get_target=
212
- "() => document.querySelector('#output-container')"
213
- )
214
-
215
- tour_btn.click(fn=lambda: gr.update(props=dict(open=True)),
216
- outputs=[tour])
217
- gr.on([tour.finish, tour.close],
218
- fn=lambda: gr.update(props=dict(open=False)),
219
- outputs=[tour])
220
-
221
- def generate(image, query):
 
 
 
 
 
 
 
 
 
 
 
222
  imageFile = process_image(image)
223
- content = [
224
- {'image': f'file://{imageFile}'},
225
- {'text': query}
226
- ]
227
- messages = [
228
- {'role': 'user', 'content': content},
229
- ]
230
- print('messages:', messages)
231
- responses = MultiModalConversation.call(
232
- model='qvq-72b-preview', messages=messages, stream=True,
233
- )
234
- yield {
235
- cancel_btn: gr.update(disabled=False)
236
- }
237
- for response in responses:
238
- if not response.status_code == HTTPStatus.OK:
239
- raise HTTPError(f'response.code: {response.code}\nresponse.message: {response.message}')
240
- response = response.output.choices[0].message.content
241
- if len(response) > 0 and response[0]['text']:
242
- print(response[0]['text'])
243
- yield {
244
- output: response[0]['text']
245
- }
246
- yield {
247
- cancel_btn: gr.update(disabled=True)
248
- }
249
-
250
- output_process = submit_btn.click(
251
- fn=generate,
252
- inputs=[*input_image, input],
253
- outputs=[output, cancel_btn])
254
- clear_btn.click(
255
- fn=on_clear,
256
- outputs=[*input_image, input])
257
- cancel_btn.click(fn=lambda : gr.update(disabled=True), inputs=None, outputs=[cancel_btn], cancels=[output_process])
258
-
259
- demo.queue(default_concurrency_limit=50).launch(ssr_mode=False)
 
 
 
 
 
 
 
1
  # Copyright (c) Alibaba, Inc. and its affiliates.
2
  import os
3
+ import secrets
4
+ import tempfile
5
+ from http import HTTPStatus
6
+ from pathlib import Path
7
 
8
  import gradio as gr
9
  import modelscope_studio.components.antd as antd
10
  import modelscope_studio.components.base as ms
11
  from PIL import Image
 
 
 
12
  from urllib3.exceptions import HTTPError
13
 
14
+ os.environ['DASHSCOPE_HTTP_BASE_URL'] = 'https://dashscope.aliyuncs.com/api/v1'
15
+ # os.environ['DASHSCOPE_WEBSOCKET_BASE_URL'] = 'https://poc-dashscope.aliyuncs.com/api-ws/v1/inference'
16
 
17
  import dashscope
18
  from dashscope import MultiModalConversation
19
+
20
+ API_KEY = os.environ.get('API_KEY')
21
  dashscope.api_key = API_KEY
 
22
 
23
  is_modelscope_studio = os.getenv('MODELSCOPE_ENVIRONMENT') == 'studio'
24
 
25
+
26
  def get_text(text: str, cn_text: str):
27
  if is_modelscope_studio:
28
  return cn_text
29
  return text
30
 
31
+
32
  def resolve_image(filename):
33
  return os.path.join(os.path.dirname(__file__), filename)
34
 
35
+
36
  DEMO_LIST = [
37
+ {
38
+ "description":
39
+ "Evaluate the integral of the functions graphed using the formula for circles: ",
40
+ "image": resolve_image("./examples/1.webp")
41
+ },
42
+ {
43
+ "description": "请解答这道题",
44
+ "image": resolve_image("./examples/5.png")
45
+ },
46
+ {
47
+ "description": "图片中的滤液E是什么化学物质?",
48
+ "image": resolve_image("./examples/3.png")
49
+ },
50
+ {
51
+ "description": "How many pelicans are there in the picture",
52
+ "image": resolve_image("./examples/6.png")
53
+ },
54
  ]
55
 
56
+
57
  def process_image(image, shouldConvert=False):
58
  # 获取上传文件的目录
59
  uploaded_file_dir = os.environ.get("GRADIO_TEMP_DIR") or str(
 
74
 
75
  return filename
76
 
77
+
78
+ def on_clear():
79
+ return {
80
+ input: gr.update(value=None),
81
+ **{
82
+ item: gr.update(value=None)
83
+ for item in input_image
84
+ },
85
+ }
86
+
87
+
88
+ css = """
89
+ .output-markdown {
90
+ overflow: unset !important;
91
+ }
92
+ """
93
+
94
+ with gr.Blocks(css=css) as demo:
95
+ with ms.Application() as app:
96
+ with antd.ConfigProvider(
97
+ locale="zh_CN" if is_modelscope_studio else None,
98
+ theme=dict(token=dict(colorPrimary="#a855f7"))):
99
+ with antd.Card(elem_style=dict(marginBottom=12),
100
+ styles=dict(body=dict(padding=4))):
101
+ with antd.Flex(elem_style=dict(width="100%"),
102
+ justify="center",
103
+ align="center",
104
+ gap=14):
105
+ with ms.Div(elem_style=dict(flexShrink=0)):
106
+ antd.Image(resolve_image("./cutelogo.jpg"),
107
+ preview=False,
108
+ height=60,
109
+ width=60)
110
+ with ms.Div():
111
+ antd.Typography.Title("QVQ-72B-Preview",
112
+ elem_style=dict(margin=0,
113
+ fontSize=24),
114
+ level=1)
115
+ with ms.AutoLoading():
116
+ with antd.Row(gutter=[8, 8], align="stretch"):
117
+ with antd.Col(xs=24, md=8):
118
+ with antd.Space(direction="vertical",
119
+ elem_style=dict(width="100%")):
120
  with antd.Space(direction="vertical",
121
+ elem_style=dict(width="100%"),
122
+ elem_id="input-container"):
123
+ with ms.Fragment():
124
+ input_image = gr.Image(type="pil",
125
+ label="Upload",
126
+ sources=["upload"]),
127
+ input = antd.Input.Textarea(
128
+ placeholder=get_text(
129
+ "Ask a question", "输入一个问题"),
130
+ auto_size=dict(maxRows=6, minRows=2),
131
+ allow_clear=True)
132
+
133
+ with antd.Flex(align="center",
134
+ justify="space-between"):
135
+ antd.Typography.Text(get_text(
136
+ "Warning: This model only supports single-turn dialogue.",
137
+ "注:当前模型只支持单轮对话,如需中文回答,提示词加“用中文回答”"),
138
+ type="warning")
139
+ tour_btn = antd.Button(get_text(
140
+ "Tour", "使用指引"),
141
+ variant="filled",
142
+ color="default")
143
+
144
+ with antd.Row(gutter=8):
145
+ with antd.Col(span=12):
146
+ clear_btn = antd.Button(get_text(
147
+ "Clear", "清除"),
148
+ block=True)
149
+ with antd.Col(span=12):
150
+ submit_btn = antd.Button(
151
+ get_text("Submit", "提交"),
152
+ type="primary",
153
+ block=True,
154
+ elem_id="submit-btn")
155
+
156
+ antd.Divider(get_text("Examples", "示例"))
157
+
158
+ with antd.Flex(gap="small", wrap=True):
159
+ for item in DEMO_LIST:
160
+
161
+ def bind_on_example(_item):
162
+
163
+ def on_example():
164
+ return gr.update(
165
+ value=_item['description']
166
+ ), gr.update(value=_item['image'])
167
+
168
+ return on_example
169
+
170
+ with antd.Card(
171
+ hoverable=True,
172
+ elem_style=dict(
173
+ width="100%")) as example:
174
+ if "description" in item:
175
+ antd.Typography.Text(
176
+ item["description"])
177
+ if "image" in item:
178
+ antd.Image(item["image"],
179
+ preview=False)
180
+ example.click(
181
+ fn=bind_on_example(item),
182
+ outputs=[input, input_image[0]])
183
+
184
+ with antd.Col(xs=24, md=16):
185
+ with antd.Card(title=get_text("Answer", "答案"),
186
+ elem_style=dict(height="100%"),
187
+ elem_id="output-container"):
188
+ with ms.Slot("extra"):
189
+ cancel_btn = antd.Button(get_text(
190
+ "Stop", "停止"),
191
+ elem_id="cancel-btn",
192
+ block=True,
193
+ disabled=True)
194
+ with ms.Div(elem_style=dict(
195
+ maxHeight=1600,
196
+ display="flex",
197
+ flexDirection="column-reverse",
198
+ overflow="auto")):
199
  output = gr.Markdown(
200
  show_copy_button=True,
201
+ elem_classes="output-markdown",
202
  latex_delimiters=[{
203
  "left": '$$',
204
  "right": '$$',
 
216
  "right": '\\]',
217
  "display": True
218
  }])
219
+ with antd.Tour(open=False) as tour:
220
+ antd.Tour.Step(
221
+ title=get_text("Step 1", "步骤 1"),
222
+ description=get_text("Upload image and enter text",
223
+ "传入图片和文本"),
224
+ get_target=
225
+ "() => document.querySelector('#input-container')")
226
+ antd.Tour.Step(
227
+ title=get_text("Step 2", "步骤 2"),
228
+ description=get_text("Click the submit button",
229
+ "点击提交按钮"),
230
+ get_target="() => document.querySelector('#submit-btn')"
231
+ )
232
+ antd.Tour.Step(
233
+ title=get_text("Step 3", "步骤 3"),
234
+ description=get_text("Wait for the result", "等待结果返回"),
235
+ get_target=
236
+ "() => document.querySelector('#output-container')")
237
+ antd.Tour.Step(
238
+ title=get_text("Tips", "提示"),
239
+ description=get_text("Click here to end output early",
240
+ "点击这里提前结束输出"),
241
+ get_target="() => document.querySelector('#cancel-btn')"
242
+ )
243
+
244
+ tour_btn.click(fn=lambda: gr.update(open=True), outputs=[tour])
245
+ gr.on([tour.finish, tour.close],
246
+ fn=lambda: gr.update(open=False),
247
+ outputs=[tour])
248
+
249
+ def generate(image, query):
250
+ content = []
251
+ if not image and not query:
252
+ raise gr.Error(
253
+ get_text("Error: Input is empty", "错误:输入内容为空"))
254
+ if image:
255
  imageFile = process_image(image)
256
+ content.append({'image': f'file://{imageFile}'})
257
+ if query:
258
+ content.append({'text': query})
259
+
260
+ print("image", image)
261
+ print("query", query)
262
+ messages = [
263
+ {
264
+ 'role': 'user',
265
+ 'content': content
266
+ },
267
+ ]
268
+
269
+ responses = MultiModalConversation.call(
270
+ model='qvq-72b-preview',
271
+ messages=messages,
272
+ stream=True,
273
+ )
274
+ yield {cancel_btn: gr.update(disabled=False)}
275
+ for response in responses:
276
+ if not response.status_code == HTTPStatus.OK:
277
+ raise HTTPError(
278
+ f'response.code: {response.code}\nresponse.message: {response.message}'
279
+ )
280
+ response = response.output.choices[0].message.content
281
+ if len(response) > 0 and response[0]['text']:
282
+ print(response[0]['text'])
283
+ yield {output: response[0]['text']}
284
+ yield {cancel_btn: gr.update(disabled=True)}
285
+
286
+ output_process = submit_btn.click(fn=generate,
287
+ inputs=[*input_image, input],
288
+ outputs=[output, cancel_btn])
289
+ clear_btn.click(fn=on_clear, outputs=[*input_image, input])
290
+ cancel_btn.click(fn=None,
291
+ inputs=None,
292
+ outputs=None,
293
+ cancels=[output_process])
294
+ cancel_btn.click(fn=lambda: gr.update(disabled=True),
295
+ inputs=None,
296
+ outputs=[cancel_btn])
297
+
298
+ demo.queue(default_concurrency_limit=50).launch(ssr_mode=False)