Skip to content

Commit

Permalink
feat: add context parsers for hybrid headers
Browse files Browse the repository at this point in the history
- Pass on `x-podium-app-id` as `appId` on the context
- Pass on `x-podium-base-font-size` as `baseFontSize` on the context
- Override `deviceType` with `x-podium-device-type`
  • Loading branch information
wkillerud committed Jul 15, 2024
1 parent 3506b96 commit ae178e6
Show file tree
Hide file tree
Showing 6 changed files with 76 additions and 1 deletion.
4 changes: 4 additions & 0 deletions lib/context.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ import abslog from 'abslog';
import assert from 'assert';
import * as schemas from '@podium/schemas';
import * as utils from '@podium/utils';
import AppId from './get-app-id.js';
import BaseFontSize from './get-base-font-size.js';
import PublicPathname from './get-public-pathname.js';
import MountPathname from './get-mount-pathname.js';
import MountOrigin from './get-mount-origin.js';
Expand Down Expand Up @@ -106,6 +108,8 @@ export default class PodiumContext {
buckets: [0.001, 0.01, 0.1, 0.5, 1],
});

this.register('appId', new AppId());
this.register('baseFontSize', new BaseFontSize());
this.register(
'publicPathname',
new PublicPathname(options.publicPathname),
Expand Down
19 changes: 19 additions & 0 deletions lib/get-app-id.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
export default class PodiumContextAppIdParser {
get [Symbol.toStringTag]() {
return 'PodiumContextAppIdParser';
}

/**
* @param {import('@podium/utils').HttpIncoming} incoming
* @returns {string | null}
*/
parse(incoming) {
let value = incoming.request.headers
? incoming.request.headers['x-podium-app-id']
: null;
if (!value || value === '') {
return null;
}
return value;
}
}
19 changes: 19 additions & 0 deletions lib/get-base-font-size.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
export default class PodiumContextBaseFontSizeParser {
get [Symbol.toStringTag]() {
return 'PodiumContextBaseFontSizeParser';
}

/**
* @param {import('@podium/utils').HttpIncoming} incoming
* @returns {string | null}
*/
parse(incoming) {
let value = incoming.request.headers
? incoming.request.headers['x-podium-base-font-size']
: null;
if (!value || value === '') {
return null;
}
return value;
}
}
12 changes: 11 additions & 1 deletion lib/get-device-type.js
Original file line number Diff line number Diff line change
Expand Up @@ -55,12 +55,22 @@ export default class PodiumContextDeviceTypeParser {
const userAgent = incoming.request.headers
? incoming.request.headers['user-agent']
: '';
const deviceType = incoming.request.headers
? incoming.request.headers['x-podium-device-type']
: '';

if (!userAgent || userAgent === '') {
if (
(!userAgent || userAgent === '') &&
(!deviceType || deviceType === '')
) {
// @ts-expect-error because of Object.defineProperty
return this.default;
}

if (deviceType) {
return deviceType;
}

let type = this.cache.get(userAgent.toLowerCase());

/* istanbul ignore next */
Expand Down
5 changes: 5 additions & 0 deletions tests/context.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@ import Context from '../lib/context.js';

const HEADER_RICH = {
host: 'localhost:3030',
'x-podium-app-id': '[email protected]',
'x-podium-base-font-size': '1rem',
'x-podium-device-type': 'mobile',
'user-agent':
'Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/56.0.2924.87 Mobile Safari/537.36',
accept: 'text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8',
Expand Down Expand Up @@ -236,6 +239,8 @@ tap.test(
t.equal(result.context['podium-mount-origin'], 'http://localhost:3030');
t.equal(result.context['podium-mount-pathname'], '/');
t.equal(result.context['podium-device-type'], 'mobile');
t.equal(result.context['podium-app-id'], '[email protected]');
t.equal(result.context['podium-base-font-size'], '1rem');
t.equal(result.context['podium-locale'], 'en-US');
t.equal(result.context['podium-debug'], 'false');
t.equal(result.context['podium-requested-by'], 'foo');
Expand Down
18 changes: 18 additions & 0 deletions tests/get-device-type.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -147,6 +147,24 @@ tap.test(
},
);

tap.test(
'PodiumContextDeviceTypeParser.parse() - "x-podium-device-type" should override "user-agent"',
(t) => {
const parser = new DeviceType();
const incoming = new HttpIncoming(
Object.assign(REQ, {
headers: {
'x-podium-device-type': 'hybrid-ios',
'user-agent': UA_DESKTOP,
},
}),
);
const result = parser.parse(incoming);
t.equal(result, 'hybrid-ios');
t.end();
},
);

tap.test(
'PodiumContextDeviceTypeParser.parse() - parse a new UA - should not exist in cache pre parsing and should exist in cache post parsing',
(t) => {
Expand Down

0 comments on commit ae178e6

Please sign in to comment.