jas*_*ota 135 javascript firebase google-cloud-functions
我想为Firebase创建多个云功能,并从一个项目同时部署它们.我还想将每个函数分成一个单独的文件.目前我可以创建多个函数,如果我将它们都放在index.js中,例如:
exports.foo = functions.database.ref('/foo').onWrite(event => {
...
});
exports.bar = functions.database.ref('/bar').onWrite(event => {
...
});
Run Code Online (Sandbox Code Playgroud)
但是我想将foo和bar放在单独的文件中.我试过这个:
/functions
|--index.js (blank)
|--foo.js
|--bar.js
|--package.json
Run Code Online (Sandbox Code Playgroud)
foo.js在哪里
exports.foo = functions.database.ref('/foo').onWrite(event => {
...
});
Run Code Online (Sandbox Code Playgroud)
和bar.js是
exports.bar = functions.database.ref('/bar').onWrite(event => {
...
});
Run Code Online (Sandbox Code Playgroud)
有没有办法在不将所有函数放在index.js中的情况下完成此操作?
jas*_*ota 111
啊,Firebase的云功能正常加载节点模块,所以这样可行
结构体:
/functions
|--index.js
|--foo.js
|--bar.js
|--package.json
Run Code Online (Sandbox Code Playgroud)
index.js:
const functions = require('firebase-functions');
const fooModule = require('./foo');
const barModule = require('./bar');
exports.foo = functions.database.ref('/foo').onWrite(fooModule.handler);
exports.bar = functions.database.ref('/bar').onWrite(barModule.handler);
Run Code Online (Sandbox Code Playgroud)
foo.js:
exports.handler = (event) => {
...
};
Run Code Online (Sandbox Code Playgroud)
bar.js:
exports.handler = (event) => {
...
};
Run Code Online (Sandbox Code Playgroud)
Col*_*ent 66
@jasonsirota的答案非常有帮助.但是查看更详细的代码可能很有用,尤其是在HTTP触发函数的情况下.
使用与@ jasonsirota的答案相同的结构,假设您希望在两个不同的文件中有两个单独的HTTP触发器函数:
目录结构:
/functions
|--index.js
|--foo.js
|--bar.js
|--package.json`
Run Code Online (Sandbox Code Playgroud)
index.js:
'use strict';
const fooFunction = require('./foo');
const barFunction = require('./bar');
// Note do below initialization tasks in index.js and
// NOT in child functions:
const functions = require('firebase-functions');
const admin = require('firebase-admin');
admin.initializeApp(functions.config().firebase);
const database = admin.database();
// Pass database to child functions so they have access to it
exports.fooFunction = functions.https.onRequest((req, res) => {
fooFunction.handler(req, res, database);
});
exports.barFunction = functions.https.onRequest((req, res) => {
barFunction.handler(req, res, database);
});
Run Code Online (Sandbox Code Playgroud)
foo.js:
exports.handler = function(req, res, database) {
// Use database to declare databaseRefs:
usersRef = database.ref('users');
...
res.send('foo ran successfully');
}
Run Code Online (Sandbox Code Playgroud)
bar.js:
exports.handler = function(req, res, database) {
// Use database to declare databaseRefs:
usersRef = database.ref('users');
...
res.send('bar ran successfully');
}
Run Code Online (Sandbox Code Playgroud)
Ced*_*Ced 37
这是我个人用打字稿做的人:
/functions
|--src
|--index.ts
|--http-functions.ts
|--main.js
|--db.ts
|--package.json
|--tsconfig.json
Run Code Online (Sandbox Code Playgroud)
让我作为前言,给出两个警告来完成这项工作:
对于第2点,我不确定为什么.Secundo你应该尊重我的指标,主要和DB配置完全相同(至少尝试一下).
index.ts:处理出口.我发现让index.ts处理出口更清洁.
// main must be before functions
export * from './main';
export * from "./http-functions";
Run Code Online (Sandbox Code Playgroud)
main.ts:处理初始化.
import { config } from 'firebase-functions';
import { initializeApp } from 'firebase-admin';
initializeApp(config().firebase);
export * from "firebase-functions";
Run Code Online (Sandbox Code Playgroud)
db.ts:只是重新导出数据库,因此其名称短于database()
import { database } from "firebase-admin";
export const db = database();
Run Code Online (Sandbox Code Playgroud)
HTTP-functions.ts
// db must be imported like this
import { db } from './db';
// you can now import everything from index.
import { https } from './index';
// or (both work)
// import { https } from 'firebase-functions';
export let newComment = https.onRequest(createComment);
export async function createComment(req: any, res: any){
db.ref('comments').push(req.body.comment);
res.send(req.body.comment);
}
Run Code Online (Sandbox Code Playgroud)
Luk*_*tti 17
使用Node 8 LTS现在可以使用Cloud/Firebase功能,您可以使用扩展运算符执行以下操作:
"engines": {
"node": "8"
},
Run Code Online (Sandbox Code Playgroud)
const functions = require("firebase-functions");
const admin = require("firebase-admin");
admin.initializeApp();
module.exports = {
...require("./lib/foo.js"),
// ...require("./lib/bar.js") // add as many as you like
};
Run Code Online (Sandbox Code Playgroud)
const functions = require("firebase-functions");
const admin = require("firebase-admin");
exports.fooHandler = functions.database
.ref("/food/{id}")
.onCreate((snap, context) => {
let id = context.params["id"];
return admin
.database()
.ref(`/bar/${id}`)
.set(true);
});
Run Code Online (Sandbox Code Playgroud)
Ada*_*itz 14
bigcodenerd.org轮廓的,以便有方法更简单的架构模式分成不同的文件,并在出口一线的内index.js文件。
本示例中项目的架构如下:
项目目录
索引.js
const admin = require('firebase-admin');
const podcast = require('./podcast');
const profile = require('./profile');
admin.initializeApp();
exports.getPodcast = podcast.getPodcast();
exports.removeProfile = profile.removeProfile();
Run Code Online (Sandbox Code Playgroud)
播客.js
const functions = require('firebase-functions');
exports.getPodcast = () => functions.https.onCall(async (data, context) => {
...
return { ... }
});
Run Code Online (Sandbox Code Playgroud)
配置文件中的removeProfile方法将使用相同的模式。
Kon*_*kus 10
.
??? /build/ # Compiled output for Node.js 6.x
??? /src/ # Application source files
? ??? db.js # Cloud SQL client for Postgres
? ??? index.js # Main export(s)
? ??? someFuncA.js # Function A
? ??? someFuncA.test.js # Function A unit tests
? ??? someFuncB.js # Function B
? ??? someFuncB.test.js # Function B unit tests
? ??? store.js # Firebase Firestore client
??? .babelrc # Babel configuration
??? firebase.json # Firebase configuration
??? package.json # List of project dependencies and NPM scripts
Run Code Online (Sandbox Code Playgroud)
src/index.js - 主要出口export * from './someFuncA.js';
export * from './someFuncB.js';
Run Code Online (Sandbox Code Playgroud)
src/db.js - Postgres的Cloud SQL Clientimport { Pool } from 'pg';
import { config } from 'firebase-functions';
export default new Pool({
max: 1,
user: '<username>',
database: '<database>',
password: config().db.password,
host: `/cloudsql/${process.env.GCP_PROJECT}:<region>:<instance>`,
});
Run Code Online (Sandbox Code Playgroud)
src/store.js - Firebase Firestore客户端import firebase from 'firebase-admin';
import { config } from 'firebase-functions';
firebase.initializeApp(config().firebase);
export default firebase.firestore();
Run Code Online (Sandbox Code Playgroud)
src/someFuncA.js - 功能A.import { https } from 'firebase-functions';
import db from './db';
export const someFuncA = https.onRequest(async (req, res) => {
const { rows: regions } = await db.query(`
SELECT * FROM regions WHERE country_code = $1
`, ['US']);
res.send(regions);
});
Run Code Online (Sandbox Code Playgroud)
src/someFuncB.js - 功能B.import { https } from 'firebase-functions';
import store from './store';
export const someFuncB = https.onRequest(async (req, res) => {
const { docs: regions } = await store
.collection('regions')
.where('countryCode', '==', 'US')
.get();
res.send(regions);
});
Run Code Online (Sandbox Code Playgroud)
.babelrc{
"presets": [["env", { "targets": { "node": "6.11" } }]],
}
Run Code Online (Sandbox Code Playgroud)
firebase.json{
"functions": {
"source": ".",
"ignore": [
"**/node_modules/**"
]
}
}
Run Code Online (Sandbox Code Playgroud)
package.json{
"name": "functions",
"verson": "0.0.0",
"private": true,
"main": "build/index.js",
"dependencies": {
"firebase-admin": "^5.9.0",
"firebase-functions": "^0.8.1",
"pg": "^7.4.1"
},
"devDependencies": {
"babel-cli": "^6.26.0",
"babel-core": "^6.26.0",
"babel-jest": "^22.2.2",
"babel-preset-env": "^1.6.1",
"jest": "^22.2.2"
},
"scripts": {
"test": "jest --env=node",
"predeploy": "rm -rf ./build && babel --out-dir ./build src",
"deploy": "firebase deploy --only functions"
}
}
Run Code Online (Sandbox Code Playgroud)
$ yarn install # Install project dependencies
$ yarn test # Run unit tests
$ yarn deploy # Deploy to Firebase
Run Code Online (Sandbox Code Playgroud)
为简单起见(但确实可行),我亲自设计了这样的代码。
布局
??? /src/
? ??? index.ts
? ??? foo.ts
? ??? bar.ts
| ??? db.ts
??? package.json
Run Code Online (Sandbox Code Playgroud)
foo.ts
import * as functions from 'firebase-functions';
export const fooFunction = functions.database()......... {
//do your function.
}
export const someOtherFunction = functions.database().......... {
// do the thing.
}
Run Code Online (Sandbox Code Playgroud)
巴特
import * as functions from 'firebase-functions';
export const barFunction = functions.database()......... {
//do your function.
}
export const anotherFunction = functions.database().......... {
// do the thing.
}
Run Code Online (Sandbox Code Playgroud)
数据库
import * as admin from 'firebase-admin';
import * as functions from 'firebase-functions';
export const firestore = admin.firestore();
export const realtimeDb = admin.database();
Run Code Online (Sandbox Code Playgroud)
索引
import * as admin from 'firebase-admin';
import * as functions from 'firebase-functions';
admin.initializeApp(functions.config().firebase);
// above codes only needed if you use firebase admin
export * from './foo';
export * from './bar';
Run Code Online (Sandbox Code Playgroud)
适用于任何嵌套级别的目录。只需遵循目录内的模式即可。
归功于@zaidfazil答案
为了保持简单(但是工作),我亲自构建了我的代码.
布局
??? /src/
? ??? index.ts
? ??? foo.ts
? ??? bar.ts
??? package.json
Run Code Online (Sandbox Code Playgroud)
foo.ts
export const fooFunction = functions.database()......... {
//do your function.
}
export const someOtherFunction = functions.database().......... {
// do the thing.
}
Run Code Online (Sandbox Code Playgroud)
bar.ts
export const barFunction = functions.database()......... {
//do your function.
}
export const anotherFunction = functions.database().......... {
// do the thing.
}
Run Code Online (Sandbox Code Playgroud)
index.ts
import * as fooFunctions from './foo';
import * as barFunctions from './bar';
module.exports = {
...fooFunctions,
...barFunctions,
};
Run Code Online (Sandbox Code Playgroud)
适用于任何嵌套级别的目录.只需遵循目录中的模式.
这种格式使您的入口点可以查找其他功能文件,并自动导出每个文件中的每个功能。
主入口点脚本
在functions文件夹中查找所有.js文件,并导出从每个文件导出的每个函数。
const fs = require('fs');
const path = require('path');
// Folder where all your individual Cloud Functions files are located.
const FUNCTIONS_FOLDER = './scFunctions';
fs.readdirSync(path.resolve(__dirname, FUNCTIONS_FOLDER)).forEach(file => { // list files in the folder.
if(file.endsWith('.js')) {
const fileBaseName = file.slice(0, -3); // Remove the '.js' extension
const thisFunction = require(`${FUNCTIONS_FOLDER}/${fileBaseName}`);
for(var i in thisFunction) {
exports[i] = thisFunction[i];
}
}
});Run Code Online (Sandbox Code Playgroud)
从一个文件导出多个功能的示例
const functions = require('firebase-functions');
const query = functions.https.onRequest((req, res) => {
let query = req.query.q;
res.send({
"You Searched For": query
});
});
const searchTest = functions.https.onRequest((req, res) => {
res.send({
"searchTest": "Hi There!"
});
});
module.exports = {
query,
searchTest
}Run Code Online (Sandbox Code Playgroud)
http可访问的端点已适当命名
? functions: query: http://localhost:5001/PROJECT-NAME/us-central1/query
? functions: helloWorlds: http://localhost:5001/PROJECT-NAME/us-central1/helloWorlds
? functions: searchTest: http://localhost:5001/PROJECT-NAME/us-central1/searchTestRun Code Online (Sandbox Code Playgroud)
一个文件
如果只有几个其他文件(例如,一个),则可以使用:
const your_functions = require('./path_to_your_functions');
for (var i in your_functions) {
exports[i] = your_functions[i];
}Run Code Online (Sandbox Code Playgroud)
所以我有这个具有后台功能和http功能的项目。我也有单元测试的测试。部署云功能时,CI/CD 将使您的生活变得更加轻松
|-- package.json
|-- cloudbuild.yaml
|-- functions
|-- index.js
|-- background
| |-- onCreate
| |-- index.js
|-- create.js
|
|-- http
| |-- stripe
| |-- index.js
| |-- payment.js
|-- utils
|-- firebaseHelpers.js
|-- test
|-- ...
|-- package.json
Run Code Online (Sandbox Code Playgroud)
注意: utils/文件夹用于在函数之间共享代码
在这里,您只需导入所需的所有函数并声明它们。这里不需要有逻辑。在我看来,它使它更干净。
require('module-alias/register');
const functions = require('firebase-functions');
const onCreate = require('@background/onCreate');
const onDelete = require('@background/onDelete');
const onUpdate = require('@background/onUpdate');
const tours = require('@http/tours');
const stripe = require('@http/stripe');
const docPath = 'tours/{tourId}';
module.exports.onCreate = functions.firestore.document(docPath).onCreate(onCreate);
module.exports.onDelete = functions.firestore.document(docPath).onDelete(onDelete);
module.exports.onUpdate = functions.firestore.document(docPath).onUpdate(onUpdate);
module.exports.tours = functions.https.onRequest(tours);
module.exports.stripe = functions.https.onRequest(stripe);
Run Code Online (Sandbox Code Playgroud)
每次将更改推送到存储库时,如何进行持续集成和部署?您可以使用 google google cloud build来获得它。它是免费的,直到某一点:) 检查此链接。
./cloudbuild.yaml
steps:
- name: "gcr.io/cloud-builders/npm"
args: ["run", "install:functions"]
- name: "gcr.io/cloud-builders/npm"
args: ["test"]
- name: "gcr.io/${PROJECT_ID}/firebase"
args:
[
"deploy",
"--only",
"functions",
"-P",
"${PROJECT_ID}",
"--token",
"${_FIREBASE_TOKEN}"
]
substitutions:
_FIREBASE_TOKEN: nothing
Run Code Online (Sandbox Code Playgroud)
Firebase 文档现已更新,其中包含多文件代码组织的良好指南:
总结一下:
foo.js
const functions = require('firebase-functions');
exports.foo = functions.https.onRequest((request, response) => {
// ...
});
Run Code Online (Sandbox Code Playgroud)
bar.js
const functions = require('firebase-functions');
exports.bar = functions.https.onRequest((request, response) => {
// ...
});
Run Code Online (Sandbox Code Playgroud)
索引.js
const foo = require('./foo');
const bar = require('./bar');
exports.foo = foo.foo;
exports.bar = bar.bar;
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
41066 次 |
| 最近记录: |