Google cloud run endpoint (extensible) service proxy api gateway firebase token - google-cloud-run

Super basic (video) but the title is nearly my comment to Top 3 ways to run your containers on Google Cloud
User Authentication (content) in 2020 about api gateway from endpoints
Maybe a focal point for an answer could be the app engine role for api gateway in 2022. swagger.yaml (#comment)
# openapi2-run.yaml
swagger: "2.0"
info: # >1 API/service; spec x-google-api-name OpenAPI document extension.
title: backbank # mastercard-backbank # API_ID optional-string
#https://cloud.google.com/api-gateway/docs/get-started-cloud-run
description: node cloud run api mastercard p.12 customer keys # Sample API on API Gateway with a Cloud Run backend
version: 0.0.1
security:
- firebase: []
securityDefinitions: #https://cloud.google.com/api-gateway/docs/authenticating-users-firebase
firebase: #bearer https://cloud.google.com/endpoints/docs/openapi/openapi-extensions
authorizationUrl: "" # empty for firebase frm bearer Authorization?
flow: "implicit"
type: "oauth2"
x-google-issuer: "https://securetoken.google.com/vaumoney"
x-google-jwks_uri: "https://www.googleapis.com/service_accounts/v1/metadata/x509/securetoken#system.gserviceaccount.com"
x-google-audiences: "vaumoney"
host: "vault-co.in"
basePath: "/" # https://stackoverflow.com/questions/71258737/making-a-cloud-firestore-rest-api-call-through-cloud-endpoints
#When the basePath property is configured in the service configuration as well,
#this header applies only to URL paths that are prefixed by the basePath property value.
#URLs that aren't part of the basePath aren't passed through regardless of the x-google-allow property.
schemes:
- https
consumes:
- application/json
produces:
- application/json
#x-google-allow:
#all
#jwt_audience: https://www.googleapis.com/service_accounts/v1/metadata/x509/securetoken#system.gserviceaccount.com/vaumoney
#x-google-endpoints:
#- name: "vault-co.in"
#allowCors: True
paths:
/:
get:
summary: Yes Hello cloud run (api gateway, load balance) service
operationId: get
x-google-backend:
address: https://vault-co.in:8080 # APP_URL endpoint(s)
protocol: h2
responses:
200:
description: This is a (Non-Graphical) Application Programming Interface
#schema:
#type: string
#default: '''ello guv'''
default:
description: Something is wrong
#schema:
#type: string
#default: '''some not 200'''
options:
summary: Enable CORS with headers
operationId: options
x-google-backend:
address: https://vault-co.in:8080 # APP_URL endpoint(s)
jwt_audience: https://vault-co.in
protocol: h2
description: |
Origin, Methods and Headers allowing headers potentially requested
tags:
- CORS
responses:
200:
description: OPTIONS responding headers
headers:
Access-Control-Allow-Origin:
type: string
#$ref: '#/definitions/String'
default: "'i7l8qe.csb.app'"
Access-Control-Allow-Methods:
type: string
default: "'GET,POST'"
Access-Control-Allow-Headers:
type: string
default: "'Content-Type,X-Amz-Date,Authorization,X-Api-Key'"
403:
description: OPTIONS responding headers
headers:
Access-Control-Allow-Origin:
type: string
default: "'i7l8qe.csb.app'" # '''vau.money'''
Access-Control-Allow-Methods:
type: string
default: "'GET,POST'"
Access-Control-Allow-Headers:
type: string
default: "'Content-Type,X-Amz-Date,Authorization,X-Api-Key'"
#content: {}
default:
description: Something is wrong
#type: string
#default: '''some not 200'''
post:
summary: Respond properly indeed
operationId: posted
x-google-backend:
address: https://vault-co.in:8080 # APP_URL endpoint(s)
jwt_audience: https://vault-co.in
protocol: h2
description: |
Successful api fetch
parameters:
- name: pageOffset
in: body
required: true
schema:
type: object
properties:
pageOffset:
description: pageOffset is required, try 0
type: string
pageLength:
description: pageLength is required, try 10
type: string
postalCode:
description: postalCode is required, try 11101
type: string
responses: # https://swagger.io/docs/specification/describing-responses/
default: #200
description: post result
#content:v3 application/json:
schema:
type: object
description: response ok
required:
- results
properties:
results:
#collectionFormat: csv
type: array
default: []
items:
type: string
meta:
type: object
properties:
title:
type: string
description:
type: string
I repeat attempts in seriatim:
gcloud api-gateway gateways delete backbank --location=us-central1
gcloud api-gateway api-configs delete backbank --api=backbank
gcloud api-gateway api-configs create backbank --api=backbank --openapi-spec=swagger.yaml --project=vaumoney --backend-auth-service-account=vaumoney#appspot.gserviceaccount.com
(a) gcloud endpoints services deploy swagger.yaml --project=vaumoney
(b) gcloud services enable vault-co.in (Principal-role permission name: "firebase-adminsdk")
gcloud run deploy backbank \
--image="gcr.io/vaumoney/endpoints-runtime-serverless:2.38.0-vault-co.in-2022-09-08r2" \
--set-env-vars ESPv2_ARGS=^++^--cors_preset=cors_with_regex++--cors_allow_origin_regex=^https:[/][/]i7l8qe.csb.app$++--cors_allow_methods=GET,POST,OPTIONS++--cors_allow_headers=Origin,Content-Type,Authorization,Referrer-Policy++--cors_allow_credentials \
--platform managed --project vaumoney
Of course, I incessantly get this:
The request was not authenticated. Either allow unauthenticated invocations or set the proper Authorization header. Read more at https://cloud.google.com/run/docs/securing/authenticating Additional troubleshooting documentation can be found at: https://cloud.google.com/run/docs/troubleshooting#unauthorized-client
But OPTIONS might be the problem (albeit "" on GET):
"This would be really useful for us, we're using cloud run for all our microservices and want to call these from a SPA via API Gateway." "We're back to Cloud Endpoints and ESPv2 for the time being, but we 100% see the benefits of the managed API Gateway, should CORS support be available for gRPC requests."
What am I to do?

Related

Using OpenAPI3 (swagger) in multiple microservices and generating a single OpenAPI definition

I have a collection of microservices, each with their own complete OpenAPI spec and a root level path
Microservice Definition
openapi: 3.0.0
info:
description: Microservice API
version: '0.0.1'
paths:
/:
get:
tags:
- Root
summary: Root Path
operationId: Root
responses:
'200':
description: Request was successful
deprecated: false
/healthcheck/ping:
get:
tags:
- Healthcheck
summary: Test the reachability of the microservice.
operationId: Ping
responses:
'200':
description: Request was successful
deprecated: false
And a root OpenAPI definition
openapi: "3.0.0"
info:
version: 1.0.0
title: API
servers:
- url: http://api.something.com/v1
paths:
/microservice1:
$ref: "https://storagebucket.someservice.com/service-definitions/microservice-swagger.yaml"
It's been my assumption that it's possible to arrange things this way but I'm getting a whole host of errors in the swagger editor for validity.
Using microservice-swagger.yaml#/paths/~1 gets me somewhere but I would expect that all the paths in the service yaml to simply be appended to the path in the main definition. Does anyone know how to achieve this?
(The reason behind it being to apply this root swagger to an API Gateway whilst maintaining each service as a self contained unit)
I would for example expect the resulting swagger to offer this as a path
/microservice1/healthcheck/ping

Does OpenAPI 3.0 allow to reference server variables?

Say my OpenAPI definition has two servers. Both share the same variables. Thus I want to reference these variables to prevent duplicate code.
Actually I split my OpenAPI into files and combine it with swagger-cli bundle.
This is what it creates:
openapi: 3.0.2
info:
title: My API
description: 'some description'
version: 1.0.0
servers:
- url: 'https://stage-api.domain.com/foo/{v1}/{v2}/{v3}'
description: Staging API server for QA
variables:
v1:
description: 'variable 1'
default: 'something'
enum:
- 'foo1'
- 'foo2'
v2:
description: 'variable 2'
default: 'something'
enum:
- 'foo1'
- 'foo2'
v3:
description: 'variable 3'
default: 'something'
enum:
- 'foo1'
- 'foo2'
- url: 'https://api.domain.com/foo/{v1}/{v2}/{v3}'
description: PRODUCTION API server
variables:
region:
$ref: '#/servers/0/variables/v1'
brand:
$ref: '#/servers/0/variables/v2'
locale:
$ref: '#/servers/0/variables/v3'
paths: {}
Trying to validate this in Swagger Editor I get the following error:
Structural error at servers.1.variables.v1 should NOT have
additional properties additionalProperty: $ref Jump to line xx
Structural error at servers.1.variables.v1 should have required
property 'default' missingProperty: default Jump to line xx
Is it possible to reference the server variables or reuse them in another way?
Of course I could run swagger-cli bundle -r but I would want to prevent using that.
No, this is not supported. You can request changes to the OpenAPI Specification at
https://github.com/OAI/OpenAPI-Specification/issues
In your example, the server paths are almost the same except for the subdomain, so you can use a single server definition and make the subdomain a variable:
servers:
- url: 'https://{env}.domain.com/foo/{v1}/{v2}/{v3}'
variables:
env:
description: Environment - staging or production
default: stage-api
enum:
- stage-api
- api
# other variables
# ...

Creating a Swagger documentation for an already hosted API

I have an API that is far from standard, and I want to create Swagger docs for it. Since it's so far from standard I won't be able to generate anything, instead I'll have to do it manually.
I followed the instructions and created the "hello-world" project, I have been trying to edit this to call my own API instead. A simple GET endpoint returning a JSON list of objects.
I am assuming I can ignore everything that has to do with controllers and mocks etc since this API already returns json data if I call it through postman. I.e its a working API and all I want Swagger for is documentation.
Unfortunately I only get an "ERROR Server not found or an error occurred" when trying it out, but if I browse to the URL it's using it works fine. So I assume there is something I am missing that Swagger needs. Keep in mind I have not change any configs or anything else in this hello-world project, only the editor.
Here is my Yaml:
swagger: "2.0"
info:
version: "0.0.1"
title: Hello World App
# during dev, should point to your local machine
host: localhost
# basePath prefixes all resource paths
basePath: /appname/api/v1/object
#
schemes:
# tip: remove http to make production-grade
- https
# format of bodies a client can send (Content-Type)
consumes:
- application/json
# format of the responses to the client (Accepts)
produces:
- application/json
paths:
/campaign/:
get:
description: Get all campaigns
# used as the method name of the controller
operationId: hello
responses:
"200":
description: Success
schema:
# a pointer to a definition
$ref: "#/definitions/HelloWorldResponse"
# responses may fall through to errors
default:
description: Error
schema:
$ref: "#/definitions/ErrorResponse"
# complex objects have schema definitions
definitions:
HelloWorldResponse:
required:
- message
properties:
message:
type: string
ErrorResponse:
required:
- message
properties:
message:
type: string
Here is the request it tries to send, which looks correct:
GET https://localhost/appname/api/v1/object/campaign/ HTTP/1.1
Host: localhost
Accept: application/json
Accept-Encoding: gzip,deflate,sdch
Accept-Language: en-US,en;q=0.8,fa;q=0.6,sv;q=0.4
Cache-Control: no-cache
Connection: keep-alive
Origin: http://127.0.0.1:62430
Referer: http://127.0.0.1:62430/
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:67.0) Gecko/20100101 Firefox/67.0

Swagger UI Not adding Header to Requests

I am using Swagger 2.0 and Swagger UI 3.0.3.
In my api_definition.yaml I have the following before my paths:
swagger: '2.0'
################################################################################
# Host, Base Path, Schemes and Content Types #
################################################################################
# Metadata
info:
version: v1
title: Microservice
description: Microservice API!
host: sandbox
basePath: '/apps/fiji/v1'
schemes:
- http
securityDefinitions:
apikey:
type: apiKey
name: X-Access-Token
in: header
security:
- apikey: []
produces:
- application/json
consumes:
- application/json
This adds an Authorize button the the Swagger UI where the user can paste in their API key. I would like this API key to be sent in the request header of every request. This does not happen though and I'm not sure why. Am I missing something?
EDIT:
The request seems to send and I get back 401 Unauthorized.
Chrome Dev Tools shows the following Request Headers:
GET /apps/fiji/v1/getCPICountries HTTP/1.1
Host: sandbox
Connection: keep-alive
accept: application/json
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/57.0.2987.133 Safari/537.36
content-type: application/json
Referer: http://sandbox/apps/fiji/vendor/swagger-ui/dist/index.html?url=http://sandbox/apps/fiji/swagger/api_definition.yaml
Accept-Encoding: gzip, deflate, sdch
Accept-Language: en-US,en;q=0.8
I have the paths set up as:
# API Paths
paths:
# getCPICountries endpoint
/getCPICountries:
# HTTP operations
get:
# Describe this verb here. Note: you can use markdown
description: |
Returns a list of countries and country codes
produces:
- application/json
security:
- auth:
- role_admin
# Expected responses for this operation:
responses:
# Response code
200:
description: Successful response
# A schema describing your response object.
# Use JSON Schema format
schema:
properties:
data:
type: array
items:
$ref: '#/definitions/CPIResponse'
And definitions as follows:
definitions:
CPIResponse:
type: object
UserObject:
type: object
properties:
email:
type: string
id:
type: number
orgId:
type: number
firstName:
type: string
lastName:
type: string
The problem was that I override security in my paths. I need to remove the following:
security:
- auth:
- role_admin

Swagger fake API with swagger-node

README.md on https://github.com/swagger-api/swagger-node says 'Kick the tires. Your API is live while you edit (Did we mention no code?)' -> 'Quit faking' on the next step.
So I was under impression that Swagger will generate a fake API for me.
However, if I use such swagger.yaml:
swagger: '2.0'
info:
title: test
description: test
version: "1.0.0"
host: localhost:10010
schemes:
- https
basePath: /api
produces:
- application/json
- text/event-stream
consumes:
- application/json
paths:
/pages:
get:
summary: test
description: test
responses:
200:
description: pages
schema:
type: array
items:
$ref: '#/definitions/Page'
default:
description: Unexpected error
schema:
$ref: '#/definitions/Error'
(where definitions are also given in config)
I receive 404 in both curl http://localhost:10010/api/pages and swagger editor (swagger project edit). I know about x-swagger-router-controller thing but I expected it to work out of the box. Am I doing something wrong?
I should've read the docs more carefully. Swagger gives us the mock mode (swagger project start -m)

Resources