Parse an RPC method: rpc Name (stream? Req) returns (stream? Res) { option ... };
(self)
| 881 | ) |
| 882 | |
| 883 | def parse_rpc_method(self) -> RpcMethod: |
| 884 | """Parse an RPC method: rpc Name (stream? Req) returns (stream? Res) { option ... };""" |
| 885 | start = self.current() |
| 886 | self.consume(TokenType.RPC) |
| 887 | name = self.consume(TokenType.IDENT, "Expected method name").value |
| 888 | |
| 889 | # Parse request type |
| 890 | self.consume(TokenType.LPAREN, "Expected '(' before request type") |
| 891 | client_streaming = False |
| 892 | if self.check(TokenType.STREAM): |
| 893 | self.advance() |
| 894 | client_streaming = True |
| 895 | |
| 896 | request_type = self.parse_named_type_reference("Expected request message type") |
| 897 | self.consume(TokenType.RPAREN, "Expected ')' after request type") |
| 898 | |
| 899 | # Parse return type |
| 900 | self.consume(TokenType.RETURNS, "Expected 'returns' keyword") |
| 901 | self.consume(TokenType.LPAREN, "Expected '(' before response type") |
| 902 | server_streaming = False |
| 903 | if self.check(TokenType.STREAM): |
| 904 | self.advance() |
| 905 | server_streaming = True |
| 906 | |
| 907 | response_type = self.parse_named_type_reference( |
| 908 | "Expected response message type" |
| 909 | ) |
| 910 | self.consume(TokenType.RPAREN, "Expected ')' after response type") |
| 911 | |
| 912 | # Parse optional method options block |
| 913 | options = {} |
| 914 | if self.check(TokenType.LBRACE): |
| 915 | self.consume(TokenType.LBRACE) |
| 916 | while not self.check(TokenType.RBRACE): |
| 917 | if self.check(TokenType.OPTION): |
| 918 | name_token = self.current() |
| 919 | opt_name, opt_value = self.parse_file_option() |
| 920 | options[opt_name] = opt_value |
| 921 | if opt_name not in KNOWN_METHOD_OPTIONS: |
| 922 | warnings.warn( |
| 923 | f"Line {name_token.line}: ignoring unknown method option '{opt_name}'", |
| 924 | stacklevel=2, |
| 925 | ) |
| 926 | elif self.check(TokenType.SEMI): |
| 927 | # Allow empty ; inside block |
| 928 | self.advance() |
| 929 | else: |
| 930 | raise self.error("Expected 'option' inside method block") |
| 931 | self.consume(TokenType.RBRACE, "Expected '}' after method options") |
| 932 | else: |
| 933 | self.consume(TokenType.SEMI, "Expected ';' after method definition") |
| 934 | |
| 935 | return RpcMethod( |
| 936 | name=name, |
| 937 | request_type=request_type, |
| 938 | response_type=response_type, |
| 939 | client_streaming=client_streaming, |
| 940 | server_streaming=server_streaming, |
no test coverage detected