This page applies to Apigee and Apigee hybrid.
View Apigee Edge documentation.
This example demonstrates how to use Apigee Adapter for Envoy with an Apigee hybrid deployment.
Prerequisites
Before you begin: |
---|
|
|
|
Overview
This example explains how to use Apigee Adapter for Envoy with Apigee hybrid. In this example, you will deploy a simple HTTP service in the same Kubernetes cluster where Apigee hybrid is deployed. Then, you will configure the Apigee Adapter for Envoy to manage API calls to this service with Apigee.
The following figure shows the basic architecture for the Apigee hybrid integration:
An Envoy proxy is deployed with the target HTTP service as an Istio sidecar in the Istio service mesh. The sidecar handles API traffic to and from the target service, and communicates with the Remote Service. The Remote Service also communicates with the hybrid management plane to retrieve API product and proxy information.
Check your gcloud configuration
- Check that your
gcloud
configuration is set to the GCP project associated with your hybrid organization.To list the current settings:
gcloud config list
If necessary, set the correct GCP project ID with this command:
gcloud config set project project-id
- You must be authenticated with Google Cloud SDK (gcloud) for your GCP project:
gcloud auth login
Deploy a test service to the cluster
In this step, you will deploy a simple HTTP request/response test service to the same cluster where Apigee hybrid is deployed.
- Go to the Remote Service directory:
cd $REMOTE_SERVICE_HOME
- Enable Istio injection in the
default
namespace of the cluster. In a later step, you will deploy an Envoy sidecar to this same cluster. Enabling Istio injection makes the sidecar deployment possible. This example uses thedefault
namespace, and all subsequent instructions assume this is the case.kubectl label namespace default istio-injection=enabled
- Apply the simple
httpbin
service to the cluster in the default namespace:kubectl apply -f samples/istio/httpbin.yaml
- Now, test the service. Start a
curl
service running in the cluster and open a terminal:kubectl run -it curl --image=curlimages/curl --restart=Never -- sh
- Test the service by calling it from inside the cluster:
curl -i httpbin.default.svc.cluster.local/headers
On success, you will see a 200 status, and the service returns a list of headers. For example:
HTTP/1.1 200 OK server: envoy date: Tue, 12 May 2020 17:09:01 GMT content-type: application/json content-length: 328 access-control-allow-origin: * access-control-allow-credentials: true x-envoy-upstream-service-time: 7 { "headers": { "Accept": "*/*", "Content-Length": "0", "Host": "httpbin.default.svc.cluster.local", "User-Agent": "curl/7.70.0-DEV", "X-B3-Parentspanid": "69f88bc3e322e157", "X-B3-Sampled": "0", "X-B3-Spanid": "8dd725f30e393d8b", "X-B3-Traceid": "38093cd817ad30a569f88bc3e322e157" } }
Provision Apigee hybrid
In this step, you will use the Remote Service CLI to provision hybrid with the
remote-service
API proxy. The provisioning command also sets up a certificate on
Apigee, and generates credentials the remote service will use to securely connect back to Apigee.
- Go to the
$CLI_HOME
directory:cd $CLI_HOME
- If you are not an owner of the GCP project associated with the Apigee hybrid organization,
be sure that your GCP user account includes the
Apigee Organization Admin
role. See Granting, changing, and revoking access to resources. - Execute this command to get an access token:
TOKEN=$(gcloud auth print-access-token);echo $TOKEN
- Create the following environment variables. These variables will be used as
parameters to the provisioning script:
export ORG=organization_name
export ENV=environment_name
export RUNTIME=host_alias_url
export NAMESPACE=hybrid_runtime_namespace
Where:
Variable Description organization_name The name of the Apigee organization for you Apigee hybrid installation. environment_name The name of an environment in your Apigee hybrid organization. host_alias_url A URL that includes the hostAlias
for a virtual host defined in your hybrid configuration. The URL must start withhttps://
. For example:https://apitest.apigee-hybrid-docs.net
hybrid_runtime_namepace The namespace in which the Hybrid runtime components are deployed. Note: The default namespace for a hybrid deployment is apigee
. - Execute the following command to provision the remote service proxy to Apigee hybrid:
If you are not upgrading, use this command to provision Apigee:
./apigee-remote-service-cli provision --organization $ORG --environment $ENV \ --runtime $RUNTIME --namespace $NAMESPACE --token $TOKEN > config.yaml
If you are upgrading, use this command with the
--force-proxy-install
flag to provision Apigee:./apigee-remote-service-cli provision --force-proxy-install --organization $ORG --environment $ENV \ --runtime $RUNTIME --namespace $NAMESPACE --token $TOKEN > config.yaml
- Check the contents of the
config.yaml
file. It should look something like this:# Configuration for apigee-remote-service-envoy # generated by apigee-remote-service-cli provision on 2020-07-06 18:03:58 apiVersion: v1 kind: ConfigMap metadata: name: apigee-remote-service-envoy namespace: apigee data: config.yaml: | tenant: remote_service_api: https://apitest.apigee-hybrid-docs.net/remote-service org_name: hybrid-docs env_name: envoy allow_unverified_ssl_cert: true analytics: collection_interval: 10s fluentd_endpoint: apigee-udca-hybrid-docs-envoy.apigee:20001 tls: ca_file: /opt/apigee/tls/ca.crt key_file: /opt/apigee/tls/tls.key cert_file: /opt/apigee/tls/tls.crt --- apiVersion: v1 kind: Secret metadata: name: hybrid-docs-envoy-policy-secret namespace: apigee type: Opaque data: remote-service.crt: eyJrZXlzIjpbeyJrdHkiOiJSU0EiLCJhbGci... remote-service.key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURS... remote-service.properties: a2lkPTIwMjAtMDctMDZ...
- Apply the service configuration (the file output by the provisioning command) to the cluster:
kubectl apply -f $CLI_HOME/config.yaml
- Verify your proxy and certificate. The following should return valid JSON:
curl --http1.1 -i $RUNTIME/remote-service/certs
The output looks something like this:
{ "keys": [ { "alg": "RS256", "e": "AQAB", "kid": "2020-05-11T11:32:26-06:00", "kty": "RSA", "n": "0v-nbTQyAmtVZ-wZRP0ZPIbrVaX91YO9JZ9xCQPb4mOdOSS7yKfTDJGg0KM130sGVYBvR76alN8 fhrrSDEG5VXG8YYMqPXarwRC7MRJWocCQ_ECYrjDD0_Q018M2HyXZYSd8fhAogi9mVUYsEmCKqJH53Dh1 jqsHOQzBLKsX0iDO9hEZNFtjbX0UCbSxsUlmBCub7Uj2S-PahA6DEQOMhQjZM7bBMtkTMpFmaJ_RZTmow BHP57qMna17R8wHD4kUsO2u_-3HHs5PSj1NrEYoVU2dwLQw0GlkB__ZWeFgXTqot81vb-PmoM9YxwoZrm TcHdljugWy_s7xROPzTod0uw" } ] }
Run the Remote Service for Envoy
In this step, you start the Remote Service for Envoy client in the service mesh
where Apigee hybrid is installed. This service provides the endpoints to the Istio sidecars that
are installed on target services. In a later step, you will install a sidecar
with the httpbin
service.
- Open
$REMOTE_SERVICE_HOME/samples/istio/hybrid-apigee-remote-service-envoy.yaml
in an editor. - You may need to adjust the configuration if you are not using the latest version of
the Remote Service. If you are using the
latest version,
go to the next step. If you are not
using the latest version, set the
image:
element to reference your version. For example, if you are using versionv1.0.0-beta.4
, change theimage
tag to:image: "gcr.io/apigee-api-management-istio/apigee-remote-service-envoy:v1.0.0-beta.4"
- Set the
tls-volume.secretName
element to your organization and environment:... volumes: - name: tls-volume secret: defaultMode: 420 secretName: apigee-runtime-$ORG-$ENV-tls - name: policy-secret secret: defaultMode: 420 secretName: $ORG-$ENV-policy-secret
For example:
... volumes: - name: tls-volume secret: defaultMode: 420 secretName: apigee-runtime-myorg-myenv-tls - name: policy-secret secret: defaultMode: 420 secretName: myorg-myenv-policy-secret ...
- Apply the Apigee Remote Service to the service mesh:
kubectl apply -f $REMOTE_SERVICE_HOME/samples/istio/hybrid-apigee-remote-service-envoy.yaml
- Apply the
EnvoyFilter
to the Istio sidecars in the default namespace. TheEnvoyFilter
enables thehttpbin
sidecar to communicate with the Apigee Remote Service.:kubectl apply -f $REMOTE_SERVICE_HOME/samples/istio/envoyfilter-sidecar.yaml
Test the installation
- Now, go back to the curl shell you opened in the step
Deploy a test service to the cluster and call the
httpbin
service:curl -i httpbin.default.svc.cluster.local/headers
The service is now being managed by Apigee, and because you did not supply an API key, returns the following error.
curl -i httpbin.default.svc.cluster.local/headers HTTP/1.1 403 Forbidden date: Tue, 12 May 2020 17:51:36 GMT server: envoy content-length: 0 x-envoy-upstream-service-time: 11
- Configure an API product and get an API key as explained in How to obtain an API key.
- Make an API call using the key:
export APIKEY=YOUR_API_KEY
curl -i httpbin.default.svc.cluster.local/headers -H "x-api-key: $APIKEY"
The call should succeed with a 200 status and returning a list of headers in the response. For example:
curl -i httpbin.default.svc.cluster.local/headers -H "x-api-key: kyOTalNNLMPfOSy6rnVeclmVSL6pA2zS" HTTP/1.1 200 OK server: envoy date: Tue, 12 May 2020 17:55:34 GMT content-type: application/json content-length: 828 access-control-allow-origin: * access-control-allow-credentials: true x-envoy-upstream-service-time: 301 { "headers": { "Accept": "*/*", "Content-Length": "0", "Host": "httpbin.default.svc.cluster.local", "User-Agent": "curl/7.70.0-DEV", "X-Api-Key": "kyOTalNNLMPfOSy6rnVeclmVSL6pA2zS", "X-Apigee-Accesstoken": "", "X-Apigee-Api": "httpbin.default.svc.cluster.local", "X-Apigee-Apiproducts": "httpbin", "X-Apigee-Application": "httpbin", "X-Apigee-Authorized": "true", "X-Apigee-Clientid": "kyOTalNNLMPfOSy6rnVeclmVSL6pA2zS", "X-Apigee-Developeremail": "jdoe@example.com", "X-Apigee-Environment": "envoy", "X-Apigee-Organization": "acme-org", "X-Apigee-Scope": "", "X-B3-Parentspanid": "1476f9a2329bbdfa", "X-B3-Sampled": "0", "X-B3-Spanid": "1ad5c19bfb4bc96f", "X-B3-Traceid": "6f329a34e8ca07811476f9a2329bbdfa" } }
Next steps
API traffic to the httpbin
service is now managed by Apigee. Here are
some features you can explore and try:
- If you configured your API product as explained in
How to obtain an API key,
the quota limit was set to 5 requests per minute. Try calling the
httpbin
service a few more times to trigger the quota. When you exceed the quota, you'll see this error:HTTP/1.1 429 Too Many Requests
- Access Apigee Analytics in the Edge UI. Go to Analyze > API Metrics > API Proxy Performance.
- Generate and use JWT tokens to authenticate API calls.
- Use the CLI to manage, create tokens, and control bindings. For CLI details, see the Reference.