google-cloud-platformgoogle-cloud-functionsgoogle-api-gateway

How do I avoid people being able to access my GCP function when NOT using a Gateway and API?


I have a simple cloud function...

import functions from "@google-cloud/functions-framework";
const protectedExample = (req, res) => {
  res.send('Protected example');
};
functions.http('protectedExample', protectedExample);
export {protectedExample}

Then I protect it using my API...

swagger: '2.0'
info:
  title: hw-api Gateway
  description: Sample API Gateway
  version: 1.0.1
securityDefinitions:
  auth0:
    type: oauth2
    flow: implicit
    x-google-issuer: https://.../
    x-google-jwks_uri: https://.../.well-known/jwks.json
    x-google-audiences: https://.../node
    authorizationUrl: https://.../authorize
    scopes:
      "access:node": Grants read access
schemes:
  - https
produces:
  - application/json
paths:
  /protected:
    get:
      security:
        - auth0: [ "access:node" ]
      summary: Greet a user
      operationId: hello
      x-google-backend:
        address: https://us-central1-....cloudfunctions.net/protectedExample
      responses:
        '200':
          description: A successful response
          schema:
            type: string

This works great from an API perspective, however, when I run the following...

gcloud functions describe protectedExample

then try to call the endpoint described by

httpsTrigger:
  securityLevel: SECURE_ALWAYS
  url: https://us-central1-....cloudfunctions.net/protectedExample

I can still access the function. How do I prevent external people from accessing it except through the Gateway?

I tried --ingress-settings=internal-and-gclb but then I get

<body text=#000000 bgcolor=#ffffff>
    <h1>Error: Forbidden</h1>
    <h2>Access is forbidden.</h2>
    <h2></h2>
</body>

When I try to call it through the Gateway.


Solution

  • In order to make the Cloud Function endpoint private but still accessible to the API Gateway, you have to give the API Gateway service account the roles/cloudfunctions.invoker role, and that the gateway's service account has the cloudfunctions.functions.invoke permission.

    Make sure to also remove the allUsers role from the permissions list for the Cloud Function or deploy your Cloud Functions securely by setting the param to --no-allow-unauthenticated.

    enter image description here