WARNING: MicroPython ignores non-ascii characters of the input

会造成后端错误 获取不到json 但是data有数据

您遇到的错误 "werkzeug.exceptions.BadRequest: 400 Bad Request: Failed to decode JSON object: 'utf-8' codec can't decode byte 0xe5 in position 21: unexpected end of data" 表明服务器无法正确解码您发送的 JSON 数据。

解决方案:

eps32中字符串解析问题 主要为像后端传递数据需要.encode('utf-8')

原因分析:

  • 编码不匹配: 服务器期望接收 UTF-8 编码的 JSON 数据,而您发送的数据可能不是 UTF-8 编码。
  • 数据损坏: 数据在传输过程中可能被损坏,导致服务器无法正确解析。

前端去请求后端字符的问题

调整代码: 如果您使用的是 Python 语言,请在发送数据之前将其编码为 UTF-8。例如:

1.在esp32中设置

示例代码:
import ujson
import urequests
# 确保数据使用 UTF-8 编码
data = ujson.dumps({"user_message": user_message}).encode('utf-8')
# 发送请求
response = urequests.post(SERVER_URL, data=data, headers={"Content-Type": "application/json;charset=utf-8"})

2在后端直接获取data数据

esp32 通信 完整代码

#!/usr/bin/env python
# -*- coding: utf-8 -*-
import network
import urequests
import ujson
import time
import sys
# 配置Wi-Fi信息
# WiFi配置
SSID  = 'ChinaNet-Z252pK'
PASSWORD  = '88888888'

# 服务器URL(假设服务器在本地电脑上运行)
SERVER_URL = "http://192.168.2.3:5000/chat"  # 将 <PC_IP_ADDRESS> 替换为实际的服务器IP地址

# 连接Wi-Fi
def connect_wifi():
    wlan = network.WLAN(network.STA_IF)
    wlan.active(True)
    wlan.connect(SSID, PASSWORD)

    print("Connecting to WiFi...")
    while not wlan.isconnected():
        time.sleep(1)
        print(".", end="")

    print("\nConnected to WiFi.")
    print("IP address:", wlan.ifconfig()[0])

# 发送用户消息并获取助手响应
def send_message(user_message):
    headers = {"Content-Type": "application/json;charset=utf-8"}
    data = ujson.dumps({"user_message": user_message}).encode('utf-8')
    print({"User":user_message.decode('utf-8')}) 
    try:
        response = urequests.post(SERVER_URL, data=data, headers=headers,timeout=10)  # 设置超时时间为10秒
        if response.status_code == 200:
            # 解析服务器返回的JSON响应
            response_json = response.json()
            assistant_message = response_json.get("assistant_message", "No message returned")
            print("Assistant:", assistant_message.encode('utf-8').decode('unicode_escape'))  # 正确处理非ASCII字符
        else:
            print(f"Error: {response.status_code}")
        response.close()
    except Exception as e:
        print("Error sending request:", e)

# 主程序
def main():
    # 连接Wi-Fi
    connect_wifi()
    time.sleep(2)  # 等待Wi-Fi连接稳定

    # 循环获取用户输入并发送给服务器
    while True:
        print("Enter your message:")
        try:
            user_input = sys.stdin.readline().strip()  # 读取用户输入
        except Exception as e:
            print(f"Error reading input: {e}")
            continue
        if user_input.lower() == "exit":
            print("Exiting...")
            break
        if user_input.lower() == "":
            print("continue...")
            continue
        send_message(user_input)
        time.sleep(1)

# 启动主程序
main()

前端输入中文后,怎么转义Unicode 显示中文

在 MicroPython 环境下,处理字符串和 Unicode 的方式与标准的 Python 3 有些不同。MicroPython 的字符串通常是字节串(bytes),并且它的 Unicode 处理方式可能不如标准 Python 那么完整。不过,如果你已经有了像 \u4f60\u597d 这样的 Unicode 转义序列并希望正确显示为中文字符,你需要确保以下几点:

确保字符串是 Unicode 字符串。在 MicroPython 中,直接打印字符串时,若它是有效的 Unicode 字符串,应该能够正常显示中文字符。
从字节流解码为字符串,如果你的输入是字节流,应该显式地将其解码为字符串。
解决方法
1. 如果你已经有一个字面量字符串,包含 Unicode 转义序列(比如 \u4f60\u597d),直接打印即可:
python
# 假设这是你从某个地方获取到的字典
data = {'User': '\u4f60\u597d'}

# 直接打印 'User' 对应的值,它会显示中文
print(data['User'])  # 输出:你好
2. 如果是从字节流读取的数据,可能需要显式地解码:
python
# 假设你从某个地方读取了字节流,类似于 sys.stdin 或其他输入方式
import sys

user_input = sys.stdin.buffer.readline().strip()  # 读取字节流
# 解码并打印
print(user_input.decode('utf-8'))  # 输出:你好
3. 如果 Unicode 字符串存在 Unicode 转义(比如你获取的数据是 \u4f60\u597d),你可以使用 eval() 或手动转义来显示中文字符:
python
# 假设你有一个包含 Unicode 转义字符的字符串
unicode_string = r'\u4f60\u597d'

# 使用 eval 来转义成真实的 Unicode 字符串
print(eval(f'"{unicode_string}"'))  # 输出:你好
解释:
在 MicroPython 中,eval(f'"{unicode_string}"') 会将 \u4f60\u597d 转换为对应的中文字符 '你好'。
decode('utf-8') 适用于字节串,如果你读取的内容是字节流(bytes),你需要将其解码为字符串。
注意:
MicroPython 对 Unicode 支持有限,尤其在早期版本中,可能会遇到一些边界情况,特别是在处理非常大的字符集时。不过,对于常见的情况(如简单的中文字符),上述方法应该能够解决问题。