mirror of
https://github.com/fergalmoran/onearmy-community-platform.git
synced 2025-12-22 09:37:54 +00:00
db backup function
This commit is contained in:
1
functions-cron
Submodule
1
functions-cron
Submodule
Submodule functions-cron added at 18009b3c48
@@ -11,14 +11,14 @@
|
||||
},
|
||||
"main": "lib/index.js",
|
||||
"dependencies": {
|
||||
"axios": "^0.18.0",
|
||||
"body-parser": "^1.18.3",
|
||||
"cors": "^2.8.5",
|
||||
"express": "^4.16.4",
|
||||
"firebase-admin": "~6.0.0",
|
||||
"firebase-functions": "^2.1.0",
|
||||
"google-auth-library": "^2.0.1",
|
||||
"googleapis": "^35.0.0",
|
||||
"request-promise": "^4.2.2"
|
||||
"googleapis": "^35.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"tslint": "~5.8.0",
|
||||
|
||||
@@ -1,12 +1,14 @@
|
||||
import { pubsub } from 'firebase-functions'
|
||||
// import { pubsub } from 'firebase-functions'
|
||||
import { JWT } from 'google-auth-library'
|
||||
import * as admin from 'firebase-admin'
|
||||
// import * as rp from 'request-promise'
|
||||
import * as devKey from './config/dev-service-account-key.json'
|
||||
import * as config from './config/dev-service-account-key.json'
|
||||
import Axios from 'axios'
|
||||
|
||||
const PROJECT_ID = 'test'
|
||||
/* Cloud function to automatically backup the firebase database adapted from:
|
||||
https://thatweirddeveloper.com/how-to-back-up-cloud-firestore-periodically
|
||||
*/
|
||||
|
||||
admin.initializeApp()
|
||||
const PROJECT_ID = config.project_id
|
||||
|
||||
// authorise application using JWT, requires key file defined above as dev key
|
||||
// see config/readme for more info
|
||||
@@ -16,17 +18,15 @@ const getAccessToken = async () => {
|
||||
'https://www.googleapis.com/auth/cloud-platform',
|
||||
]
|
||||
const jwtClient = new JWT(
|
||||
devKey.client_email,
|
||||
config.client_email,
|
||||
null,
|
||||
devKey.private_key,
|
||||
config.private_key,
|
||||
scopes,
|
||||
)
|
||||
try {
|
||||
const authorization = await jwtClient.authorize()
|
||||
console.log('authorisation successful', authorization)
|
||||
return authorization.access_token
|
||||
} catch (error) {
|
||||
console.error(error)
|
||||
return null
|
||||
}
|
||||
}
|
||||
@@ -36,19 +36,35 @@ export const AuthTest = async () => {
|
||||
return token
|
||||
}
|
||||
|
||||
export const DatabaseBackup = async () =>
|
||||
pubsub.topic('firebase-backup').onPublish(async (message, context) => {
|
||||
console.log('executing database backup')
|
||||
const accessToken = await getAccessToken()
|
||||
console.log('access token received', accessToken)
|
||||
const url = `https://firestore.googleapis.com/v1beta1/projects/${PROJECT_ID}/databases/(default):exportDocuments`
|
||||
// return rp.post(url, {
|
||||
// headers: {
|
||||
// Authorization: `Bearer ${accessToken}`,
|
||||
// },
|
||||
// json: true,
|
||||
// body: {
|
||||
// outputUriPrefix: `gs://${PROJECT_ID}-backups`,
|
||||
// },
|
||||
// })
|
||||
})
|
||||
// rest reference: https://cloud.google.com/firestore/docs/reference/rest/v1beta2/projects.databases/exportDocuments
|
||||
export const BackupDatabase = async () => {
|
||||
console.log('executing database backup')
|
||||
const accessToken = await getAccessToken()
|
||||
console.log('access token received', accessToken)
|
||||
const url = `https://firestore.googleapis.com/v1beta1/projects/${PROJECT_ID}/databases/(default):exportDocuments`
|
||||
// use axios to send post request as promise
|
||||
console.log('posting', url)
|
||||
const timestamp: string = new Date().toString()
|
||||
let res
|
||||
try {
|
||||
res = await Axios({
|
||||
url: url,
|
||||
method: 'post',
|
||||
headers: {
|
||||
Authorization: `Bearer ${accessToken}`,
|
||||
},
|
||||
data: {
|
||||
outputUriPrefix: `gs://${PROJECT_ID}.appspot.com/backups/${timestamp}`,
|
||||
},
|
||||
})
|
||||
} catch (error) {
|
||||
res = 404
|
||||
}
|
||||
return res
|
||||
}
|
||||
|
||||
// const createSub = async () => {
|
||||
// pubsub
|
||||
// .topic('firebase-backup')
|
||||
// .onPublish(async (message, context) => BackupDatabase)
|
||||
// }
|
||||
|
||||
@@ -3,17 +3,19 @@ import * as bodyParser from 'body-parser'
|
||||
import * as cors from 'cors'
|
||||
import * as express from 'express'
|
||||
import * as functions from 'firebase-functions'
|
||||
import * as admin from 'firebase-admin'
|
||||
admin.initializeApp()
|
||||
|
||||
// custom module imports
|
||||
import * as DB from './databaseBackup'
|
||||
|
||||
// dev only
|
||||
const buildNumber = 1
|
||||
const app = express()
|
||||
// update on change logging purposes
|
||||
const buildNumber = 1.03
|
||||
|
||||
// express settings to handle api
|
||||
const app = express()
|
||||
// Automatically allow cross-origin requests
|
||||
app.use(cors({ origin: true }))
|
||||
|
||||
// use bodyparse to create json object from body
|
||||
app.use(
|
||||
bodyParser.json({
|
||||
@@ -23,13 +25,11 @@ app.use(
|
||||
app.use(bodyParser.urlencoded({ extended: false }))
|
||||
|
||||
/************ GET and POST requests ************************************************
|
||||
Redirect requests so that if a custom endpoint function exists on koboApi call it,
|
||||
otherwise pipe request directly to kobo native API
|
||||
Redirect requests so that if a custom endpoint function exists we can call them
|
||||
at /api/[endpoint]
|
||||
************************************************************************************/
|
||||
|
||||
app.all('*', async (req, res, next) => {
|
||||
// log the version number for dev / tracking:
|
||||
console.log('api build number', buildNumber)
|
||||
// get the endpoint based on the request path
|
||||
const endpoint = req.path.split('/')[1]
|
||||
// *** NOTE currently all request types handled the same, i.e. GET/POST
|
||||
@@ -38,17 +38,35 @@ app.all('*', async (req, res, next) => {
|
||||
case 'db-test':
|
||||
const token = await DB.AuthTest()
|
||||
res.send(token)
|
||||
break
|
||||
case 'backup':
|
||||
const response = await DB.BackupDatabase()
|
||||
res.send(response)
|
||||
break
|
||||
default:
|
||||
res.send('invalid api endpoint')
|
||||
}
|
||||
})
|
||||
|
||||
// Expose Express API as a single Cloud Function:
|
||||
exports.api = functions.https.onRequest(app)
|
||||
|
||||
app.listen(3000, 'localhost', listen => {
|
||||
console.log('API listening on port 3000')
|
||||
console.log(`API v${buildNumber} listening on port 3000`)
|
||||
})
|
||||
|
||||
/************ Cron tasks ***********************************************************
|
||||
Use pubsub to automatically subscribe to messages sent from cron.
|
||||
Add/change schedule from `./functions-cron/appengine/cron.yaml`
|
||||
************************************************************************************/
|
||||
|
||||
exports.backupFirestore = functions.pubsub
|
||||
.topic('firebase-backup')
|
||||
.onPublish(async (message, context) => {
|
||||
console.log('initiating backup')
|
||||
// run our daily db backup task
|
||||
const backup = await DB.BackupDatabase()
|
||||
console.log('backup:', backup)
|
||||
return true
|
||||
})
|
||||
|
||||
// add export so can be used by test
|
||||
export default app
|
||||
|
||||
11974
package-lock.json
generated
11974
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
@@ -32,6 +32,7 @@
|
||||
"src/setupTests.ts",
|
||||
"config/*.js",
|
||||
"config/jest/*.js",
|
||||
"functions-cron",
|
||||
"functions"
|
||||
]
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user