Upload 2 files
Browse files- .gitattributes +1 -0
- app.py +229 -0
- moss-dpo-47k-comparison-inference.xlsx +3 -0
.gitattributes
CHANGED
@@ -33,3 +33,4 @@ saved_model/**/* filter=lfs diff=lfs merge=lfs -text
|
|
33 |
*.zip filter=lfs diff=lfs merge=lfs -text
|
34 |
*.zst filter=lfs diff=lfs merge=lfs -text
|
35 |
*tfevents* filter=lfs diff=lfs merge=lfs -text
|
|
|
|
33 |
*.zip filter=lfs diff=lfs merge=lfs -text
|
34 |
*.zst filter=lfs diff=lfs merge=lfs -text
|
35 |
*tfevents* filter=lfs diff=lfs merge=lfs -text
|
36 |
+
moss-dpo-47k-comparison-inference.xlsx filter=lfs diff=lfs merge=lfs -text
|
app.py
ADDED
@@ -0,0 +1,229 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
import openai
|
2 |
+
import tiktoken
|
3 |
+
|
4 |
+
import numpy as np
|
5 |
+
import concurrent
|
6 |
+
import collections
|
7 |
+
import threading
|
8 |
+
import datetime
|
9 |
+
import time
|
10 |
+
import pytz
|
11 |
+
import json
|
12 |
+
import os
|
13 |
+
|
14 |
+
openai.api_key = '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'
|
15 |
+
os.environ["access_key"] = "key"
|
16 |
+
|
17 |
+
timezone = pytz.timezone('Asia/Shanghai')
|
18 |
+
timestamp2string = lambda timestamp: datetime.datetime.fromtimestamp(timestamp).astimezone(timezone).strftime('%Y-%m-%d %H:%M:%S')
|
19 |
+
|
20 |
+
def num_tokens_from_messages(messages, model="gpt-3.5-turbo"):
|
21 |
+
"""Returns the number of tokens used by a list of messages."""
|
22 |
+
try:
|
23 |
+
encoding = tiktoken.encoding_for_model(model)
|
24 |
+
except KeyError:
|
25 |
+
encoding = tiktoken.get_encoding("cl100k_base")
|
26 |
+
if model == "gpt-3.5-turbo": # note: future models may deviate from this
|
27 |
+
num_tokens = 0
|
28 |
+
len_values = 0
|
29 |
+
for message in messages:
|
30 |
+
num_tokens += 4 # every message follows <im_start>{role/name}\n{content}<im_end>\n
|
31 |
+
for key, value in message.items():
|
32 |
+
try:
|
33 |
+
num_tokens += len(encoding.encode(value))
|
34 |
+
except:
|
35 |
+
num_tokens += int(num_tokens/len_values*len(value)) # linear estimation
|
36 |
+
len_values += len(value)
|
37 |
+
if key == "name": # if there's a name, the role is omitted
|
38 |
+
num_tokens += -1 # role is always required and always 1 token
|
39 |
+
num_tokens += 2 # every reply is primed with <im_start>assistant
|
40 |
+
return num_tokens
|
41 |
+
else:
|
42 |
+
raise NotImplementedError(f"""num_tokens_from_messages() is not presently implemented for model {model}.
|
43 |
+
See https://github.com/openai/openai-python/blob/main/chatml.md for information on how messages are converted to tokens.""")
|
44 |
+
|
45 |
+
|
46 |
+
def read_tasks(cache_file="qas-5000.json"):
|
47 |
+
#from make_qas import input_dir
|
48 |
+
from make_qas_comparison import input_dir
|
49 |
+
file = f"{input_dir}/qas.json"
|
50 |
+
with open(file, "r", encoding="utf-8") as f:
|
51 |
+
qas = json.loads(f.read())
|
52 |
+
if cache_file is not None:
|
53 |
+
with open(cache_file, "r", encoding="utf-8") as f:
|
54 |
+
cache_qas = json.loads(f.read())
|
55 |
+
cache_q2a = {qa["q"]:qa["a"] for qa in cache_qas}
|
56 |
+
else:
|
57 |
+
cache_q2a = {}
|
58 |
+
qs = [qa["q"] for qa in qas if qa["a"] is None and qa["q"] not in cache_q2a] # 还未请求处理的queries
|
59 |
+
qas = [{"q":qa["q"], "a":qa["a"] if qa["a"] is not None else cache_q2a[qa["q"]]}
|
60 |
+
for qa in qas if qa["a"] is not None or qa["q"] in cache_q2a] # 已经完成请求处理的queries
|
61 |
+
print(f"read {len(qs)} queries without responses from {file} or {cache_file}")
|
62 |
+
print(f"read {len(qas)} queries with responses from {file} or {cache_file}")
|
63 |
+
return qs, qas
|
64 |
+
|
65 |
+
qs, qas = read_tasks()
|
66 |
+
start_time = time.time()
|
67 |
+
num_read_qas = len(qas)
|
68 |
+
|
69 |
+
def ask(query, timeout=600):
|
70 |
+
answer = None
|
71 |
+
dead_time = time.time() + timeout
|
72 |
+
attempt_times = 0
|
73 |
+
while answer is None and time.time()<dead_time and attempt_times<10:
|
74 |
+
try:
|
75 |
+
messages=[
|
76 |
+
{"role": "user", "content": query}
|
77 |
+
]
|
78 |
+
if num_tokens_from_messages(messages)>4096:
|
79 |
+
return None
|
80 |
+
answer = openai.ChatCompletion.create(
|
81 |
+
model="gpt-3.5-turbo-0301",
|
82 |
+
messages=messages,
|
83 |
+
temperature=0.1,
|
84 |
+
)["choices"][0]["message"]["content"]
|
85 |
+
except Exception as e:
|
86 |
+
if time.time()<dead_time:
|
87 |
+
print(e)
|
88 |
+
if "Please reduce the length of the messages." in str(e):
|
89 |
+
return None
|
90 |
+
else:
|
91 |
+
attempt_times += 1
|
92 |
+
wait_time = int(attempt_times*10)
|
93 |
+
time.sleep(wait_time)
|
94 |
+
print(f"retry in {attempt_times*10} seconds...")
|
95 |
+
return answer
|
96 |
+
|
97 |
+
|
98 |
+
def askingChatGPT(qs, qas, min_interval_seconds=3, max_interval_seconds=15, max_retry_times=3):
|
99 |
+
|
100 |
+
history_elapsed_time = [max_interval_seconds]*10
|
101 |
+
for i, q in enumerate(qs):
|
102 |
+
ask_start_time = time.time()
|
103 |
+
|
104 |
+
# 最直接的方法,调用ask函数,但可能因为超时等原因阻塞住
|
105 |
+
#a = ask(q)
|
106 |
+
|
107 |
+
# 下面是我之前设计的一系列,超时->重试,的方法
|
108 |
+
def ask_(q, timeout):
|
109 |
+
executor = concurrent.futures.ThreadPoolExecutor()
|
110 |
+
future = executor.submit(ask, q, timeout) # 提交函数调用任务
|
111 |
+
try:
|
112 |
+
a = future.result(timeout=timeout) # 等待函数调用任务完成,超时时间为30秒
|
113 |
+
return a
|
114 |
+
except concurrent.futures.TimeoutError:
|
115 |
+
print(f"ask call timed out after {timeout:.2f} seconds, retrying...")
|
116 |
+
executor.shutdown(wait=False)
|
117 |
+
return ask_(q, timeout*2) # 当超时时,重新调用函数
|
118 |
+
|
119 |
+
retry_times = 0
|
120 |
+
a = None
|
121 |
+
while a is None and retry_times<max_retry_times:
|
122 |
+
a = ask_(q, timeout=max(max_interval_seconds,np.mean(sorted(history_elapsed_time)[:8])))
|
123 |
+
retry_times += 1
|
124 |
+
|
125 |
+
qas.append({"q":q, "a":a})
|
126 |
+
|
127 |
+
ask_end_time = time.time()
|
128 |
+
elapsed_time = ask_end_time - ask_start_time
|
129 |
+
history_elapsed_time = history_elapsed_time[1:] + [elapsed_time]
|
130 |
+
delayTime = min_interval_seconds - elapsed_time
|
131 |
+
if delayTime>0:
|
132 |
+
time.sleep(delayTime)
|
133 |
+
|
134 |
+
print(f"{timestamp2string(time.time())}: iterations: {i+1} / {len(qs)} | elapsed time of this query (s): {elapsed_time:.2f}")
|
135 |
+
|
136 |
+
return
|
137 |
+
|
138 |
+
|
139 |
+
thread = threading.Thread(target=lambda :askingChatGPT(qs, qas))
|
140 |
+
thread.daemon = True
|
141 |
+
thread.start()
|
142 |
+
|
143 |
+
|
144 |
+
import gradio as gr
|
145 |
+
|
146 |
+
|
147 |
+
def showcase(access_key):
|
148 |
+
if not access_key==os.getenv('access_key'):
|
149 |
+
chatbot_ret = [(f"Your entered Access Key:<br>{access_key}<br>is incorrect.", f"So i cannot provide you any information in this private space.")]
|
150 |
+
else:
|
151 |
+
recent_qas = qas[-10:]
|
152 |
+
chatbot_ret = [(f"Your entered Access Key is correct.", f"The latest {len(recent_qas)} query-responses are displayed below.")]
|
153 |
+
for qa in recent_qas:
|
154 |
+
chatbot_ret += [(qa["q"].replace("\n","<br>"), str(qa["a"]).replace("\n","<br>"))]
|
155 |
+
return chatbot_ret
|
156 |
+
|
157 |
+
|
158 |
+
def download(access_key):
|
159 |
+
if not access_key.startswith(os.getenv('access_key')):
|
160 |
+
chatbot_ret = [(f"Your entered Access Key:<br>{access_key}<br>is incorrect.", f"So i cannot provide you any information in this private space.")]
|
161 |
+
file_ret = gr.File.update(value=None, visible=False)
|
162 |
+
else:
|
163 |
+
chatbot_ret = [(f"Your entered Access Key is correct.", f"The file containing all processed query-responses ({len(qas)} in total) can be downloaded below.")]
|
164 |
+
from make_qas import input_dir
|
165 |
+
filename = f"{input_dir}/qas-{len(qas)}.json"
|
166 |
+
with open(filename, "w", encoding="utf-8") as f:
|
167 |
+
f.write(json.dumps(qas, ensure_ascii=False, indent=4))
|
168 |
+
file_ret = gr.File.update(value=filename, visible=True)
|
169 |
+
return chatbot_ret, file_ret
|
170 |
+
|
171 |
+
|
172 |
+
def display(access_key):
|
173 |
+
if not access_key==os.getenv('access_key'):
|
174 |
+
chatbot_ret = [(f"Your entered Access Key:<br>{access_key}<br>is incorrect.", f"So i cannot provide you any information in this private space.")]
|
175 |
+
elif len(qas)-num_read_qas<1:
|
176 |
+
chatbot_ret = [(f"Your entered Access Key is correct.", f"But the progress has just started for a while and has no useful progress information to provide.")]
|
177 |
+
else:
|
178 |
+
num_total_qs, num_processed_qs = len(qs), len(qas) - num_read_qas
|
179 |
+
time_takes = time.time() - start_time
|
180 |
+
time_remains = time_takes * (num_total_qs-num_processed_qs) / num_processed_qs
|
181 |
+
end_time = start_time + time_takes + time_remains
|
182 |
+
|
183 |
+
messages = []
|
184 |
+
for qa in qas:
|
185 |
+
messages.append({"role":"user", "content":qa["q"]})
|
186 |
+
messages.append({"role":"assistant", "content":qa["a"] or ""})
|
187 |
+
num_tokens_processed = num_tokens_from_messages(messages)
|
188 |
+
num_tokens_total = int(num_tokens_processed * (num_total_qs+num_read_qas) / (num_processed_qs+num_read_qas))
|
189 |
+
dollars_tokens_processed = 0.002 * int(num_tokens_processed/1000)
|
190 |
+
dollars_tokens_total = 0.002 * int(num_tokens_total/1000)
|
191 |
+
|
192 |
+
chatbot_ret = [(f"Your entered Access Key is correct.", f"The information of progress is displayed below.")]
|
193 |
+
chatbot_ret += [(f"The number of processed / total queries:", f"{num_processed_qs} / {num_total_qs} (+{num_read_qas})")]
|
194 |
+
chatbot_ret += [(f"The hours already takes / est. remains:", f"{time_takes/3600:.2f} / {time_remains/3600:.2f}")]
|
195 |
+
chatbot_ret += [(f"The time starts / est. ends:", f"{timestamp2string(start_time)} / {timestamp2string(end_time)}")]
|
196 |
+
chatbot_ret += [(f"The number of processed / est. total tokens:", f"{num_tokens_processed} / {num_tokens_total}")]
|
197 |
+
chatbot_ret += [(f"The dollars of processed / est. total tokens:", f"{dollars_tokens_processed:.2f} / {dollars_tokens_total:.2f}")]
|
198 |
+
|
199 |
+
return chatbot_ret
|
200 |
+
|
201 |
+
|
202 |
+
with gr.Blocks() as demo:
|
203 |
+
|
204 |
+
gr.Markdown(
|
205 |
+
"""
|
206 |
+
Hello friends,
|
207 |
+
|
208 |
+
Thanks for your attention on this space. But this space is for my own use, i.e., building a dataset with answers from ChatGPT, and the access key for runtime feedback is only shared to my colleagues.
|
209 |
+
|
210 |
+
If you want to ask ChatGPT on Huggingface just as the title says, you can try this [one](https://huggingface.co/spaces/zhangjf/chatbot) I built for public.
|
211 |
+
"""
|
212 |
+
)
|
213 |
+
|
214 |
+
with gr.Column(variant="panel"):
|
215 |
+
chatbot = gr.Chatbot()
|
216 |
+
txt = gr.Textbox(show_label=False, container=False,
|
217 |
+
placeholder="Enter your Access Key to access this private space")
|
218 |
+
with gr.Row():
|
219 |
+
button_showcase = gr.Button("Show Recent Query-Responses")
|
220 |
+
button_download = gr.Button("Download All Query-Responses")
|
221 |
+
button_display = gr.Button("Display Progress Infomation")
|
222 |
+
|
223 |
+
downloadfile = gr.File(None, interactive=False, show_label=False, visible=False)
|
224 |
+
|
225 |
+
button_showcase.click(fn=showcase, inputs=[txt], outputs=[chatbot])
|
226 |
+
button_download.click(fn=download, inputs=[txt], outputs=[chatbot, downloadfile])
|
227 |
+
button_display.click(fn=display, inputs=[txt], outputs=[chatbot])
|
228 |
+
|
229 |
+
demo.launch()
|
moss-dpo-47k-comparison-inference.xlsx
ADDED
@@ -0,0 +1,3 @@
|
|
|
|
|
|
|
|
|
1 |
+
version https://git-lfs.github.com/spec/v1
|
2 |
+
oid sha256:1a13a4fdfca9b705f15214d791fa2c8a6697db457d350863e4e95c62e620f04b
|
3 |
+
size 13179564
|