diff --git a/.github/workflows/push.yml b/.github/workflows/push.yml index a9d5e23..6f41785 100644 --- a/.github/workflows/push.yml +++ b/.github/workflows/push.yml @@ -31,3 +31,4 @@ jobs: run: | docker tag ghcr.io/wanteddev/lighthouse:${{github.event.release.tag_name}} ghcr.io/wanteddev/lighthouse:latest docker push ghcr.io/wanteddev/lighthouse:latest + if: "github.event.release.prerelease != true" diff --git a/.gitignore b/.gitignore index 31a37f7..b150984 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,3 @@ node_modules -*.http \ No newline at end of file +*.http +.env \ No newline at end of file diff --git a/src/routes/index.js b/src/routes/index.js index d755e9d..d918892 100644 --- a/src/routes/index.js +++ b/src/routes/index.js @@ -209,28 +209,27 @@ router.post('/receive_submission', async function(req, res) { user_id: res_data.user.id, username: res_data.user.username, channel, + auth_header: undefined, + cookie_name: undefined, + cookie_value: undefined, }; + console.log(JSON.stringify(values)); for (const key in values) { if (values[key].audit_options && values[key].audit_options.selected_options && values[key].audit_options.selected_options.length > 0) { values[key].audit_options.selected_options.forEach(option => { submission[option.value] = true; }); - } - - if (values[key].audit_url) { - submission.audit_url = values[key].audit_url.value; - } - - if (values[key].schedule) { - submission.schedule = values[key].schedule.value; + } else { + for (const optionKey of Object.keys(values[key])) { + submission[optionKey] = values[key][optionKey].value; + } } } try { // Ad-hoc run if (!is_schedule) { - const options = { throttling: submission.throttling, performance: submission.performance, @@ -238,6 +237,9 @@ router.post('/receive_submission', async function(req, res) { 'best-practices': submission['best-practices'], pwa: submission.pwa, seo: submission.seo, + auth_header: submission.auth_header, + cookie_name: submission.cookie_name, + cookie_value: submission.cookie_value, }; res.send(); await runAudit(submission.audit_url, submission.user_id, submission.channel, options); @@ -255,6 +257,9 @@ router.post('/receive_submission', async function(req, res) { 'best-practices': schedule['best-practices'], pwa: schedule.pwa, seo: schedule.seo, + auth_header: schedule.auth_header, + cookie_name: schedule.cookie_name, + cookie_value: schedule.cookie_value, }; await runAudit(schedule.audit_url, schedule.user_id, schedule.channel, options); }); diff --git a/src/store/schedule.js b/src/store/schedule.js index f695a50..ad32046 100644 --- a/src/store/schedule.js +++ b/src/store/schedule.js @@ -16,6 +16,9 @@ const schema = new mongoose.Schema({ seo: Boolean, pwa: Boolean, throttling: Boolean, + auth_header: String, + cookie_name: String, + cookie_value: String, }); const ScheduleModel = mongoose.model('Schedule', schema); @@ -34,6 +37,9 @@ async function createSchedule(payload) { seo: payload.seo, pwa: payload.pwa, throttling: payload.throttling, + auth_header: payload.auth_header, + cookie_name: payload.cookie_name, + cookie_value: payload.cookie_value, }); const data = await new_schedule.save(); diff --git a/src/utils/lighthouse.js b/src/utils/lighthouse.js index a4af532..863ded1 100644 --- a/src/utils/lighthouse.js +++ b/src/utils/lighthouse.js @@ -27,18 +27,22 @@ async function launchPuppeteer(url, options) { '--disable-dev-shm-usage' ] }); + const page = await browser.newPage(); - // Run authentication script (as injected javascript) - if (options.auth_script) { - const page = await browser.newPage(); - await page.goto(url, { - waitUntil: 'networkidle0', - }); - await page.waitForSelector(options.await_selector, {visible: true}); - await page.evaluate(options.auth_script); - await page.waitForNavigation(); + if (options.auth_header) { + await page.setExtraHTTPHeaders({ + 'Authorization': options.auth_header, + }) } + if (options.cookie_name && options.cookie_value) { + await page.setCookie({ name: options.cookie_name, value: options.cookie_value, url }); + } + await page.goto(url, { + waitUntil: 'networkidle0', + }); + await page.waitForSelector('body', {visible: true}); + await page.close(); // Lighthouse will open URL. Puppeteer observes `targetchanged` and sets up network conditions. // Possible race condition. let opts = { @@ -83,7 +87,6 @@ async function launchPuppeteer(url, options) { const {lhr} = await lighthouse(url, opts); // Return response back to main thread parentPort.postMessage(lhr); - await browser.close(); return; } catch(error) { diff --git a/src/utils/responseBuilder.js b/src/utils/responseBuilder.js index 148ecf5..25d710f 100644 --- a/src/utils/responseBuilder.js +++ b/src/utils/responseBuilder.js @@ -123,6 +123,60 @@ function generateAuditDialog(is_schedule) { blocks.push(schedule); } + const auth_header = { + type: 'input', + optional: true, + element: { + type: 'plain_text_input', + action_id: 'auth_header', + placeholder: { + type: 'plain_text', + text: 'JWT ofma3103dSFNsUJasn311ndSN' + } + }, + label: { + type: 'plain_text', + text: 'Authorization Header' + } + }; + blocks.push(auth_header); + + const cookie_name = { + type: 'input', + optional: true, + element: { + type: 'plain_text_input', + action_id: 'cookie_name', + placeholder: { + type: 'plain_text', + text: 'jwt' + } + }, + label: { + type: 'plain_text', + text: 'Cookie Name' + } + }; + blocks.push(cookie_name); + + const cookie_value = { + type: 'input', + optional: true, + element: { + type: 'plain_text_input', + action_id: 'cookie_value', + placeholder: { + type: 'plain_text', + text: 'ofma3103dSFNsUJasn311ndSN...' + } + }, + label: { + type: 'plain_text', + text: 'Cookie Value' + } + }; + blocks.push(cookie_value); + // Option dropdowns const options = { type: 'input',