• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2022 The Pigweed Authors
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License"); you may not
4 // use this file except in compliance with the License. You may obtain a copy of
5 // the License at
6 //
7 //     https://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
11 // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
12 // License for the specific language governing permissions and limitations under
13 // the License.
14 
15 #include "gtest/gtest.h"
16 #include "pw_rpc/nanopb/client_server_testing.h"
17 #include "pw_rpc_test_protos/test.rpc.pb.h"
18 
19 namespace pw::rpc {
20 namespace {
21 
22 using GeneratedService = ::pw::rpc::test::pw_rpc::nanopb::TestService;
23 
24 class TestService final : public GeneratedService::Service<TestService> {
25  public:
TestUnaryRpc(const pw_rpc_test_TestRequest & request,pw_rpc_test_TestResponse & response)26   Status TestUnaryRpc(const pw_rpc_test_TestRequest& request,
27                       pw_rpc_test_TestResponse& response) {
28     response.value = request.integer + 1;
29     return static_cast<Status::Code>(request.status_code);
30   }
31 
TestAnotherUnaryRpc(const pw_rpc_test_TestRequest &,NanopbUnaryResponder<pw_rpc_test_TestResponse> &)32   void TestAnotherUnaryRpc(const pw_rpc_test_TestRequest&,
33                            NanopbUnaryResponder<pw_rpc_test_TestResponse>&) {}
34 
TestServerStreamRpc(const pw_rpc_test_TestRequest &,ServerWriter<pw_rpc_test_TestStreamResponse> &)35   static void TestServerStreamRpc(
36       const pw_rpc_test_TestRequest&,
37       ServerWriter<pw_rpc_test_TestStreamResponse>&) {}
38 
TestClientStreamRpc(ServerReader<pw_rpc_test_TestRequest,pw_rpc_test_TestStreamResponse> &)39   void TestClientStreamRpc(
40       ServerReader<pw_rpc_test_TestRequest, pw_rpc_test_TestStreamResponse>&) {}
41 
TestBidirectionalStreamRpc(ServerReaderWriter<pw_rpc_test_TestRequest,pw_rpc_test_TestStreamResponse> &)42   void TestBidirectionalStreamRpc(
43       ServerReaderWriter<pw_rpc_test_TestRequest,
44                          pw_rpc_test_TestStreamResponse>&) {}
45 };
46 
TEST(NanopbClientServerTestContext,ReceivesUnaryRpcReponse)47 TEST(NanopbClientServerTestContext, ReceivesUnaryRpcReponse) {
48   NanopbClientServerTestContext<> ctx;
49   TestService service;
50   ctx.server().RegisterService(service);
51 
52   pw_rpc_test_TestResponse response pw_rpc_test_TestResponse_init_default;
53   auto handler = [&response](const pw_rpc_test_TestResponse& server_response,
54                              pw::Status) { response = server_response; };
55 
56   pw_rpc_test_TestRequest request{.integer = 1,
57                                   .status_code = OkStatus().code()};
58   auto call = GeneratedService::TestUnaryRpc(
59       ctx.client(), ctx.channel().id(), request, handler);
60   // Force manual forwarding of packets as context is not threaded
61   ctx.ForwardNewPackets();
62 
63   const auto sent_request =
64       ctx.request<test::pw_rpc::nanopb::TestService::TestUnaryRpc>(0);
65   const auto sent_response =
66       ctx.response<test::pw_rpc::nanopb::TestService::TestUnaryRpc>(0);
67 
68   EXPECT_EQ(response.value, sent_response.value);
69   EXPECT_EQ(response.value, request.integer + 1);
70   EXPECT_EQ(request.integer, sent_request.integer);
71 }
72 
TEST(NanopbClientServerTestContext,ReceivesMultipleReponses)73 TEST(NanopbClientServerTestContext, ReceivesMultipleReponses) {
74   NanopbClientServerTestContext<> ctx;
75   TestService service;
76   ctx.server().RegisterService(service);
77 
78   pw_rpc_test_TestResponse response1 pw_rpc_test_TestResponse_init_default;
79   pw_rpc_test_TestResponse response2 pw_rpc_test_TestResponse_init_default;
80   auto handler1 = [&response1](const pw_rpc_test_TestResponse& server_response,
81                                pw::Status) { response1 = server_response; };
82   auto handler2 = [&response2](const pw_rpc_test_TestResponse& server_response,
83                                pw::Status) { response2 = server_response; };
84 
85   pw_rpc_test_TestRequest request1{.integer = 1,
86                                    .status_code = OkStatus().code()};
87   pw_rpc_test_TestRequest request2{.integer = 2,
88                                    .status_code = OkStatus().code()};
89   const auto call1 = GeneratedService::TestUnaryRpc(
90       ctx.client(), ctx.channel().id(), request1, handler1);
91   // Force manual forwarding of packets as context is not threaded
92   ctx.ForwardNewPackets();
93   const auto call2 = GeneratedService::TestUnaryRpc(
94       ctx.client(), ctx.channel().id(), request2, handler2);
95   // Force manual forwarding of packets as context is not threaded
96   ctx.ForwardNewPackets();
97 
98   const auto sent_request1 =
99       ctx.request<test::pw_rpc::nanopb::TestService::TestUnaryRpc>(0);
100   const auto sent_request2 =
101       ctx.request<test::pw_rpc::nanopb::TestService::TestUnaryRpc>(1);
102   const auto sent_response1 =
103       ctx.response<test::pw_rpc::nanopb::TestService::TestUnaryRpc>(0);
104   const auto sent_response2 =
105       ctx.response<test::pw_rpc::nanopb::TestService::TestUnaryRpc>(1);
106 
107   EXPECT_EQ(response1.value, request1.integer + 1);
108   EXPECT_EQ(response2.value, request2.integer + 1);
109   EXPECT_EQ(response1.value, sent_response1.value);
110   EXPECT_EQ(response2.value, sent_response2.value);
111   EXPECT_EQ(request1.integer, sent_request1.integer);
112   EXPECT_EQ(request2.integer, sent_request2.integer);
113 }
114 
115 }  // namespace
116 }  // namespace pw::rpc
117