在 .NET 客户端中使用协议缓冲区对 RESTful 请求进行结构支持
此示例显示当您使用 .NET 客户端 API、MATLAB® Production Server™ 用于 MATLAB 函数执行的 RESTful API 和协议缓冲区 (protobuf) 发出同步请求时,如何发送表示为 .NET 对象数组的 MATLAB 结构体 (struct
(MATLAB)) 作为输入。该示例提供并解释了一个示例 Java® 客户端 SortStudentsSyncREST.cs
,用于评估部署在服务器上的 MATLAB 函数。
要在向服务器发出请求时使用 protobuf,请在客户端代码中将 HTTP Content-Type
请求标头设置为 application/x-google-protobuf
。.NET 客户端库中的 MathWorks.MATLAB.ProductionServer.Client.REST
命名空间提供了辅助类,用于内部根据 proto 格式创建 protobuf 消息并返回相应的字节数组。在 HTTP 请求正文中使用此字节数组。.NET 客户端库提供了反序列化 protobuf 响应的方法和类。
在同步请求执行中,客户端发出请求后,服务器模块所有进一步的请求,直到完成对原始请求的处理为止。处理完成后,服务器自动向客户端返回响应。有关详细信息,请参阅同步执行。
要使用 .NET 客户端 API,您必须在 C#工程中添加对 MathWorks.MATLAB.ProductionServer.Client.dll
文件的引用。有关为您的工程准备 Microsoft® Visual Studio® 环境的更多信息,请参阅准备您的 Microsoft Visual Studio 环境。
在本地 MATLAB Production Server 安装中,客户端 API 位于
,其中 $MPS_INSTALL
/client
是 MATLAB Production Server 的安装位置。客户端 API 也可从 MATLAB Production Server 客户端库下载。Java 客户端 API 也托管在 https://mvnrepository.com/artifact/com.mathworks.prodserver/mps_java_client 的 Maven™ 存储库中。$MPS_INSTALL
将 MATLAB 函数部署到服务器
编写一个 MATLAB 函数 sortstudents
,以包含学生信息的结构体数组作为输入,并根据学生分数返回已排序的学生数组。学生姓名、分数和成绩构成输入结构体的字段。在服务器上部署此函数。该示例假定服务器实例在 http://localhost:9910
上运行。
有关如何部署的信息,请参阅针对 MATLAB Production Server 创建可部署存档。
示例 MATLAB struct
S
和 MATLAB 函数 sortstudents
的代码如下。
S.name = 'Ed Plum'; S.score = 83; S.grade = 'B+'
function sorted = sortstudents(unsorted)
scores = {unsorted.score};
scores = cell2mat(scores);
[s i] = sort(scores);
sorted = unsorted(i);
创建辅助类
创建 .NET 类来将数据发送到 MATLAB struct
或从后者接收数据。
创建一个具有与输入结构体相同数据成员的 .NET 类
Student
。class Student { public string name; private string gr; private int sc; public string grade { get { return gr; } set { gr = value; } } public int score { get { return sc; } set { sc = value; } } public override string ToString() { return name + " : " + grade + " : " + score; } }
创建一个扩展接口
StudentMarshaller
的 .NET 类MWDefaultMarshalingRules
。由于 .NET 本身不支持结构体,因此扩展MWDefaultMarshalingRules
接口可让您为被编组的类列表实现一组新的编组规则,将 .NET 对象序列化为结构体,并将结构体反序列化为 .NET 对象。设置StructTypes
属性以返回类型Student
。class StudentMarshaler : MWDefaultMarshalingRules { public override IList<Type> StructTypes { get { return new List<Type> { typeof(Student) }; } } }
创建一个想要排序的
Student
类型的数组。Student s1 = new Student(); s1.name = "Tony Miller"; s1.score = 90; s1.grade = "A"; Student s2 = new Student(); s2.name = "Ed Plum"; s2.score = 80; s2.grade = "B+"; Student s3 = new Student(); s3.name = "Mark Jones"; s3.score = 85; s3.grade = "A-"; Student[] unsorted = new Student[] { s1, s2, s3 };
向服务器发出同步请求
在 C# 客户端代码中,使用 POST Synchronous Request 向服务器发出初始请求。有关 MATLAB Production Server 中同步请求执行的更多信息,请参阅同步执行。
创建请求。
使用 .NET
WebRequest.Create
方法创建 POST 同步请求。请求 URL 包括服务器实例的地址(
http://localhost:9910
)、部署的存档的名称(sortstudents
)和要评估的 MATLAB 函数的名称(sortstudents
)。将 HTTP 请求方法设置为POST
。将 HTTPContent-Type
请求标头设置为application/x-google-protobuf
,因为 API 返回协议缓冲区消息的字节数组。String mpsBaseUrl = "http://localhost:9910"; var firstRequest = (HttpWebRequest)WebRequest.Create(mpsBaseUrl + "/sortstudents/sortstudents"); firstRequest.Method = "POST"; firstRequest.ContentType = "application/x-google-protobuf";
将请求发送到服务器。
使用 .NET
WebRequest.getResponse
方法将请求发送到服务器。使用 MATLAB Production Server .NET 客户端 API 的
Create(arg1, arg2, arg3, arg4)
类中定义的MATLABParams
方法来构建协议缓冲区消息。Create
方法将部署函数的预期输出参量数量、预期输出类型、MWDefaultMarshalingRules
类型的对象以及表示部署函数输入的对象数组作为输入。由于部署的sortstudents
函数返回单个结构体数组,因此将arg1
设置为1
,将arg2
设置为new List<Type> { typeof(Student[]) }
。将arg3
设置为new StudentMarshaler()
,将arg4
设置为new object[] { unsorted }
,这是sortstudents
函数的输入。MATLABParams mlParams = MATLABParams.Create(1, new List<Type> { typeof(Student[]) }, new StudentMarshaler(), new object[] { unsorted }); mlParams.WriteTo(firstRequest.GetRequestStream()); var response = (HttpWebResponse)firstRequest.GetResponse();
有关 WebRequest
类的更多信息,请参阅 Microsoft 文档。
接收并解释服务器响应
成功执行 POST 同步请求后,服务器将以协议缓冲区消息进行响应。使用 MATLABResult
类的方法解析协议缓冲区消息以获取请求的结果。要创建 MATLABResult
对象,请将 MATLABParams
mlParams
对象和 POST 同步请求的响应主体传递给 Create
方法。将 MATLABResult
mlResult
的返回类型设置为 Student[]
。
如果部署的 MATLAB 函数执行时出现错误,则对 Result
方法的调用将抛出包含来自 MATLAB 的错误消息的 MATLABException
。
MATLABResult mlResult; mlResult = MATLABResult.Create(mlParams, response.GetResponseStream()); try { Student[] result = mlResult.Result<Student[]>(); Console.WriteLine("Printing the sorted Student array...\n"); PrintStudent(result); } catch (MATLABException e) { Console.WriteLine(e.ToString()); }
该示例使用辅助方法 PrintStudent
,该方法将 POST 同步请求的响应主体作为输入,并打印相应的学生排序列表。
static void PrintStudent(Student[] students) { foreach (Student s in students) { Console.WriteLine(s.ToString()); } }
运行该应用程序将生成以下输出。
Printing the sorted Student array... Ed Plum : B+ : 80 Mark Jones : A- : 85 Tony Miller : A : 90
以下是 SortStudentsSyncREST.cs
C# 客户端的示例代码。
代码: