c# - 通过 UnityWebRequest 发送“复杂”模型数据
问题描述
我正在尝试在我的 Unity 项目中使用一些简单的 .NET API。通过手动指定每个字段的名称,我已经能够在 API 服务器上填充模型(类)。问题是这些模型的内容主要是原始数据类型,主要是整数和字符串。我的模型结构将需要嵌套模型(类),例如:
public class Echo
{
public string text { get; set; }
}
public class ComplexData
{
public List<Echo> echo { get; set; }
public string description { get; set; }
}
我在 Unity 中有完全相同的模型,serializable
并且没有 getter 和 setter,因为这是我在研究中看到的。
所以这是我用来发送这个模型的代码,它在被发送到这个函数之前填充(并通过断点确认)。请记住,我尝试过WWWForm
、Dictionary
和IMultipartFormSection
数据类型无济于事。我将它们留在代码中只是为了演示我到目前为止所做的尝试:
IEnumerator sendComplexModel(string url, ComplexData complexData)
{
string complex = JsonUtility.ToJson(complexData);
WWWForm form = new WWWForm();
form.AddField("complexData", complex);
Dictionary<string, string> keyValuePairs = new Dictionary<string, string>();
keyValuePairs.Add("complexData", complex);
List<IMultipartFormSection> formData = new List<IMultipartFormSection>();
formData.Add(new MultipartFormDataSection("complexData", complex));
UnityWebRequest uwr = UnityWebRequest.Post(url, formData);
yield return uwr.SendWebRequest();
if (uwr.isNetworkError)
{
Debug.Log("Something went wrong");
}
else
{
Debug.Log(uwr.downloadHandler.text);
}
}
你可以假设我已经更新了参数:UnityWebRequest uwr = UnityWebRequest.Post(url, formData);
使用我上面创建的相关数据结构进行测试
将 null 传递给 .NET的每个重载函数UnityWebRequest
如 Visual Studio 的此屏幕截图所示:
我究竟做错了什么?使用标准的 Unity 库是否可以实现这样的功能?我更愿意坚持使用UnityWebRequest
Unity 中内置的任何类似库。
这是两个模型(类)的并排,左边是 .NET API,右边是 Unity:
任何帮助将不胜感激,在此先感谢。
====================更新=======================
@LukeBriggs
我已经按如下方式实现了您的代码,再次进行完整性检查,在网络调用之前添加一个断点以仔细检查我实际上是在发送一个填充模型。
这就是我更新代码的方式:
string complex = JsonUtility.ToJson(complexData);
UnityWebRequest uwr = UnityWebRequest.Post(url, complex);
uwr.SetRequestHeader("Content-Type", "application/json");
yield return uwr.SendWebRequest();
if (uwr.isNetworkError)
{
Debug.Log("Something went wrong");
}
else
{
Debug.Log(uwr.downloadHandler.text);
}
Visual Studio 现在通过空引用异常,而以前它只会显示模型属性/字段为空。截屏:
解决方案
内容类型很重要
首先,将 Unity 视为常规 JSON API 的任何其他客户端。然后目标是让 Unity 发送 JSON 结构化数据。
提示:您还可以创建一些 JSON 并将其发布到您的 API 中,使用 postman、curl 等工具,甚至只是 Web 浏览器中的 devtools 来测试 API 方面的事情。
所以,你目前真的很接近那个。缺少的关键部分只是您的标题。发出 POST 请求时,您必须指定实际发送的数据格式——这是由Content-Type
标头完成的。标准默认是多部分表单内容类型,它不支持这种嵌套数据,但 JSON 支持。以下是在 Unity 中指定“我正在发布 JSON”的方式:
string jsonToSend = JsonUtility.ToJson(complexData);
UnityWebRequest uwr = UnityWebRequest.Post(url, "");
uwr.uploadHandler = new UploadHandlerRaw(System.Text.Encoding.UTF8.GetBytes(jsonToSend));
uwr.SetRequestHeader("Content-Type", "application/json"); // <--- The missing magic line
yield return uwr.SendWebRequest();
..
[FromBody] 也很重要
在您的 API 中,尝试添加 [FromBody] 参数属性,如下所示:
public string getComplexData([FromBody] ComplexData complexData)
{
..
}
推荐阅读
- javascript - 如果条件不满足,如何从正文中删除类?
- reactjs - 如何使用 url GET 参数中的密钥设置 AWS 放大公共 API?
- python - 在python中聚合n行数据帧的随机子集
- asp.net-core-3.0 - ToLocalTime 的时区是否有变化
- javascript - 选定值的 InnerHTML 输出
- angular - 如何以 Angular Reactive 形式获取复选框值
- azure - 如何在 Azure 门户中登录到不同的租户(非默认)?
- sonarqube - Github Actions、Python Coverage 和 Sonar Qube
- javascript - 需要使用 JS 替换页面上的 URL
- python - 如何设置相对路径以使用 Python 3 在 PyInstaller 中构建可移植的 .exe?