721浏览
查看: 721|回复: 0

[ESP8266/ESP32] Beetle ESP32 C6试用评测【2】AIGC大爆发

[复制链接]
本帖最后由 kylinpoet 于 2024-4-15 19:00 编辑

一、前言

       各位大佬的评测文章陆续上传,屏幕显示、传感器、执行件等陆续上阵,满目琳琅,但好像没有看到声音处理的相关帖子(或者是我没发现?)本来想接个麦克风,用API搞个网络语音识别。但翻遍家里仓库,没有找到可用设备,只好作罢。还是按照原思路,把esp32和现在流行的AIGC做个联结。
       笔者在
前文 最后的内容中提到的ESP32 Web Server,就是为本文准备的。



二、AIGC平台和智谱清言
      
       现在市面上的AIGC平台很多,有开源也有商用的。由清华智谱研发的 ChatGLM 效果是较理性的。正好这几天在本地搭建了白嫖glm4的API服务,正好拿来试手,当然大家有兴趣也可以使用 ChatGLM智谱清言 的网络端进行试用(选择glm4效果更佳,可绘图)。

Beetle ESP32 C6试用评测【2】AIGC大爆发图1

      确定好平台后,就可以使用现成的工具来生成板子的python代码了,我们可以看到,生成的代码逻辑比较准确,基本上可以无损使用:

Beetle ESP32 C6试用评测【2】AIGC大爆发图2

配置好,相关参数,就可以愉快玩耍了。

Beetle ESP32 C6试用评测【2】AIGC大爆发图3

在thonny选择主板执行,访问打印的IP地址:

Beetle ESP32 C6试用评测【2】AIGC大爆发图4
Beetle ESP32 C6试用评测【2】AIGC大爆发图5

当然,怎么能只有文字呢,要图片也是可以可以顺手捏来的。

Beetle ESP32 C6试用评测【2】AIGC大爆发图6

三、几个坑点

1. 万恶的Python 2过去了,以为在Python 3里不会有编码问题了,很不幸,因为在mpy里用socket创建Web服务的时候,是用字节字符串进行数据传输的,因此在处理 html 的 form post 传过来的数据时,需要进行编码处理:
Beetle ESP32 C6试用评测【2】AIGC大爆发图7

当然这个函数,是用GLM4 在线生成的,毕竟mpy 自带的 url 处理函数还不是很完整:

Beetle ESP32 C6试用评测【2】AIGC大爆发图8

2. 在进行数据post时,要进行data的字节化处理,这里被耽搁了下,主要是要使用:data.encode()这个方法。


Beetle ESP32 C6试用评测【2】AIGC大爆发图9

3. 当然,还有生成图片时,返回数据的解析处理等,必须使用AIGC来完成,使用起来相当丝滑:

Beetle ESP32 C6试用评测【2】AIGC大爆发图10

Beetle ESP32 C6试用评测【2】AIGC大爆发图11

四、完整代码

  1. import socket
  2. import urequests
  3. import json
  4. # WiFi设置
  5. SSID = 'ssid'
  6. PASSWORD = 'pass'
  7. # OpenAI API设置
  8. API_URL = 'http://*.*.*.*:8000/v1/chat/completions'
  9. API_KEY = 'eyJhbG......'
  10. def connect_wifi(ssid, password):
  11.     import network
  12.     sta_if = network.WLAN(network.STA_IF)
  13.     if not sta_if.isconnected():
  14.         print('Connecting to WiFi...')
  15.         sta_if.active(True)
  16.         sta_if.connect(ssid, password)
  17.         while not sta_if.isconnected():
  18.             pass
  19.     print('WiFi connected')
  20.     print('ip:{}'.format(sta_if.ifconfig()[0]))
  21. def decode_html_entities(encoded_str):
  22.     import re
  23.     # 正则表达式用于找到形式为 %26%23<数字>%3B 的编码实体
  24.     pattern = re.compile(r'%26%23(\d+)%3B')
  25.     # 函数用于替换每个匹配的实体
  26.     def replace_entity(match):
  27.         # 提取数字部分,并转换为整数
  28.         code_point = int(match.group(1))
  29.         # 将整数转换为对应的Unicode字符
  30.         return chr(code_point)
  31.     # 使用正则表达式的sub方法替换所有匹配的实体
  32.     return pattern.sub(replace_entity, encoded_str)
  33. def start_server():
  34.     s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
  35.     s.bind(('', 80))
  36.     s.listen(5)
  37.     while True:
  38.         conn, addr = s.accept()
  39.         request = str(conn.recv(1024))
  40.         print(request)
  41.         
  42.         # 检查是否是POST请求
  43.         if 'POST /' in request:
  44.             # 解析用户输入
  45.             # request = request.decode()
  46.             start_index = request.find('prompt=') + len('prompt=')
  47.             input_text = request[start_index:-1].replace('%20', ' ')
  48.             input_text = decode_html_entities(input_text)
  49.             print(input_text)
  50.             # 使用OpenAI API获取结果
  51.             response = use_openai_api(input_text)
  52.             
  53.             # 发送HTTP响应
  54.             conn.send('HTTP/1.1 200 OK\n')
  55.             conn.send('Content-Type: text/html\n')
  56.             conn.send('Connection: close\n\n')
  57.             conn.sendall(html_page(response))
  58.         else:
  59.             # 发送HTML表单
  60.             conn.send('HTTP/1.1 200 OK\n')
  61.             conn.send('Content-Type: text/html\n')
  62.             conn.send('Connection: close\n\n')
  63.             conn.sendall(html_page(None))
  64.         
  65.         conn.close()
  66. def use_openai_api(prompt):
  67.     headers = {
  68.         'Content-Type': 'application/json',
  69.         'Authorization': 'Bearer ' + API_KEY
  70.     }
  71.     data = json.dumps(
  72.         {
  73.             "model": "glm4",
  74.             "messages": [{
  75.                 "role": "user",
  76.                 "content": prompt}],
  77.             "stream": False}
  78.         )
  79.     # try:
  80.     print(data)
  81.     response = urequests.post(API_URL, headers=headers, data=data.encode())
  82.     response = response.json()
  83.     print(response)
  84.     return response['choices'][0]['message']['content']
  85.     # except Exception as e:
  86.         # print(str(e))
  87. def extract_image_url(text):
  88.     # 使用正则表达式匹配图片链接
  89.     import re
  90.     image_url_match = re.search(r'!\[.*?\]\((https://.*?\.(png|jpg|jpeg|gif))\)', text)
  91.     if image_url_match:
  92.         return image_url_match.group(1)
  93.     return None
  94. def html_page(result):
  95.     # image_url = extract_image_url(result)        
  96.     if result:
  97.         image_url = extract_image_url(result)
  98.         if image_url:
  99.             response_html = f"<p><img src='{image_url}' alt='OpenAI Response' width='500px'></br >{result}</p>"
  100.         else:
  101.             response_html = f"<p>{result}</p>"
  102.     else:
  103.         response_html = ""
  104.     return f"""
  105.     <html>
  106.     <head>
  107.     <meta charset="UTF-8">
  108.     </head>
  109.     <body>
  110.     <h2>OpenAI Input:</h2>
  111.     <form action="/" method="post">
  112.     <textarea style="width: 500px; height: 100px;" name="prompt" rows="4" cols="50"></textarea>
  113.     <br>
  114.     <input type="submit" value="Submit">
  115.     </form>
  116.     <h2>OpenAI Response:</h2>
  117.     {response_html}
  118.     </body>
  119.     </html>
  120.     """
  121. # 连接到WiFi
  122. connect_wifi(SSID, PASSWORD)
  123. # 启动服务器
  124. start_server()
复制代码


以上!




您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

为本项目制作心愿单
购买心愿单
心愿单 编辑
[[wsData.name]]

硬件清单

  • [[d.name]]
btnicon
我也要做!
点击进入购买页面
上海智位机器人股份有限公司 沪ICP备09038501号-4

© 2013-2024 Comsenz Inc. Powered by Discuz! X3.4 Licensed

mail