如何拥有自己的大模型
尝试了一下调用、调试文心一言大模型,挺简单的。以下是从零开始的调用流程
1.前期准备
1创建百度智能云账号
进入网址后,按官网提示正常进行就行,这个应该不算难
2.实名认证
进入用户中心处,找到实名认证进行认证,上传身份证信息与照片即可,其余邮箱、电话等账号绑定依据个人口味添加
3 服务开通
在申请使用权限确认后,进入服务开通界面,点击立即使用
点击下一步
确认订单
公测账号都有测试代金券,不必担心产生额外费用,服务开通成功页面如下所示
2.调用官方大模型
在创建自己的模型前要先学会调用官方的大模型
1.创建应用接入
进入应用接入模块,点击创建应用
按顺序输入信息即可,这里推荐服务配置全选,如果第一次使用,应该是没有在线服务的,这点不需要担心
创建完成之后会生成AK(API Key)与SK(Secret Key),后续会使用
2.平台调用模型
根据自己需求在模型广场自行选择模型即可。在本文例子中我尝试ERNIE-Bot 4.0模型
选择模型后点击即可,进入界面后点击体验即可
这个时候会出现两种情况.1.?已开通付费? ? ?2.未开通付费
未开通付费
已开通后通过对话框可直接使用,未开通会受到界面提示点击开通即可
这里说明一下,不同模型收费标准不一样,根据需要购买即可
我开通的是ERNIE-Bot大模型公有云在线调用服务和ERNIE-Bot-turbo-0922大模型公有云在线调用服务和ChatGLM2-6B-32K大模型公有云训练服务-SFT-全量更新。后续如果出现对应服务未开通情况自行按需求开通即可
开通完成后
直接进行对话即可
3.本地代码调用
在确定好在官网可以正常使用,即可在本地环境(安装好对应包)进行尝试
准备阶段
这个时候就需要两样东西:AK(API Key)与SK(Secret Key)
在官方文档中,可以使用不同语言调用不同模型
网址:API列表 - 千帆大模型平台 | 百度智能云文档 (baidu.com)
python示例
以下是python示例(作者主修python)
目前我发现用户可修改三处地方
1.AK? ? ?2.SK? ? ? ?3.url
AK与SK均在应用接入时生成,直接更换即可。指向用户自己,调用密钥,将“xxxx”更换为自己的AK与SK即可
url决定调用模型种类,获取方法如下
按图中顺序依次选择。在自己创建的应用最右侧点击移动端测试,选择自己要进行的服务(及大模型),之后官网会自动生成对应的API信息:二维码、请求地址、API Key、Secret Key、模型名称、应用名称。我们需要的即是请求地址,复制请求地址
在下面代码中第十行,main()第一行中的”https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/om82aolq_kubila“部分修改为自己的请求地址即可
url = "https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/om82aolq_kubila?access_token=" + get_access_token()
import requests
import json
API_KEY = "xxxx"
# API_KEY
SECRET_KEY = "xxxx"
# SECRET_KEY
def main():
url = "https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/completions?access_token=" + get_access_token()
payload = json.dumps({
"messages": [
{
"role": "user",
"content": "介绍一下你自己"
}
]
})
headers = {
'Content-Type': 'application/json'
}
response = requests.request("POST", url, headers=headers, data=payload)
print(response.json()["result"])
def get_access_token():
url = "https://aip.baidubce.com/oauth/2.0/token"
params = {"grant_type": "client_credentials", "client_id": API_KEY, "client_secret": SECRET_KEY}
return str(requests.post(url, params=params).json().get("access_token"))
if __name__ == '__main__':
main()
本地调用
在本地环境进行运行即可调用,可根据需求进行修改问题与界面
修改代码
比如修改代码后在新的命令窗口或网页调用(自行修改代码即可)
from flask import Flask, render_template, request
import requests
import json
from PyQt5.QtCore import Qt
from PyQt5.QtWidgets import QApplication, QWidget, QVBoxLayout, QLabel, QTextEdit, QPushButton, QHBoxLayout, \
QScrollArea
app = Flask(__name__)
API_KEY = "xxxx"
SECRET_KEY = "xxxx"
class ChatWindow(QWidget):
def __init__(self):
super().__init__()
self.setWindowTitle('Chat')
self.setStyleSheet("""
background-color: lightblue;
font-family: Arial, sans-serif;
""")
self.init_ui()
def init_ui(self):
main_layout = QVBoxLayout()
chat_window = QScrollArea()
chat_window.setWidgetResizable(True)
chat_window.setVerticalScrollBarPolicy(Qt.ScrollBarAlwaysOn)
chat_window.setHorizontalScrollBarPolicy(Qt.ScrollBarAlwaysOff)
chat_container = QWidget()
chat_layout = QVBoxLayout(chat_container)
chat_window.setWidget(chat_container)
main_layout.addWidget(QLabel('<h1>糖患卫士</h1>'))
main_layout.addWidget(chat_window)
input_layout = QHBoxLayout()
prompt_input = QTextEdit()
prompt_input.setPlaceholderText("输入消息")
input_layout.addWidget(prompt_input)
send_button = QPushButton("发送")
input_layout.addWidget(send_button)
main_layout.addLayout(input_layout)
self.setLayout(main_layout)
send_button.clicked.connect(lambda: self.add_message('user', prompt_input.toPlainText()))
prompt_input.returnPressed.connect(send_button.click)
def add_message(self, role, content):
message_box = QTextEdit(content)
message_box.setReadOnly(True)
message_box.setStyleSheet("""
background-color: white;
padding: 20px;
border-radius: 5px;
margin-bottom: 20px;
""")
if role == 'user':
message_box.setAlignment(Qt.AlignLeft)
else:
message_box.setAlignment(Qt.AlignRight)
chat_container = self.findChild(QWidget, 'chat_container')
chat_layout = chat_container.layout()
chat_layout.addWidget(message_box)
scroll_bar = self.findChild(QScrollArea).verticalScrollBar()
scroll_bar.setValue(scroll_bar.maximum())
def main(prompt):
url = "https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/om82aolq_kubila?access_token=" + get_access_token()
payload = json.dumps({
"messages": [
{
"role": "user",
"content": prompt
}
]
})
headers = {
'Content-Type': 'application/json'
}
response = requests.request("POST", url, headers=headers, data=payload)
return eval(response.text.replace('false','"false"'))['result']
def get_access_token():
url = "https://aip.baidubce.com/oauth/2.0/token"
params = {"grant_type": "client_credentials", "client_id": API_KEY, "client_secret": SECRET_KEY}
return str(requests.post(url, params=params).json().get("access_token"))
@app.route('/')
def index():
return render_template('index.html')
@app.route('/submit', methods=['POST'])
def submit():
prompt = request.form['prompt']
content = main(prompt)
return {'role': 'bot', 'content': content}
if __name__ == '__main__':
chat_window = ChatWindow()
app = QApplication([])
chat_window.show()
app.run()
C++语言示例
准备与修改内容同上
#include <stdio.h>
#include <iostream>
#include <string.h>
#include <curl/curl.h>
#include <json/json.h>
#include <fstream>
#include <memory>
std::string client_id = "xxx";
std::string client_secret = "xxx";
inline size_t onWriteData(void * buffer, size_t size, size_t nmemb, void * userp)
{
std::string * str = dynamic_cast<std::string *>((std::string *)userp);
str->append((char *)buffer, size * nmemb);
return nmemb;
}
std::string getAccessToken()
{
std::string result;
CURL *curl;
CURLcode res;
curl = curl_easy_init();
if(curl)
{
curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "POST");
curl_easy_setopt(curl, CURLOPT_URL, "https://aip.baidubce.com/oauth/2.0/token");
curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
curl_easy_setopt(curl, CURLOPT_DEFAULT_PROTOCOL, "https");
struct curl_slist *headers = NULL;
headers = curl_slist_append(headers, "Content-Type: application/x-www-form-urlencoded");
headers = curl_slist_append(headers, "Accept: application/json");
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
std::string data = "grant_type=client_credentials&client_id="+client_id+"&client_secret="+client_secret;
curl_easy_setopt(curl, CURLOPT_POSTFIELDS, data.c_str());
curl_easy_setopt(curl, CURLOPT_WRITEDATA, &result);
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, onWriteData);
res = curl_easy_perform(curl);
}
curl_easy_cleanup(curl);
Json::Value obj;
std::string error;
Json::CharReaderBuilder crbuilder;
std::unique_ptr<Json::CharReader> reader(crbuilder.newCharReader());
reader->parse(result.data(), result.data() + result.size(), &obj, &error);
return obj["access_token"].asString();
}
int main(int argc, char *argv[])
{
std::string result;
CURL *curl;
CURLcode res;
curl = curl_easy_init();
if(curl) {
curl_easy_setopt(curl, CURLOPT_CUSTOMREQUEST, "POST");
curl_easy_setopt(curl, CURLOPT_URL, ("https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/completions?access_token=" + getAccessToken()).c_str());
curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
curl_easy_setopt(curl, CURLOPT_DEFAULT_PROTOCOL, "https");
struct curl_slist *headers = NULL;
headers = curl_slist_append(headers, "Content-Type: application/json");
curl_easy_setopt(curl, CURLOPT_HTTPHEADER, headers);
const char *data = "{\"messages\":[{\"role\":\"user\",\"content\":\"介绍一下你自己\"},{\"role\":\"assistant\",\"content\":\"您好,我是文心一言,英文名是ERNIE Bot。我能够与人对话互动,回答问题,协助创作,高效便捷地帮助人们获取信息、知识和灵感。\"}]}";
curl_easy_setopt(curl, CURLOPT_POSTFIELDS, data);
curl_easy_setopt(curl, CURLOPT_WRITEDATA, &result);
curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, onWriteData);
res = curl_easy_perform(curl);
std::cout<<result;
}
curl_easy_cleanup(curl);
return (int)res;
}
GO示例
package main
import (
"encoding/json"
"fmt"
"io/ioutil"
"net/http"
"strings"
)
const API_KEY = "RgAq3HSxxxxDlvXOoLy"
const SECRET_KEY = "zWSdXWxxxxKmkRWi8YORj"
func main() {
url := "<https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/completions?access_token=>" + GetAccessToken()
payload := strings.NewReader(``)
client := &http.Client {}
req, err := http.NewRequest("POST", url, payload)
if err != nil {
fmt.Println(err)
return
}
req.Header.Add("Content-Type", "application/json")
res, err := client.Do(req)
if err != nil {
fmt.Println(err)
return
}
defer res.Body.Close()
body, err := ioutil.ReadAll(res.Body)
if err != nil {
fmt.Println(err)
return
}
fmt.Println(string(body))
}
/**
* 使用 AK,SK 生成鉴权签名(Access Token)
* @return string 鉴权签名信息(Access Token)
*/
func GetAccessToken() string {
url := "<https://aip.baidubce.com/oauth/2.0/token>"
postData := fmt.Sprintf("grant_type=client_credentials&client_id=%s&client_secret=%s", API_KEY, SECRET_KEY)
resp, err := http.Post(url, "application/x-www-form-urlencoded", strings.NewReader(postData))
if err != nil {
fmt.Println(err)
return ""
}
defer resp.Body.Close()
body, err := ioutil.ReadAll(resp.Body)
if err != nil {
fmt.Println(err)
return ""
}
accessTokenObj := map[string]string{}
json.Unmarshal([]byte(body), &accessTokenObj)
return accessTokenObj["access_token"]
}
其它
错误码
如果请求错误,服务器返回的JSON文本包含以下参数。
名称 | 描述 |
---|---|
error_code | 错误码 |
error_msg | 错误描述信息,帮助理解和解决发生的错误 |
例如Access Token失效返回以下内容,需要重新获取新的Access Token再次请求。
{
"error_code": 110,
"error_msg": "Access token invalid or no longer valid"
}
千帆大模型平台相关错误码,请查看错误码说明。
4.自己微调大模型
1.数据集准备
在微调大模型前需要准备好自己的数据集json文件、txt文件、csv文件、xlsx文件、压缩包文件(本文已json文件为例
进入网址后,点击图中创建数据集按钮
根据个人要求进行命名,选择数据类型、标注类型、标注模板、保存位置等等,完成后点击创建并导入即可
构建方式、数据标注状态、导入方式、导入格式后直接上传即可,这里采取有标注信息的json文件采取本地导入的方式。
json文件格式数据要求如下
1. 文件内单条数据格式要求为[{"prompt" : "prompt内容", "response": [["response内容"]]}],?下载数据样例。
2. 每一行表示一组数据,每组数据中的prompt和response加起来之和字符数不超过32000Token(包括中英文、数字、符号等),超出部分将被截断。
3. 支持文本文件类型为jsonl,编码仅支持UTF-8,单次上传限制100个文本文件,单个文件不超过100M
[{"prompt": "xxxx", "response": [["xxxx"]]}]
[{"prompt": "xxxx", "response": [["xxxx"]]}]
[{"prompt": "xxxx", "response": [["xxxx"]]}]
[{"prompt": "xxxx", "response": [["xxxx"]]}]
[{"prompt": "xxxx", "response": [["xxxx"]]}]
按照上述方式上传后,等待一分钟左右数据导入完成。如若无需修改,选择发布即可,发布完成后,数据集上传已完成,进入下一步模型训练。
2.模型训练
导入数据及后开始将新数据进行模型训练,按下图选择任务名称、任务类型任务描述、选择基础模型、模型版本(这里模型要选择自己开通过的,否则要从新开通)
训练配置可选择增量训练(仅支持选择2023年9月22日后训练的模型。同时由于大模型权重占用较大存储,只能选择三个月内训练的模型发起增量训练),
训练方法分为两种:1.全量更新(全量更新在训练过程中对大模型的全部参数进行更新)2.
LoRA(LoRA在固定预训练大模型本身的参数的基础上,在保留自注意力模块中原始权重矩阵的基础上,对权重矩阵进行低秩分解,训练过程中只更新低秩部分的参数。)建议选择LoRA)
其余数据配置按需要选择,数据集这是可选择第一步构造的“我的数据集”,选择完之后进行付费训练即可。这里注意是否开通对应服务,若未开通,在确定按钮右侧选择“前往开通“即可。
点击确定并付费后会进行训练,这里时间可能会较长,训练完成后即可进入下一步
等待模型训练完成后,将模型发布,即可开启大模型服务
创建的大模型可在我的模型处查看并编辑
3.开启大模型服务
在模型创建并发布成功后,即可开启大模型服务
进入在线服务界面选择我的服务后点击创建服务即可
进入创建界面后,1.输入服务名称(任意、支持中文、英文、数字、中划线(-)、下划线(_),1-20个字符以内),2.选择模型,3.这里选择我的模型,在这里会看到我们上一步发布的模型,4.输入API地址(这里按格式要求命名即可),5.选择资源池,这里选择私人资源池,6.随后选择开通的时间(这里我感觉这个消费还是比较贵的,哎),可以选的对应天数与小时,最低一个小时,我这里28元。7.点击确定后付费即可(注册时的20元代金卷可以使用)
模型服务发布需要等待几分钟
点击服务详情后复制标注出的服务地址,下一步会使用。
到这里模型已经发布
4.调用大模型服务
这里直接参考上述本地代码调用即可
?在下面代码中第十行,main()第一行中的”https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/om82aolq_kubila“部分修改为自己的请求地址即可(及上一步复制信息)
url = "https://aip.baidubce.com/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/om82aolq_kubila?access_token=" + get_access_token()
在调用前要保证应用接入AK与SK的服务要包含自己新开通的服务即可调用
作者新尝试调用大模型,如有错误拜托大家及时联系,希望能帮到大家
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。 如若内容造成侵权/违法违规/事实不符,请联系我的编程经验分享网邮箱:veading@qq.com进行投诉反馈,一经查实,立即删除!