-
Notifications
You must be signed in to change notification settings - Fork 106
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #16 from jameshy/refresh
2019 update
- Loading branch information
Showing
27 changed files
with
4,708 additions
and
266 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,14 +1,32 @@ | ||
const crypto = require('crypto') | ||
|
||
const algorithm = 'aes-256-ctr' | ||
|
||
const ALGORITHM = 'aes-256-cbc' | ||
|
||
module.exports = { | ||
encrypt(readableStream, password) { | ||
const cipher = crypto.createCipher(algorithm, password) | ||
return readableStream.pipe(cipher) | ||
encrypt(readableStream, key, iv) { | ||
this.validateKey(key) | ||
if (iv.length !== 16) { | ||
throw new Error(`encrypt iv must be exactly 16 bytes, but received ${iv.length}`) | ||
} | ||
const cipher = crypto.createCipheriv(ALGORITHM, Buffer.from(key, 'hex'), iv) | ||
readableStream.pipe(cipher) | ||
return cipher | ||
}, | ||
decrypt(readableStream, key, iv) { | ||
this.validateKey(key) | ||
const decipher = crypto.createDecipheriv(ALGORITHM, Buffer.from(key, 'hex'), iv) | ||
readableStream.pipe(decipher) | ||
return decipher | ||
}, | ||
validateKey(key) { | ||
const bytes = Buffer.from(key, 'hex') | ||
if (bytes.length !== 32) { | ||
throw new Error('encrypt key must be a 32 byte hex string') | ||
} | ||
return true | ||
}, | ||
decrypt(readableStream, password) { | ||
const decipher = crypto.createDecipher(algorithm, password) | ||
return readableStream.pipe(decipher) | ||
generateIv() { | ||
return crypto.randomBytes(16) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,54 +1,49 @@ | ||
const utils = require('./utils') | ||
const uploadS3 = require('./upload-s3') | ||
const pgdump = require('./pgdump') | ||
const encryption = require('./encryption') | ||
const Promise = require('bluebird') | ||
// todo: make these const, (mockSpawn doesn't allow this, so remove mockSpawn) | ||
var uploadS3 = require('./upload-s3') | ||
var pgdump = require('./pgdump') | ||
|
||
const DEFAULT_CONFIG = require('./config') | ||
|
||
function handler(event, context) { | ||
const config = Object.assign({}, DEFAULT_CONFIG, event) | ||
|
||
async function backup(config) { | ||
if (!config.PGDATABASE) { | ||
throw new Error('PGDATABASE not provided in the event data') | ||
} | ||
if (!config.S3_BUCKET) { | ||
throw new Error('S3_BUCKET not provided in the event data') | ||
} | ||
|
||
// determine the path for the database dump | ||
const key = utils.generateBackupPath( | ||
config.PGDATABASE, | ||
config.ROOT | ||
) | ||
|
||
const pgdumpProcess = pgdump(config) | ||
return pgdumpProcess | ||
.then(readableStream => { | ||
if (config.ENCRYPTION_PASSWORD) { | ||
console.log('encrypting dump') | ||
readableStream = encryption.encrypt( | ||
readableStream, | ||
config.ENCRYPTION_PASSWORD | ||
) | ||
} | ||
// stream to s3 uploader | ||
return uploadS3(readableStream, config, key) | ||
}) | ||
.catch(e => { | ||
throw e | ||
}) | ||
// spawn the pg_dump process | ||
let stream = await pgdump(config) | ||
if (config.ENCRYPT_KEY && encryption.validateKey(config.ENCRYPT_KEY)) { | ||
// if encryption is enabled, we generate an IV and store it in a separate file | ||
const iv = encryption.generateIv() | ||
const ivKey = key + '.iv' | ||
|
||
await uploadS3(iv.toString('hex'), config, ivKey) | ||
stream = encryption.encrypt(stream, config.ENCRYPT_KEY, iv) | ||
} | ||
// stream the backup to S3 | ||
return uploadS3(stream, config, key) | ||
} | ||
|
||
module.exports = function (event, context, cb) { | ||
return Promise.try(() => handler(event, context)) | ||
.then(result => { | ||
cb(null) | ||
return result | ||
}) | ||
.catch(err => { | ||
cb(err) | ||
throw err | ||
}) | ||
async function handler(event) { | ||
const config = { ...DEFAULT_CONFIG, ...event } | ||
try { | ||
return await backup(config) | ||
} | ||
catch (error) { | ||
// log the error and rethrow for Lambda | ||
if (process.env.NODE_ENV !== "test") { | ||
console.error(error) | ||
} | ||
throw error | ||
} | ||
} | ||
|
||
module.exports = handler |
Oops, something went wrong.