mirror of
https://github.com/comatory/fb2iCal
synced 2025-01-27 15:49:17 +01:00
initial commit
This commit is contained in:
commit
7d1a7cfa32
2
.gitignore
vendored
Normal file
2
.gitignore
vendored
Normal file
@ -0,0 +1,2 @@
|
||||
node_modules/
|
||||
dist/
|
15
lib/crawler.js
Normal file
15
lib/crawler.js
Normal file
@ -0,0 +1,15 @@
|
||||
const puppeteer = require('puppeteer')
|
||||
|
||||
const crawl = async (url) => {
|
||||
const browser = await puppeteer.launch()
|
||||
const page = await browser.newPage()
|
||||
await page.goto(url)
|
||||
|
||||
const html = await page.evaluate(() => document.body.innerHTML)
|
||||
|
||||
await browser.close()
|
||||
|
||||
return html
|
||||
}
|
||||
|
||||
module.exports = crawl
|
40
lib/index.js
Normal file
40
lib/index.js
Normal file
@ -0,0 +1,40 @@
|
||||
const express = require('express')
|
||||
const bodyParser = require('body-parser')
|
||||
const path = require('path')
|
||||
|
||||
const crawl = require('./crawler')
|
||||
const parseHTML = require('./parser')
|
||||
|
||||
const port = process.env.PORT || 3000
|
||||
const app = express()
|
||||
|
||||
app.set('view engine', 'ejs')
|
||||
app.set('views', path.join(__dirname, 'views'))
|
||||
app.use(bodyParser())
|
||||
|
||||
app.get('/', (req, res) => {
|
||||
res.render('index')
|
||||
})
|
||||
|
||||
app.get('*', (req, res) => {
|
||||
res.render('404')
|
||||
})
|
||||
|
||||
app.post('/download', async (req, res) => {
|
||||
const { url } = req.body
|
||||
|
||||
try {
|
||||
const html = await crawl(url)
|
||||
const data = parseHTML(html)
|
||||
console.log(data)
|
||||
} catch (err) {
|
||||
console.error(err)
|
||||
return res.render('error', { error: err.toString() })
|
||||
}
|
||||
|
||||
return res.render('download', { url })
|
||||
})
|
||||
|
||||
app.listen(port, () => {
|
||||
console.log(`App running on port ${port}`)
|
||||
})
|
26
lib/parser.js
Normal file
26
lib/parser.js
Normal file
@ -0,0 +1,26 @@
|
||||
const { parse } = require('node-html-parser')
|
||||
|
||||
const parseHTML = (html) => {
|
||||
let data = {}
|
||||
|
||||
const root = parse(html)
|
||||
const eventSummary = root.querySelector('#event_summary')
|
||||
|
||||
const timeInfo = eventSummary.querySelector('#event_time_info')
|
||||
const timeContent = timeInfo.querySelector('[content]')
|
||||
|
||||
if (
|
||||
timeContent &&
|
||||
timeContent.attributes &&
|
||||
timeContent.attributes.content
|
||||
) {
|
||||
data = {
|
||||
...data,
|
||||
time: timeContent.attributes.content.value,
|
||||
}
|
||||
}
|
||||
|
||||
return data
|
||||
}
|
||||
|
||||
module.exports = parseHTML
|
17
lib/views/404.ejs
Normal file
17
lib/views/404.ejs
Normal file
@ -0,0 +1,17 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<title>Facebook Events to iCal Converter | 404</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h2>Page does not exist</h2>
|
||||
|
||||
<p>
|
||||
The page you requested does not exist.
|
||||
|
||||
<a href="/">Go back</a>
|
||||
</p>
|
||||
</body>
|
||||
</html>
|
20
lib/views/download.ejs
Normal file
20
lib/views/download.ejs
Normal file
@ -0,0 +1,20 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<title>Facebook Events to iCal Converter | download</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h2>Your ICS file is ready</h2>
|
||||
|
||||
<p>
|
||||
The <code>ics</code> file was created successfully from url
|
||||
<a href="<%= url %>"><%= url %></a>.
|
||||
</p>
|
||||
<p>
|
||||
Your download will start automatically.
|
||||
</p>
|
||||
<a href="/">Go back</a>
|
||||
</body>
|
||||
</html>
|
18
lib/views/error.ejs
Normal file
18
lib/views/error.ejs
Normal file
@ -0,0 +1,18 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<title>Facebook Events to iCal Converter | error</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h2>Error</h2>
|
||||
|
||||
<p>
|
||||
There was an error parsing the URL:
|
||||
|
||||
<%= error || '' %>
|
||||
</p>
|
||||
<a href="/">Go back</a>
|
||||
</body>
|
||||
</html>
|
23
lib/views/index.ejs
Normal file
23
lib/views/index.ejs
Normal file
@ -0,0 +1,23 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<title>Facebook Events to iCal Converter</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<h1>Facebook Events to iCal Converter</h1>
|
||||
|
||||
<p>
|
||||
Insert Facebook event URL into the form. When you submit it
|
||||
you will get <a href="https://en.wikipedia.org/wiki/ICalendar"><code>ics</code></a>
|
||||
file that you can import
|
||||
into your calendar.
|
||||
</p>
|
||||
|
||||
<form action='/download' method='POST'>
|
||||
<input type='text' name='url' placeholder='Paste / type FB event URL here...' />
|
||||
<input type='submit' value='Submit' />
|
||||
</form>
|
||||
</body>
|
||||
</html>
|
3075
package-lock.json
generated
Normal file
3075
package-lock.json
generated
Normal file
File diff suppressed because it is too large
Load Diff
30
package.json
Normal file
30
package.json
Normal file
@ -0,0 +1,30 @@
|
||||
{
|
||||
"name": "facebook-events-ical-converter",
|
||||
"version": "1.0.0",
|
||||
"description": "App that converts events on Facebook event page to iCal file.",
|
||||
"main": "lib/index.js",
|
||||
"scripts": {
|
||||
"start": "PORT=80 node lib/index.js",
|
||||
"start:dev": "nodemon lib/index.js",
|
||||
"test": "echo \"Error: no test specified\" && exit 1"
|
||||
},
|
||||
"keywords": [
|
||||
"facebook",
|
||||
"event",
|
||||
"ical",
|
||||
"convert",
|
||||
"download"
|
||||
],
|
||||
"author": "Ondrej Synacek <ondrejsynacek@fastmail.com>",
|
||||
"license": "ISC",
|
||||
"dependencies": {
|
||||
"body-parser": "^1.19.0",
|
||||
"ejs": "^2.7.1",
|
||||
"express": "^4.17.1",
|
||||
"node-html-parser": "^1.1.16",
|
||||
"puppeteer": "^1.20.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"nodemon": "^1.19.3"
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user