Защитить Google Cloud-функции HTTP-триггер с помощью auth

Сегодня я просматриваю Google Cloud Functions следующим образом: https://cloud.google.com/functions/docs/quickstart

Я создал функцию с триггером HTTP и смог выполнить запрос POST для запуска функции для записи в Datastore.

Мне было интересно, есть ли способ защитить эту конечную точку HTTP? В настоящее время кажется, что он примет запрос от любого/любого.

Когда я прихожу к поиску, я вижу, что большинство результатов говорят о защите вещей с помощью Firebase. Однако я не использую службу Firebase здесь.

Могут ли мои параметры либо открыть его, либо надеяться, что никто не знает конечную точку URL (безопасность от неизвестности) или не выполнит мою собственную проверку подлинности в самой функции?

Ответ 1

Изучив это далее и воспользовавшись подсказкой ответа @ricka, я решил реализовать проверку подлинности для моих облачных функций с помощью токена JWT, переданного в форме токена доступа к заголовку авторизации.

Вот реализация в Node:

const client = jwksClient({
  cache: true,
  rateLimit: true,
  jwksRequestsPerMinute: 5,
  jwksUri: "https://<auth0-account>.auth0.com/.well-known/jwks.json"
});

function verifyToken(token, cb) {
  let decodedToken;
  try {
    decodedToken = jwt.decode(token, {complete: true});
  } catch (e) {
    console.error(e);
    cb(e);
    return;
  }
  client.getSigningKey(decodedToken.header.kid, function (err, key) {
    if (err) {
      console.error(err);
      cb(err);
      return;
    }
    const signingKey = key.publicKey || key.rsaPublicKey;
    jwt.verify(token, signingKey, function (err, decoded) {
      if (err) {
        console.error(err);
        cb(err);
        return
      }
      console.log(decoded);
      cb(null, decoded);
    });
  });
}

function checkAuth (fn) {
  return function (req, res) {
    if (!req.headers || !req.headers.authorization) {
      res.status(401).send('No authorization token found.');
      return;
    }
    const parts = req.headers.authorization.split(' ');
    if (parts.length != 2) {
      res.status(401).send('Bad credential format.');
      return;
    }
    const scheme = parts[0];
    const credentials = parts[1];

    if (!/^Bearer$/i.test(scheme)) {
      res.status(401).send('Bad credential format.');
      return;
    }
    verifyToken(credentials, function (err) {
      if (err) {
        res.status(401).send('Invalid token');
        return;
      }
      fn(req, res);
    });
  };
}

Я использую jsonwebtoken для проверки токена JWT и jwks-rsa для получения открытого ключа. Я использую Auth0, поэтому jwks-rsa обращается к списку открытых ключей, чтобы получить их.

Затем функцию checkAuth можно использовать для защиты облачной функции:

exports.get = checkAuth(function (req, res) {
    // do things safely here
});

Вы можете увидеть это изменение в моем репозитории github на https://github.com/tnguyen14/functions-datastore/commit/a6b32704f0b0a50cd719df8c1239f993ef74dab6

Токен доступа/доступа можно получить несколькими способами. Для Auth0 документ API можно найти по адресу https://auth0.com/docs/api/authentication#authorize-client.

Как только это будет сделано, вы можете запустить облачную функцию (если у вас включена функция HTTP триггера), например,

curl -X POST -H "Content-Type: application/json" \
-H "Authorization: Bearer access-token" \
-d '{"foo": "bar"}' \
"https://<cloud-function-endpoint>.cloudfunctions.net/get"

Ответ 2

Похоже, в настоящее время существует 2 способа защиты конечной точки HTTP Cloud Function.

1) Используйте имя функции с труднодоступным именем (например: my-function-vrf55m6f5Dvkrerytf35)

2) Проверьте пароль/учетные данные/подписанный запрос внутри самой функции (используя заголовок или параметр)

Наверное, лучше всего сделать то и другое.

Ответ 3

Не стоит "оставлять это открытым и надеяться, что никто не знает". Вы можете выполнить свою собственную проверку безопасности или попробовать модуль Google Function Authorizer (https://www.npmjs.com/package/google-function-authorizer).

Ответ 4

Вы можете создать собственный алгоритм аутентификации для проверки Клиента.

Проверьте алгоритм из; https://security.stackexchange.com/q/210085/22239