Creating a gRPC API with a single proto file¶
This guide will walk you through the process of creating and deploying a gRPC API using the WSO2 APK REST API. We will use the Student Service API as an example in this guide.
Sample Backend for Student Service API¶
We will use a sample API called the Student Service API, which has a single .proto file as its definition. If you wish to deploy an API with multiple .proto files, you can refer to this guide.
We will use the sample Student Service backend for this guide, which can be created using the following command.
kubectl apply -f https://raw.githubusercontent.com/wso2/apk/main/developer/tryout/samples/student-sample-backend.yaml -n <namespace>
You can check the status of the pods by using
kubectl get pods -n <namespace>
Creating and deploying a gRPC API¶
The following steps are a quickstart guide on deploying a GRPC API that has a single .proto file as its API definition.
If you wish to deploy an API with multiple .proto files, you can refer to this guide.
Step 1 - Obtain the proto files for the given API¶
Download and save the following file as Student.proto.
Student API: Student.proto
Step 2 - Generate the APK configuration¶
Execute the following request to generate the APK configuration. Use the values provided in the table below in the body of your request.
Field | Value |
---|---|
definition | The proto file that was downloaded at the beginning of Step 1. |
Student Service API:
curl -k --location 'https://api.am.wso2.com:9095/api/configurator/1.2.0/apis/generate-configuration' \
--header 'Host: api.am.wso2.com' \
--form 'apiType="GRPC"' \
--form 'definition=@"/Users/user/Student.proto"'
curl --location 'https://<host>:9095/api/configurator/1.2.0/apis/generate-configuration' \
--header 'Host: <host>' \
--form 'apiType="GRPC"' \
--form 'definition=@"<path/to/definition.proto>"'
---
name: "6a254687f3229c35dd0189aac7f7fc4b6228e97a"
basePath: "/org.apk"
version: "v1"
type: "GRPC"
defaultVersion: false
subscriptionValidation: false
operations:
- target: "student_service.StudentService"
verb: "GetStudent"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "GetStudentStream"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "SendStudentStream"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "SendAndGetStudentStream"
secured: true
scopes: []
You will get the apk-conf file content as the response, as seen in the above sample response. Save this content into a file with the .apk-conf
file extension. You will need to fill in the name and endpoint configuration fields before deploying the API.
Note
- The .proto file has the
package
string, which is used to get the basepath and version of the API. - The structure of the package string should be
package <basepath>.<version>.<service-name>
- The basepath and version are autogenerated from the contents of the proto file. If you modify it in the API, ensure that you also modify it in the .proto file prior to generating any code from it.
- For example, in the Student Service API,
- Package name:
student_service
- Basepath:
/org.apk
- Version:
v1
- Therefore, the package name in the proto file should
org.apk.v1.student_service
.
- Package name:
Step 3 - Updating the APK-Conf file¶
Let's add the endpoint configurations section to the file as follows.
endpointConfigurations:
production:
endpoint: "http://student-backend:6565"
The URL"http://student-backend:6565" points to the backend we deployed in the previous section.
Let's also rename the API from the autogenerated string to "StudentServiceAPI".
Your apk-conf file will now be as follows.
name: "StudentServiceAPI"
basePath: "/org.apk"
version: "v1"
type: "GRPC"
id: "student-api"
endpointConfigurations:
production:
endpoint: "http://student-backend:6565"
defaultVersion: false
subscriptionValidation: false
operations:
- target: "student_service.StudentService"
verb: "GetStudent"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "GetStudentStream"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "SendStudentStream"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "SendAndGetStudentStream"
secured: true
scopes: []
Step 4 - Deploy the API¶
To deploy the API, we need a valid access token issued by an identity provider (IdP). Follow the Generate Access Token documentation to generate an access token.
After generating the token, you can deploy the gRPC API with the following command.
curl -k --location 'https://api.am.wso2.com:9095/api/deployer/1.2.0/apis/deploy' \
--header 'Host: api.am.wso2.com' \
--header 'Authorization: bearer eyJhbGciOiJSUzI1NiIsICJ0eXAiOiJKV1QiLCAia2lkIjoiZ2F0ZXdheV9jZXJ0aWZpY2F0ZV9hbGlhcyJ9.eyJpc3MiOiJodHRwczovL2lkcC5hbS53c28yLmNvbS90b2tlbiIsICJzdWIiOiI0NWYxYzVjOC1hOTJlLTExZWQtYWZhMS0wMjQyYWMxMjAwMDIiLCAiZXhwIjoxNjg4MTMxNDQ0LCAibmJmIjoxNjg4MTI3ODQ0LCAiaWF0IjoxNjg4MTI3ODQ0LCAianRpIjoiMDFlZTE3NDEtMDA0Ni0xOGE2LWFhMjEtYmQwYTk4ZjYzNzkwIiwgImNsaWVudElkIjoiNDVmMWM1YzgtYTkyZS0xMWVkLWFmYTEtMDI0MmFjMTIwMDAyIiwgInNjb3BlIjoiZGVmYXVsdCJ9.RfKQq2fUZKZFAyjimvsPD3cOzaVWazabmq7b1iKYacqIdNjkvO9CQmu7qdtrVNDmdZ_gHhWLXiGhN4UTSCXv_n1ArDnxTLFBroRS8dxuFBZoD9Mpj10vYFSDDhUfFqjgMqtpr30TpDMfee1wkqB6K757ZSjgCDa0hAbv555GkLdZtRsSgR3xWcxPBsIozqAMFDCWoUCbgTQuA5OiEhhpVco2zv4XLq2sz--VRoBieO12C69KnGRmoLuPtvOayInvrnV96Tbt9fR0fLS2l1nvAdFzVou0SIf9rMZLnURLVQQYE64GR14m-cFRYdUI9vTsFHZBl5w-uCLdzMMofzZaLQ' \
--form 'apkConfiguration=@"path/to/apk-conf-file"' \
--form 'definitionFile=@"path/to/proto-definition"'
curl -k --location 'https://<host>:9095/api/deployer/1.2.0/apis/deploy' \
--header 'Host: <host>' \
--header 'Authorization: bearer <access-token>' \
--form 'apkConfiguration=@"path/to/apk-conf-file.apk-conf"' \
--form 'definitionFile=@"path/to/proto-definition.proto"'
---
name: "StudentServiceAPI"
basePath: "/org.apk"
version: "v1"
type: "GRPC"
id: "student-api"
endpointConfigurations:
production:
endpoint: "http://student-backend:6565"
defaultVersion: false
subscriptionValidation: false
operations:
- target: "student_service.StudentService"
verb: "GetStudent"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "GetStudentStream"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "SendStudentStream"
secured: true
scopes: []
- target: "student_service.StudentService"
verb: "SendAndGetStudentStream"
secured: true
scopes: []
Execute the command below. You will be able to see that the API is successfully deployed.
kubectl get apis -n <namespace>
Invoking a gRPC API¶
You will need a gRPC backend in order to invoke the API and get a correct response. A sample backend for both the Student Service and Order Service APIs have been provided under this section.
Once your gRPC API has been deployed, you can invoke it either via Postman, a custom client, or the grpcurl
command-line tool. You can download the grpcurl tool from here. Code for custom clients can be generated by providing the modified proto file to the Protocol buffer Compiler.
If you are using grpcurl, you can view the various flags needed for sending requests here.
A sample gRPC call is provided below.
Student Service API:
grpcurl -insecure \
-import-path /Users/User/proto-files\
-proto Student.proto \
-d '{"id": 1}' \
-H 'Authorization: Bearer eyJhbGciOiJSUzI1NiIsICJ0eXAiOiJKV1QiLCAia2lkIjoiZ2F0ZXdheV9jZXJ0aWZpY2F0ZV9hbGlhcyJ9.eyJpc3MiOiJodHRwczovL2lkcC5hbS53c28yLmNvbS90b2tlbiIsICJzdWI' \
default.gw.wso2.com:9095 org.apk.v1.student_service.StudentService/GetStudent
grpcurl -insecure \
-import-path <path-to-folder-containing-proto-file> \
-proto <proto-file-name> \
-d '{"argument": value}' \
-H 'Authorization: Bearer <Access-Token>' \
default.gw.wso2.com:9095 <complete-service-and-method-name>