Configurar Cloud Endpoint y Autenticación API KEY GCP
Cómo exponer un microservicio desplegado en GKE a través de Cloud Endpoint incorporando una API KEY.
Descripción
Cloud Endpoint es un sistema de administración de API que proporciona funciones para ayuda crear, mantener y proteger sus APIS.
Para identificar un servicio que envía solicitudes a tu API, usas una API key generada en GCP. El servicio de llamadas emplea la Api key y enviarlo en la solicitud a tu API.
Pre-requisitos
- Definir Contrato Openapi.yaml en version 2.0
- Habilitar APIS
- Crear recursos GCP (IP EXTERNA, Cluster GKE y Service Accounts)
- Generar archivos k8s
Requisitos Técnicos
Google Cloud Platform
- Una cuenta personal de Google Cloud
- SDK de Google Cloud
Contrato openapi-jwt.yaml
Para integrar CloudEndpoint en el contrato se debe agregar la siguiente sintaxis.
host: "DOMAIN_OPENAPI"
x-google-endpoints:
- name: "DOMAIN_OPENAPI"
target: "IP_RESERVADA"
Para agregar la autenticación con Api Key se debe agregar la siguiente sintaxis.
securityDefinitions:
apitoken:
type: "apiKey"
name: "key"
in: "query"
security:
- apitoken: []
DOMAIN_OPENAPI : Dominio al cual sera asociado el contrato, se puede ocupar un dominio propio o uno generado por google.
IP_RESERVADA : En la sección target del contrato solo aplica si se utiliza el dominio generado por google.
swagger: "2.0"
info:
description: "A simple Google Cloud Endpoints API example."
title: "Endpoints Example Cloudendpoint"
version: "1.0.0"
host: "DOMAIN_OPENAPI"
x-google-endpoints:
- name: "DOMAIN_OPENAPI"
target: "IP_RESERVADA"
consumes:
- "application/json"
produces:
- "application/json"
schemes:
- "https"
- "http"
securityDefinitions:
# This section configures basic authentication with an API key.
api_key:
type: "apiKey"
name: "key"
in: "query"
security:
- api_key: []
paths:
"/echo":
post:
description: "Echo back a given message."
operationId: "echo"
produces:
- "application/json"
responses:
200:
description: "Echo"
schema:
$ref: "#/definitions/echoMessage"
parameters:
- description: "Message to echo"
in: body
name: message
required: true
schema:
$ref: "#/definitions/echoMessage"
"/auth/info/googlejwt":
get:
description: "Returns the requests' authentication information."
operationId: "auth_info_google_jwt"
produces:
- "application/json"
responses:
200:
description: "Authentication info."
schema:
$ref: "#/definitions/authInfoResponse"
definitions:
echoMessage:
type: "object"
properties:
message:
type: "string"
authInfoResponse:
properties:
id:
type: "string"
email:
type: "string"
Al rellenar los campos mencionados es necesario desplegar el contrato en GCP.
Habilitar APIS en GCP
servicemanagement.googleapis.com
servicecontrol.googleapis.com
endpoints.googleapis.com
Generar Recursos GCP
Crear Ip externa ip-cloudendpoint de tipo Global
VPC NETWORK >> External IP Adressess >> Reserve static address
Crear Cluster GKE
kubernetes Engine >> Cluster >> Create Cluster
Service Accounts
IAM & ADMIN >> Service Accounts >> Create Service Accounts
Para este ejemplo se creará una cuenta de servicio
Se debe crear una cuenta de servicio para realizar la integración con el endpoint desplegado, para que tenga acceso al contrato.
El permiso que debe tener es el siguiente: Service Controller
Desplegar contrato openapi en cloud endpoint
gcloud config set project [PROJECT ID]
gcloud endpoints services deploy openapi-apikey.yaml
Contrato Desplegado
Paths Contrato Desplegado
Generar API KEY
Se generan credenciales de tipo API KEY
Después de crear la cuenta de servicio se procede a editar la configuración para asignarla a nuestro contrato desplegado en Cloudendpoint.
Habilitar API Desplegada
Generar Archivos K8S
Deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: esp-echo
spec:
replicas: 1
strategy:
type: RollingUpdate
rollingUpdate:
maxSurge: 50% # how many pods we can add at a time
maxUnavailable: 50%
selector:
matchLabels:
app: esp-echo
template:
metadata:
labels:
app: esp-echo
tier: backend
spec:
volumes:
- name: credentials
secret:
secretName: service-account-creds
containers:
- name: esp-echo
image: gcr.io/endpoints-release/echo:latest
- name: esp
image: gcr.io/endpoints-release/endpoints-runtime:1
args: [
"--http_port=8080",
"--backend=127.0.0.1:8081",
"--service=echo-api.endpoints.project-id.cloud.goog",
"--rollout_strategy=managed",
"-z=healthz",
"--service_account_key=/secrets/cloud-endpoints/echo-cloudendpoint.json"]
readinessProbe:
httpGet:
path: /healthz
port: 8080
ports:
- containerPort: 8080
volumeMounts:
- name: credentials
mountPath: /secrets/cloud-endpoints
readOnly: true
En el despliegue se encontraran 2 componentes, el cliente de cloudendpoint y el componente con las características desplegadas en el contrato openapi.
La propiedad service en el deployment debe ser reemplazada por el valor desplegado en su contrato.
Ejemplo:
"--http_port=8080",
"--backend=127.0.0.1:8081",
"--service=echo-api.endpoints.project-id.cloud.goog
Service.yaml
apiVersion: v1
kind: Service
metadata:
name: esp-echo-service
annotations:
spec:
ports:
- name: http
port: 80
protocol: TCP
targetPort: 8080
selector:
app: esp-echo
tier: backend
# LOCAL/INTERNAL: NodePort, GCP/EXTERNAL: LoadBalancer, ClusterIP
type: NodePort
Ingress.yaml
apiVersion: extensions/v1beta1
kind: Ingress
metadata:
name: "ingress"
annotations:
kubernetes.io/ingress.allow-http: "true"
kubernetes.io/ingress.global-static-ip-name: "ip-cloudendpoint"
spec:
rules:
- http:
paths:
- backend:
serviceName: "esp-echo-service"
servicePort: 80
path: "/*"
Se genera el namespace cloud-endpoint y el secreto con el contenido de la cuenta de servicio para acceder al contrato desplegado en cloudendpoint.
kubectl create namespace cloud-endpoint
kubectl -n cloud-endpoint create secret generic service-account-creds --from-file=echo-cloudendpoint.json
Ya teniendo los archivos se realiza el despliegue de los componentes en el cluster GKE:
kubectl -n cloud-endpoint apply -f Deployment.yaml
kubectl -n cloud-endpoint apply -f Service.yaml
kubectl -n cloud-endpoint apply -f Ingress.yaml
Verificar servicios desplegados
Cuando se realizan los despliegues se reflejará en la interfaz de GCP:
Verificar logs servicios desplegados
Componente esp
Componente esp echo
Validar endpoint que expone el servicio
Endpoint 1
http://IP-EXTERNA/echo
Endpoint 2
http://IP-EXTERNA/auth/info/googlejwt
Al intentar consultar los diferentes endpoint, nos responde el servicio que no estamos autorizados.
Agregar API KEY
Al tener ya disponible la Api key y asociada al contrato, se procede a integrar la api key en la url.
Endpoint 1
http://IP-EXTERNA/echo?api_key=[API_KEY]
Endpoint 2
http://IP-EXTERNA/auth/info/googlejwt?api_key=[API_KEY]
Hemos aprendido a realizar la integración de CloudEndpoint más la autenticación a través de un método de API KEY.
Código Fuente: https://github.com/mauricio-echeverria/Cloud-Endpoint-y-Autenticacion-apikey