|
import json, requests |
|
import gradio as gr |
|
import uuid |
|
import time |
|
import random |
|
import os |
|
|
|
|
|
def generate_uuid(): |
|
random_uuid = uuid.uuid4() |
|
random_uuid_str = str(random_uuid) |
|
formatted_uuid = f"{random_uuid_str[0:8]}-{random_uuid_str[9:13]}-{random_uuid_str[14:18]}-{random_uuid_str[19:23]}-{random_uuid_str[24:]}" |
|
return formatted_uuid |
|
|
|
|
|
|
|
def delete_conversation(user_id,channel_id,cookie): |
|
url = f"https://claude.ai/api/organizations/{user_id}/chat_conversations/{channel_id}" |
|
|
|
payload = json.dumps(f"{channel_id}") |
|
headers = { |
|
'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36 Edg/114.0.1823.82', |
|
'Accept-Language': 'en-US,en;q=0.5', |
|
'Content-Type': 'application/json', |
|
'Content-Length': '38', |
|
'Referer': 'https://claude.ai/chats', |
|
'Origin': 'https://claude.ai', |
|
'Sec-Fetch-Dest': 'empty', |
|
'Sec-Fetch-Mode': 'cors', |
|
'Sec-Fetch-Site': 'same-origin', |
|
'Connection': 'keep-alive', |
|
'Cookie': f'{cookie}', |
|
'TE': 'trailers' |
|
} |
|
|
|
response = requests.delete(url, headers=headers, data=payload) |
|
|
|
if response.status_code == 204: |
|
return True |
|
else: |
|
return False |
|
|
|
def create_new_chat(user_id,cookie): |
|
url = f"https://claude.ai/api/organizations/{user_id}/chat_conversations" |
|
uuid = generate_uuid() |
|
|
|
payload = json.dumps({"uuid": uuid, "name": ""}) |
|
headers = { |
|
'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36 Edg/114.0.1823.82', |
|
'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8,en-GB;q=0.7,en-US;q=0.6', |
|
'Referer': 'https://claude.ai/chats', |
|
'Content-Type': 'application/json', |
|
'Origin': 'https://claude.ai', |
|
'Connection': 'keep-alive', |
|
'Cookie': cookie, |
|
'Sec-Fetch-Dest': 'empty', |
|
'Sec-Fetch-Mode': 'cors', |
|
'Sec-Fetch-Site': 'same-origin', |
|
} |
|
|
|
|
|
|
|
|
|
response = requests.post(url, headers=headers, data=payload) |
|
print(f"新的对话页面:{response.json()}") |
|
|
|
|
|
return response.json() |
|
|
|
def get_content_type(file_path): |
|
|
|
extension = os.path.splitext(file_path)[-1].lower() |
|
if extension == '.pdf': |
|
return 'application/pdf' |
|
elif extension == '.txt': |
|
return 'text/plain' |
|
elif extension == '.csv': |
|
return 'text/csv' |
|
|
|
else: |
|
return 'application/octet-stream' |
|
|
|
def upload_attachment(cookie ,organization_id,file_path): |
|
url = 'https://claude.ai/api/convert_document' |
|
headers = { |
|
'User-Agent':'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36 Edg/114.0.1823.82', |
|
'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8,en-GB;q=0.7,en-US;q=0.6', |
|
'Referer': 'https://claude.ai/chats', |
|
'Origin': 'https://claude.ai', |
|
'Sec-Fetch-Dest': 'empty', |
|
'Sec-Fetch-Mode': 'cors', |
|
'Sec-Fetch-Site': 'same-origin', |
|
'Connection': 'keep-alive', |
|
'Cookie': f'{cookie}', |
|
'TE': 'trailers' |
|
} |
|
|
|
file_name = os.path.basename(file_path) |
|
print(file_name) |
|
content_type = get_content_type(file_path) |
|
print(content_type) |
|
files = { |
|
'file': (file_name, open(file_path, 'rb'), content_type), |
|
'orgUuid': (None, organization_id) |
|
|
|
} |
|
print(files) |
|
response = requests.post(url, headers=headers, files=files) |
|
print(f"response:{response.text}") |
|
if response.status_code == 200: |
|
return response.json() |
|
else: |
|
return False |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
def request_to_v2(message, cookie, user_id,attachment=None,context=[]): |
|
context = [message] |
|
|
|
|
|
|
|
|
|
attachment = attachment.name |
|
attachments = [] |
|
if attachment: |
|
attachment_response = upload_attachment(cookie,user_id,attachment) |
|
if attachment_response: |
|
attachments = [attachment_response] |
|
print(f"attachment_response:{attachment_response}") |
|
else: |
|
bots = "\nError: Invalid file format. Please try again." |
|
print(bots) |
|
context += [bots] |
|
responses = [(u, b) for u, b in zip(context[::2], context[1::2])] |
|
return responses, context |
|
|
|
|
|
if not attachment: |
|
attachments = [] |
|
|
|
|
|
|
|
response_json = create_new_chat(user_id,cookie) |
|
channel_id = response_json.get('uuid',"") |
|
print(channel_id) |
|
|
|
|
|
timeout = 5*60 |
|
context = [message] |
|
headers = { |
|
|
|
|
|
|
|
|
|
'Content-Type': 'application/json', |
|
'Origin': 'https://claude.ai', |
|
'Referer': f'https://claude.ai/chat/{channel_id}', |
|
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36', |
|
'Cookie': cookie, |
|
'Accept-Language': 'zh-CN,zh;q=0.9,en;q=0.8', |
|
|
|
'Accept': 'text/event-stream, text/event-stream', |
|
'Sec-Ch-Ua': '"Not.A/Brand";v="8", "Chromium";v="114", "Google Chrome";v="114"', |
|
'Sec-Ch-Ua-Mobile': '?0', |
|
'Sec-Ch-Ua-Platform': '"Windows"', |
|
'Sec-Fetch-Dest': 'empty', |
|
'Sec-Fetch-Mode': 'cors', |
|
'Sec-Fetch-Site': 'same-origin', |
|
'Connection': 'keep-alive', |
|
} |
|
post_msg_url = 'https://claude.ai/api/append_message' |
|
post_msg_data = { |
|
"completion":{ |
|
"incremental":True, |
|
"prompt": message, |
|
"timezone":"Asia/Shanghai", |
|
"model":"claude-2" |
|
}, |
|
"organization_uuid": user_id, |
|
"conversation_uuid": channel_id, |
|
"text": message, |
|
"attachments": attachments |
|
} |
|
post_msg_data = json.dumps(post_msg_data) |
|
|
|
|
|
response = { |
|
"status_code":-1, |
|
"text":"报错啦" |
|
} |
|
|
|
try: |
|
print(f"输入的问题:{message}") |
|
response = requests.post(post_msg_url, headers=headers, data=post_msg_data, verify=False, stream=False,timeout = timeout) |
|
bots = "" |
|
print("a"*100) |
|
for data in response.iter_lines(): |
|
if data: |
|
|
|
data_str = data.decode('utf-8') |
|
|
|
data_str = data_str.replace("data: ", "") |
|
data_json = json.loads(data_str) |
|
|
|
bots += data_json["completion"] |
|
print(bots) |
|
context += [bots] |
|
responses = [(u, b) for u, b in zip(context[::2], context[1::2])] |
|
return responses, context |
|
|
|
except Exception as e: |
|
print(">>>>>> 查询失败") |
|
print(e) |
|
print(response.text) |
|
|
|
response =">>>>>> 查询失败\n报错信息为:"+ str(e) + f"\n response信息:\n错误代码:{response.status_code}\n错误信息{response.text}" |
|
context += [response] |
|
responses = [(u, b) for u, b in zip(context[::2], context[1::2])] |
|
|
|
return responses, context |
|
|
|
finally: |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
print("*-"*100) |
|
|
|
|
|
|
|
with gr.Blocks() as dialog_app: |
|
gr.HTML("""<h1 align="center">Claude2-API-xiaolv-第2版-单轮对话</h1>""") |
|
with gr.Tab("Claude2 API xiaolv"): |
|
gr.Markdown(""" |
|
## 需要传入的参数有: |
|
1.cookie:intercom-device-id-lupk8zyo=8888 |
|
2.user_id:对应 organization_uuid |
|
## 特点: |
|
1. 根据传入的cookie 和 user_id 自动创建一个新的聊天频道(conversation_uuid/channel_id); |
|
2. 在新的聊天聊天频道进行对话; |
|
3. 请求放回后,自动删除新的聊天频道,避免频繁调用导致页面太多记录。 |
|
4. 模型只能进行一次聊天,对于特定场景比较有用,防止模型记住历史数据,影响模型对实际数据的输出额判断。 |
|
""") |
|
gr.HTML( |
|
"""5.如果想多轮对话的话,可以参考以下这个地址:<a href="https://huggingface.co/spaces/xiaolv/claude2_xiaolv">Claude2-API-xiaolv-第1版-多轮对话</a>如果喜欢请给个 💖 。""" |
|
) |
|
|
|
|
|
with gr.Row(): |
|
with gr.Column(scale=0.4): |
|
cookies = gr.Textbox(lines=2, label="输入cookies") |
|
user_id = gr.Textbox(lines=2, label="输入user_id/organization_uuid") |
|
file = gr.File(label='请上传知识库文件, 目前支持txt、csv、pdf格式',file_types=['.txt', '.csv', '.pdf']) |
|
|
|
|
|
with gr.Column(scale=0.6): |
|
chatbot = gr.Chatbot([]) |
|
|
|
state = gr.State([]) |
|
|
|
with gr.Row(): |
|
inputs = gr.Textbox( |
|
label="输入问题", |
|
placeholder="请输入你的文本,确保已经正确填入cookies、user_id" |
|
) |
|
inputs.submit(request_to_v2, [inputs, cookies, user_id,file,state], [chatbot, state]) |
|
send = gr.Button("发送请求.....") |
|
send.click(request_to_v2, [inputs, cookies, user_id,file,state], [chatbot, state], api_name="xiaolvgpt", show_progress=True) |
|
|
|
|
|
gr.Markdown(""" |
|
清除历史记录是,请输入:```/resrt```""") |
|
|
|
|
|
|
|
|
|
dialog_app.launch(show_error=True) |
|
|
|
|
|
|
|
|