2020-03-27 17:12:38 -04:00
|
|
|
const needle = require('needle');
|
|
|
|
const cheerio = require('cheerio');
|
|
|
|
const config = require('./config');
|
|
|
|
|
|
|
|
const cookiejar = {};
|
|
|
|
async function fetch(uri, meth, data, opts, ...rest) {
|
|
|
|
meth = meth || 'get';
|
|
|
|
opts = opts || {};
|
|
|
|
opts.headers = opts.headers || {};
|
|
|
|
opts.headers.Referer = uri;
|
|
|
|
opts.cookies = cookiejar;
|
|
|
|
const r = await needle(meth, uri, data, opts, ...rest);
|
2020-03-27 17:20:16 -04:00
|
|
|
if (r.cookies)
|
2020-03-27 17:12:38 -04:00
|
|
|
Object.keys(r.cookies).forEach(k => cookiejar[k] = r.cookies[k]);
|
|
|
|
const $ = cheerio.load(r.body.toString());
|
|
|
|
let err;
|
2020-03-27 17:20:16 -04:00
|
|
|
$('h1').each(function () {
|
2020-03-27 17:12:38 -04:00
|
|
|
const t = $(this).text();
|
2020-03-27 17:20:16 -04:00
|
|
|
if (/^\s*Oops!/.test(t))
|
2020-03-27 17:12:38 -04:00
|
|
|
err = t;
|
|
|
|
});
|
2020-03-27 17:20:16 -04:00
|
|
|
if (err)
|
2020-03-27 17:12:38 -04:00
|
|
|
throw Error(`${uri} returned oops: ${err}`);
|
|
|
|
return $;
|
|
|
|
}
|
|
|
|
|
|
|
|
function getfields($, sel) {
|
|
|
|
const fields = {};
|
2020-03-27 17:20:16 -04:00
|
|
|
$('input').each(function () {
|
2020-03-27 17:12:38 -04:00
|
|
|
const e = $(this);
|
|
|
|
const n = e.attr('name');
|
2020-03-27 17:20:16 -04:00
|
|
|
if (!n) return;
|
2020-03-27 17:12:38 -04:00
|
|
|
const v = e.attr('value');
|
2020-03-27 17:20:16 -04:00
|
|
|
if (v) fields[n] = v;
|
2020-03-27 17:12:38 -04:00
|
|
|
});
|
|
|
|
return fields;
|
|
|
|
}
|
|
|
|
|
|
|
|
async function login_core() {
|
|
|
|
const uri = config.root + '/user/sign-in';
|
|
|
|
console.log('fetching sign-in page...');
|
|
|
|
let $ = await fetch(uri);
|
|
|
|
const fields = getfields($);
|
|
|
|
fields.username = config.user;
|
|
|
|
fields.password = config.pass;
|
|
|
|
console.log('submitting sign-in form...');
|
|
|
|
$ = await fetch(uri, 'post', fields);
|
|
|
|
let success;
|
2020-03-27 17:20:16 -04:00
|
|
|
$('h1').each(function () {
|
2020-03-27 17:12:38 -04:00
|
|
|
success = success || /^\s*Redirecting\b/i.test($(this).text());
|
|
|
|
});
|
2020-03-27 17:20:16 -04:00
|
|
|
if (!success)
|
2020-03-27 17:12:38 -04:00
|
|
|
throw Error('sign-in no redirect: ' + $('body').text());
|
|
|
|
}
|
|
|
|
|
|
|
|
let loginprom;
|
|
|
|
async function login() {
|
2020-03-27 17:20:16 -04:00
|
|
|
if (!loginprom)
|
2020-03-27 17:12:38 -04:00
|
|
|
loginprom = login_core();
|
|
|
|
return await loginprom;
|
|
|
|
}
|
|
|
|
|
|
|
|
function findopt($, sel, name) {
|
|
|
|
let v;
|
|
|
|
$(sel).each(function () {
|
|
|
|
const o = $(this);
|
|
|
|
const t = o.text();
|
|
|
|
if (t.toLowerCase().startsWith(name.toLowerCase()))
|
|
|
|
v = o.attr('value');
|
|
|
|
});
|
|
|
|
return v;
|
|
|
|
}
|
|
|
|
|
2020-03-27 17:20:16 -04:00
|
|
|
module.exports = {
|
|
|
|
fetch,
|
|
|
|
getfields,
|
|
|
|
login,
|
|
|
|
findopt
|
|
|
|
};
|