Created
September 10, 2017 18:38
-
-
Save lgvalle/a4726f22f14ed5cedbe90ab53a092e08 to your computer and use it in GitHub Desktop.
Blogpost Firebase II - Full code
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
const ONE_HOUR = 3600000 | |
var functions = require('firebase-functions'); | |
const URL_THE_GUARDIAN = "https://www.theguardian.com/uk/london/rss" | |
var Client = require('node-rest-client').Client; | |
var client = new Client(); | |
const admin = require('firebase-admin'); | |
admin.initializeApp(functions.config().firebase); | |
exports.fetchGuardianWithoutCache = functions.https.onRequest((req, res) => { | |
console.log("Fetching The Guardian Without Cache"); | |
return request(URL_THE_GUARDIAN) | |
.then(data => cleanUp(data)) | |
.then(items => saveInDatabase2(items)) | |
.then(items => response(res, items, 201)) | |
}); | |
exports.fetchGuardian = functions.https.onRequest((req, res) => { | |
console.log("Fetching The Guardian"); | |
var lastEdition = admin.database().ref('/feed/guardian'); | |
return lastEdition | |
.once('value') | |
.then(snapshot => { | |
if (isCacheValid(snapshot)) { | |
return response(res, snapshot.val(), 200) | |
} else { | |
return request(URL_THE_GUARDIAN) | |
.then(data => cleanUp(data)) | |
.then(items => save(lastEdition, items)) | |
.then(items => response(res, items, 201)) | |
} | |
}) | |
}); | |
function save(databaseRef, items) { | |
return databaseRef | |
.set({ | |
date: new Date(Date.now()).toISOString(), | |
items: items | |
}) | |
.then(() => { | |
return Promise.resolve(items); | |
}) | |
} | |
function saveInDatabase2(items) { | |
return admin.database().ref('/feed/guardian') | |
.set({ items: items }) | |
.then(() => { | |
return Promise.resolve(items); | |
}) | |
} | |
function request(url) { | |
return new Promise(function (fulfill, reject) { | |
client.get(url, function (data, response) { | |
fulfill(data) | |
}) | |
}) | |
} | |
function response(res, items, code) { | |
return Promise.resolve(res.status(code) | |
.type('application/json') | |
.send(items)) | |
} | |
function isCacheValid(snapshot) { | |
return ( | |
snapshot.exists() && | |
elapsed(snapshot.val().date) < ONE_HOUR | |
) | |
} | |
function handleCache(snapshot, res, lastEdition) { | |
if (snapshot.exists() && elapsed(snapshot.val().date) < ONE_HOUR) { | |
console.log("Exist & still valid -> return from DB") | |
return res.status(200) | |
.type('application/json') | |
.send(snapshot.val()); | |
} else { | |
console.log("Exist but old -> continue") | |
} | |
console.log("Missing -> fetch") | |
client.get(URL_THE_GUARDIAN, function (data, response) { | |
console.log("feed fetched"); | |
//const items = parseChannel(data.rss.channel) | |
const items = cleanUp(data) | |
return lastEdition | |
.set({ | |
date: new Date(Date.now()).toISOString(), | |
items: items | |
}) | |
.then(function () { | |
res.status(201) | |
.type('application/json') | |
.send(items) | |
}) | |
}); | |
} | |
function elapsed(date) { | |
const then = new Date(date) | |
const now = new Date(Date.now()) | |
return now.getTime() - then.getTime() | |
} | |
function cleanUp(data) { | |
console.log("Cleaning up data: ", data) | |
// Empty array to add clean up elements | |
const items = [] | |
// We are only interested in 'channel' children | |
const channel = data.rss.channel | |
channel.item.forEach(element => { | |
item = { | |
title: element.title, | |
description: element.description, | |
date: element.pubDate, | |
creator: element['dc:creator'], | |
media: [] | |
} | |
// Iterates through all the elements named '<media:content>' extracting the info we care about | |
element['media:content'].forEach(mediaContent => { | |
item.media.push({ | |
url: mediaContent.$.url, // Parses media:content url attribute | |
credit: mediaContent['media:credit']._ // Parses media:cretit tag content | |
}) | |
}); | |
items.push(item); | |
}); | |
return Promise.resolve(items); | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment