Best practice for creating multiple lightweight Google Cloud Functions?

前端 未结 2 558
一整个雨季
一整个雨季 2020-12-31 19:27

The way it seems Google Cloud Functions works is by:

  • your modules go inside a functions directory
  • that functions directory t
2条回答
  •  遥遥无期
    2020-12-31 19:54

    Rather than exporting each Cloud Function individually, we can export all of them at once by requiring a file that export's every file in a specific directory and its subdirectories.

    functions/index.js
    'use strict';
    
    const admin = require('firebase-admin');
    const functions = require('firebase-functions');
    const logging = require('@google-cloud/logging')();
    const stripe = require('stripe')(functions.config().stripe.token);
    
    admin.initializeApp(functions.config().firebase);
    
    module.exports = require('./exports')({
        admin, functions, logging, stripe
    });
    

    We can create a folder for each provider, e.g. auth, database, https, in which we can organise the associated resource's events such as auth.user.onCreate or database.ref.onWrite.

    By structuring our files this way with an event in each file, we can search for the function files and use the file path to dynamically create the Cloud Function's name and export it.

    e.g. functions/exports/auth/user/onCreate.f.js -> onCreateAuthUser

    functions/exports/index.js
    'use strict';
    
    module.exports = (app) => {
    
        const glob = require('glob');
    
        glob.sync('./**/*.f.js', { cwd: __dirname }).forEach(file => {
    
            const only = process.env.FUNCTION_NAME;
            const name = concoctFunctionName(file);
    
            if (only === undefined || only === name) {
                exports[name] = require(file)(app);
            }
        });
    
        return exports;
    }
    
    function concoctFunctionName(file) {
    
        const camel = require('camelcase');
        const split = file.split('/');
        const event = split.pop().split('.')[0];
        const snake = `${event}_${split.join('_')}`;
    
        return camel(snake);
    }
    

    Finally, our function files can use the argument passed to access commonly required services such as Firebase Admin and Functions, and even Stripe.

    functions/exports/auth/user/onCreate.f.js
    'use strict';
    
    module.exports = ({ admin, functions, stripe }) => {
    
        return functions.auth.user().onCreate(event => {
    
            const { email, uid } = event.data;
            const ref = admin.database.ref.child(`user-customer/${uid}`);
    
            return stripe.customers.create({ 
                email, metadata: { uid } 
            }).then(customer => {
                return ref.set(customer);
            });
        });
    }
    

提交回复
热议问题