diff --git a/packages/pwa-kit-react-sdk/CHANGELOG.md b/packages/pwa-kit-react-sdk/CHANGELOG.md
index 2c3b5bd447..186ab005ec 100644
--- a/packages/pwa-kit-react-sdk/CHANGELOG.md
+++ b/packages/pwa-kit-react-sdk/CHANGELOG.md
@@ -1,4 +1,6 @@
## v2.8.0-dev (Mar 03, 2023)
+- Remove usage of `device-context` due to deprecation of user agent string. [#1168](https://github.com/SalesforceCommerceCloud/pwa-kit/pull/1168)
+
## v2.7.0 (Mar 03, 2023)
## v2.6.0 (Jan 25, 2023)
diff --git a/packages/pwa-kit-react-sdk/src/ssr/browser/main.jsx b/packages/pwa-kit-react-sdk/src/ssr/browser/main.jsx
index bdcd7dcc28..ac650475cd 100644
--- a/packages/pwa-kit-react-sdk/src/ssr/browser/main.jsx
+++ b/packages/pwa-kit-react-sdk/src/ssr/browser/main.jsx
@@ -8,7 +8,6 @@
import React, {useRef} from 'react'
import ReactDOM from 'react-dom'
import {BrowserRouter as Router} from 'react-router-dom'
-import DeviceContext from '../universal/device-context'
import {ServerContext, CorrelationIdProvider} from '../universal/contexts'
import App from '../universal/components/_app'
import {getAppConfig} from '../universal/compatibility'
@@ -52,16 +51,14 @@ export const OuterApp = ({routes, error, WrappedApp, locals}) => {
return uuidv4()
}}
>
-
-
-
-
-
+
+
+
diff --git a/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.js b/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.js
index 993f2582d2..fec94fbc00 100644
--- a/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.js
+++ b/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.js
@@ -18,7 +18,6 @@ import {StaticRouter as Router, matchPath} from 'react-router-dom'
import serialize from 'serialize-javascript'
import {getAssetUrl} from '../universal/utils'
-import DeviceContext from '../universal/device-context'
import {ServerContext, CorrelationIdProvider} from '../universal/contexts'
import Document from '../universal/components/_document'
@@ -29,7 +28,7 @@ import {getAppConfig} from '../universal/compatibility'
import Switch from '../universal/components/switch'
import {getRoutes, routeComponent} from '../universal/components/route-component'
import * as errors from '../universal/errors'
-import {detectDeviceType, isRemote} from 'pwa-kit-runtime/utils/ssr-server'
+import {isRemote} from 'pwa-kit-runtime/utils/ssr-server'
import {proxyConfigs} from 'pwa-kit-runtime/utils/ssr-shared'
import {getConfig} from 'pwa-kit-runtime/utils/ssr-config'
import sprite from 'svg-sprite-loader/runtime/sprite.build'
@@ -116,7 +115,6 @@ export const render = async (req, res, next) => {
const component = await route.component.getComponent()
// Step 3 - Init the app state
- const deviceType = detectDeviceType(req)
const props = {
error: null,
appState: {},
@@ -125,8 +123,7 @@ export const render = async (req, res, next) => {
res,
App: WrappedApp,
routes,
- location,
- deviceType
+ location
}
let appJSX =
@@ -167,8 +164,7 @@ export const render = async (req, res, next) => {
res,
location,
config,
- appJSX,
- deviceType
+ appJSX
})
} catch (e) {
// This is an unrecoverable error.
@@ -192,17 +188,7 @@ export const render = async (req, res, next) => {
}
}
-const OuterApp = ({
- req,
- res,
- error,
- App,
- appState,
- routes,
- routerContext,
- location,
- deviceType
-}) => {
+const OuterApp = ({req, res, error, App, appState, routes, routerContext, location}) => {
const AppConfig = getAppConfig()
return (
@@ -211,11 +197,9 @@ const OuterApp = ({
correlationId={res.locals.requestId}
resetOnPageChange={false}
>
-
-
-
-
-
+
+
+
@@ -230,15 +214,14 @@ OuterApp.propTypes = {
appState: PropTypes.object,
routes: PropTypes.array,
routerContext: PropTypes.object,
- location: PropTypes.object,
- deviceType: PropTypes.string
+ location: PropTypes.object
}
const renderToString = (jsx, extractor) =>
ReactDOMServer.renderToString(extractor.collectChunks(jsx))
const renderApp = (args) => {
- const {req, res, appStateError, appJSX, appState, config, deviceType} = args
+ const {req, res, appStateError, appJSX, appState, config} = args
const extractor = new ChunkExtractor({statsFile: BUNDLES_PATH, publicPath: getAssetUrl()})
const ssrOnly = 'mobify_server_only' in req.query || '__server_only' in req.query
@@ -300,7 +283,6 @@ const renderApp = (args) => {
const windowGlobals = {
__INITIAL_CORRELATION_ID__: res.locals.requestId,
__CONFIG__: config,
- __DEVICE_TYPE__: deviceType,
__PRELOADED_STATE__: appState,
__ERROR__: error,
// `window.Progressive` has a long history at Mobify and some
diff --git a/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.test.js b/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.test.js
index 1f7857641d..b6f7481750 100644
--- a/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.test.js
+++ b/packages/pwa-kit-react-sdk/src/ssr/server/react-rendering.test.js
@@ -39,11 +39,6 @@ const opts = (overrides = {}) => {
}
}
-const mobile =
- 'Mozilla/5.0 (iPhone; U; CPU like Mac OS X; en) AppleWebKit/420+ (KHTML, like Gecko) Version/3.0 Mobile/1A543 Safari/419.3'
-const tablet =
- 'Mozilla/5.0 (iPad; CPU OS 6_1 like Mac OS X) AppleWebKit/536.26 (KHTML, like Gecko) Version/6.0 Mobile/10B141 Safari/8536.25'
-
jest.mock('../universal/compatibility', () => {
const AppConfig = jest.requireActual('../universal/components/_app-config').default
const {withReactQuery} = jest.requireActual('../universal/components/with-react-query')
@@ -433,10 +428,8 @@ describe('The Node SSR Environment', () => {
console.error(html)
const doc = parse(html)
const include = ['
This is a PWA
']
- const data = dataFromHTML(doc)
const dataScript = doc.querySelectorAll('script[id=mobify-data]')[0]
expect(dataScript.innerHTML.split(/\r\n|\r|\n/)).toHaveLength(1)
- expect(data.__DEVICE_TYPE__).toBe('DESKTOP')
include.forEach((s) => expect(html).toEqual(expect.stringContaining(s)))
expect(scriptsAreSafe(doc)).toBe(true)
}
@@ -444,17 +437,12 @@ describe('The Node SSR Environment', () => {
{
description: `rendering PWA's for tablet`,
req: {
- url: '/pwa/',
- headers: {
- 'User-Agent': tablet
- }
+ url: '/pwa/'
},
assertions: (res) => {
expect(res.statusCode).toBe(200)
const html = res.text
const doc = parse(html)
- const data = dataFromHTML(doc)
- expect(data.__DEVICE_TYPE__).toBe('TABLET')
const include = ['This is a PWA
']
include.forEach((s) => expect(html).toEqual(expect.stringContaining(s)))
expect(scriptsAreSafe(doc)).toBe(true)
@@ -463,17 +451,12 @@ describe('The Node SSR Environment', () => {
{
description: `rendering PWA's for mobile`,
req: {
- url: '/pwa/',
- headers: {
- 'User-Agent': mobile
- }
+ url: '/pwa/'
},
assertions: (res) => {
expect(res.statusCode).toBe(200)
const html = res.text
const doc = parse(html)
- const data = dataFromHTML(doc)
- expect(data.__DEVICE_TYPE__).toBe('PHONE')
const include = ['This is a PWA
']
include.forEach((s) => expect(html).toEqual(expect.stringContaining(s)))
expect(scriptsAreSafe(doc)).toBe(true)
diff --git a/packages/pwa-kit-react-sdk/src/ssr/universal/device-context.js b/packages/pwa-kit-react-sdk/src/ssr/universal/device-context.js
deleted file mode 100644
index dcece9703c..0000000000
--- a/packages/pwa-kit-react-sdk/src/ssr/universal/device-context.js
+++ /dev/null
@@ -1,9 +0,0 @@
-/*
- * Copyright (c) 2022, Salesforce, Inc.
- * All rights reserved.
- * SPDX-License-Identifier: BSD-3-Clause
- * For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/BSD-3-Clause
- */
-
-import React from 'react'
-export default React.createContext()
diff --git a/packages/pwa-kit-runtime/CHANGELOG.md b/packages/pwa-kit-runtime/CHANGELOG.md
index c2a118f456..01ff6e094b 100644
--- a/packages/pwa-kit-runtime/CHANGELOG.md
+++ b/packages/pwa-kit-runtime/CHANGELOG.md
@@ -1,5 +1,7 @@
## v2.8.0-dev (Mar 03, 2023)
- Add optional parameter to override configuration folder used in `getConfig` [#1049](https://github.com/SalesforceCommerceCloud/pwa-kit/pull/1049)
+- Remove usage of `detect-device-type` due to deprecation of user agent string. [#1168](https://github.com/SalesforceCommerceCloud/pwa-kit/pull/1168)
+
## v2.7.0 (Mar 03, 2023)
- Support Node 16 [#965](https://github.com/SalesforceCommerceCloud/pwa-kit/pull/965)
diff --git a/packages/pwa-kit-runtime/package-lock.json b/packages/pwa-kit-runtime/package-lock.json
index 0e40c7097b..1cfc065482 100644
--- a/packages/pwa-kit-runtime/package-lock.json
+++ b/packages/pwa-kit-runtime/package-lock.json
@@ -21,7 +21,6 @@
"morgan": "^1.10.0",
"semver": "^7.3.8",
"set-cookie-parser": "^2.6.0",
- "ua-parser-js": "^1.0.34",
"whatwg-encoding": "^1.0.5"
},
"devDependencies": {
@@ -2816,24 +2815,6 @@
"node": ">= 0.6"
}
},
- "node_modules/ua-parser-js": {
- "version": "1.0.35",
- "resolved": "https://registry.npmjs.org/ua-parser-js/-/ua-parser-js-1.0.35.tgz",
- "integrity": "sha512-fKnGuqmTBnIE+/KXSzCn4db8RTigUzw1AN0DmdU6hJovUTbYJKyqj+8Mt1c4VfRDnOVJnENmfYkIPZ946UrSAA==",
- "funding": [
- {
- "type": "opencollective",
- "url": "https://opencollective.com/ua-parser-js"
- },
- {
- "type": "paypal",
- "url": "https://paypal.me/faisalman"
- }
- ],
- "engines": {
- "node": "*"
- }
- },
"node_modules/undefsafe": {
"version": "2.0.5",
"resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.5.tgz",
@@ -5128,11 +5109,6 @@
"mime-types": "~2.1.24"
}
},
- "ua-parser-js": {
- "version": "1.0.35",
- "resolved": "https://registry.npmjs.org/ua-parser-js/-/ua-parser-js-1.0.35.tgz",
- "integrity": "sha512-fKnGuqmTBnIE+/KXSzCn4db8RTigUzw1AN0DmdU6hJovUTbYJKyqj+8Mt1c4VfRDnOVJnENmfYkIPZ946UrSAA=="
- },
"undefsafe": {
"version": "2.0.5",
"resolved": "https://registry.npmjs.org/undefsafe/-/undefsafe-2.0.5.tgz",
diff --git a/packages/pwa-kit-runtime/package.json b/packages/pwa-kit-runtime/package.json
index a1d3606fe9..b1e67e8e3c 100644
--- a/packages/pwa-kit-runtime/package.json
+++ b/packages/pwa-kit-runtime/package.json
@@ -42,7 +42,6 @@
"morgan": "^1.10.0",
"semver": "^7.3.8",
"set-cookie-parser": "^2.6.0",
- "ua-parser-js": "^1.0.34",
"whatwg-encoding": "^1.0.5"
},
"devDependencies": {
diff --git a/packages/pwa-kit-runtime/src/ssr/server/express.js b/packages/pwa-kit-runtime/src/ssr/server/express.js
index fe70ace375..414e50c69d 100644
--- a/packages/pwa-kit-runtime/src/ssr/server/express.js
+++ b/packages/pwa-kit-runtime/src/ssr/server/express.js
@@ -17,8 +17,7 @@ import {
parseCacheControl,
parseEndParameters,
isRemote,
- wrapResponseWrite,
- detectDeviceType
+ wrapResponseWrite
} from '../../utils/ssr-server'
import {CONTENT_ENCODING, X_MOBIFY_FROM_CACHE} from './constants'
import {X_MOBIFY_REQUEST_CLASS} from '../../utils/ssr-proxying'
@@ -53,18 +52,6 @@ export const RESOLVED_PROMISE = Promise.resolve()
* appropriate to include these, the caller should add their values
* (or values based on them) to the options.extras array.
*
- * Requests that come to a deployed Express app contain headers that
- * identify the device type. By default, this method generates different
- * cache keys for different device types (effectively, the values of the
- * headers used by getBrowserSize are included in 'options.extras'). To
- * suppress this, pass true for options.ignoreDeviceType
- * Note: CloudFront will pass 4 device type headers, and ALL of them will
- * be present in the request headers, they are 'CloudFront-Is-Desktop-Viewer',
- * 'CloudFront-Is-Mobile-Viewer', 'CloudFront-Is-SmartTV-Viewer' and
- * 'CloudFront-Is-Tablet-Viewer'. The values can be 'true' or 'false', and it
- * is possible that a device falls into more than one device type category
- * and multiple device type headers can be 'true' at the same time.
- *
* By default, method will generate different cache keys for requests with
* different request classes (effectively, the value of the request-class
* string is included in 'extras'). To suppress this, pass true for
@@ -74,8 +61,6 @@ export const RESOLVED_PROMISE = Promise.resolve()
* @param [options] {Object} values that affect the cache key generation.
* @param [options.extras] {Array} extra string values
* to be included in the key.
- * @param [options.ignoreDeviceType] {Boolean} set this to true to suppress
- * automatic variation of the key by device type.
* @param [options.ignoreRequestClass] {Boolean} set this to true to suppress
* automatic variation of the key by request class.
* @returns {String} the generated key.
@@ -99,10 +84,6 @@ export const generateCacheKey = (req, options = {}) => {
elements.push(...filteredQueryStrings)
}
- if (!options.ignoreDeviceType) {
- elements.push(`device=${detectDeviceType(req)}`)
- }
-
if (!options.ignoreRequestClass) {
const requestClass = req.get(X_MOBIFY_REQUEST_CLASS)
if (requestClass) {
diff --git a/packages/pwa-kit-runtime/src/ssr/server/express.test.js b/packages/pwa-kit-runtime/src/ssr/server/express.test.js
index 4cd547c699..d93f5bf9af 100644
--- a/packages/pwa-kit-runtime/src/ssr/server/express.test.js
+++ b/packages/pwa-kit-runtime/src/ssr/server/express.test.js
@@ -878,52 +878,6 @@ describe('generateCacheKey', () => {
expect(generateCacheKey(mockRequest({url: '/test3?a=2'}))).not.toEqual(result1)
})
- test('user agent affects key', () => {
- const result1 = generateCacheKey(mockRequest())
- const request2 = mockRequest({
- headers: {
- 'user-agent':
- 'Mozilla/5.0 (iPhone; CPU iPhone OS 11_0 like Mac OS X) AppleWebKit/604.1.38 (KHTML, like Gecko) Version/11.0 Mobile/15A372 Safari/604.1'
- }
- })
- expect(generateCacheKey(request2)).not.toEqual(result1)
- // query string and device type is hashed
- expect(generateCacheKey(request2)).toBe(
- `/test/${getHashForString(['a=1', 'device=PHONE'].join('-'))}`
- )
- })
-
- test('CloudFront device headers affect key', () => {
- const result1 = generateCacheKey(mockRequest())
- const request2 = mockRequest({
- headers: {
- 'CloudFront-Is-Desktop-Viewer': 'false',
- 'CloudFront-Is-Mobile-Viewer': 'true',
- 'CloudFront-Is-SmartTV-Viewer': 'false',
- 'CloudFront-Is-Tablet-Viewer': 'false'
- }
- })
- expect(generateCacheKey(request2)).not.toEqual(result1)
- expect(generateCacheKey(request2)).toBe(
- `/test/${getHashForString(['a=1', 'device=PHONE'].join('-'))}`
- )
- })
-
- test('multiple CloudFront device headers affect key', () => {
- const request1 = mockRequest({
- headers: {
- 'CloudFront-Is-Desktop-Viewer': 'false',
- 'CloudFront-Is-Mobile-Viewer': 'true',
- 'CloudFront-Is-SmartTV-Viewer': 'false',
- 'CloudFront-Is-Tablet-Viewer': 'true'
- }
- })
-
- expect(generateCacheKey(request1)).toBe(
- `/test/${getHashForString(['a=1', 'device=TABLET'].join('-'))}`
- )
- })
-
test('request class affects key', () => {
const result1 = generateCacheKey(mockRequest())
const request2 = mockRequest({
diff --git a/packages/pwa-kit-runtime/src/utils/ssr-server.js b/packages/pwa-kit-runtime/src/utils/ssr-server.js
index b7302194fd..f7e7337cd2 100644
--- a/packages/pwa-kit-runtime/src/utils/ssr-server.js
+++ b/packages/pwa-kit-runtime/src/utils/ssr-server.js
@@ -12,7 +12,6 @@
// This file is kept for backwards compatibility / simpler imports.
export * from './ssr-server/cached-response'
export * from './ssr-server/configure-proxy'
-export * from './ssr-server/detect-device-type'
export * from './ssr-server/metrics-sender'
export * from './ssr-server/outgoing-request-hook'
export * from './ssr-server/parse-end-parameters'
diff --git a/packages/pwa-kit-runtime/src/utils/ssr-server.test.js b/packages/pwa-kit-runtime/src/utils/ssr-server.test.js
index 8c7155366d..31eb70492b 100644
--- a/packages/pwa-kit-runtime/src/utils/ssr-server.test.js
+++ b/packages/pwa-kit-runtime/src/utils/ssr-server.test.js
@@ -26,11 +26,7 @@ import {
processExpressResponse,
processLambdaResponse,
updateGlobalAgentOptions,
- wrapResponseWrite,
- detectDeviceType,
- DESKTOP,
- PHONE,
- TABLET
+ wrapResponseWrite
} from './ssr-server'
import {
@@ -72,47 +68,6 @@ const baseMobify = {
}
}
-const userAgents = {
- phone: {
- iphone5orSE:
- 'Mozilla/5.0 (iPhone; CPU iPhone OS 10_3_1 like Mac OS X) AppleWebKit/603.1.30 (KHTML, like Gecko) Version/10.0 Mobile/14E304 Safari/602.1',
- iphone6or7or8:
- 'Mozilla/5.0 (iPhone; CPU iPhone OS 11_0 like Mac OS X) AppleWebKit/604.1.38 (KHTML, like Gecko) Version/11.0 Mobile/15A372 Safari/604.1',
- iphone6or7or8plus:
- 'Mozilla/5.0 (iPhone; CPU iPhone OS 11_0 like Mac OS X) AppleWebKit/604.1.38 (KHTML, like Gecko) Version/11.0 Mobile/15A372 Safari/604.1',
- iphoneX:
- 'Mozilla/5.0 (iPhone; CPU iPhone OS 11_0 like Mac OS X) AppleWebKit/604.1.38 (KHTML, like Gecko) Version/11.0 Mobile/15A372 Safari/604.1',
- nexus4: 'Mozilla/5.0 (Linux; Android 4.4.2; Nexus 4 Build/KOT49H) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Mobile Safari/537.36',
- nexus5: 'Mozilla/5.0 (Linux; Android 6.0; Nexus 5 Build/MRA58N) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Mobile Safari/537.36',
- nexus6: 'Mozilla/5.0 (Linux; Android 7.1.1; Nexus 6 Build/N6F26U) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Mobile Safari/537.36',
- galaxyS5:
- 'Mozilla/5.0 (Linux; Android 5.0; SM-G900P Build/LRX21T) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Mobile Safari/537.36',
- pixel2: 'Mozilla/5.0 (Linux; Android 8.0; Pixel 2 Build/OPD3.170816.012) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Mobile Safari/537.36',
- pixel2XL:
- 'Mozilla/5.0 (Linux; Android 8.0.0; Pixel 2 XL Build/OPD1.170816.004) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Mobile Safari/537.36'
- },
- tablet: {
- nexus7: 'Mozilla/5.0 (Linux; Android 6.0.1; Nexus 7 Build/MOB30X) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Safari/537.36',
- nexus10:
- 'Mozilla/5.0 (Linux; Android 6.0.1; Nexus 10 Build/MOB31T) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Safari/537.36',
- ipad: 'Mozilla/5.0 (iPad; CPU OS 11_0 like Mac OS X) AppleWebKit/604.1.34 (KHTML, like Gecko) Version/11.0 Mobile/15A5341f Safari/604.1',
- ipadAir:
- 'Mozilla/5.0 (iPad; CPU OS 11_4 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/11.0 Mobile/15E148 Safari/604.1',
- ipadPro:
- 'Mozilla/5.0 (iPad; CPU OS 11_0 like Mac OS X) AppleWebKit/604.1.34 (KHTML, like Gecko) Version/11.0 Mobile/15A5341f Safari/604.1'
- },
- desktop: {
- chrome72:
- 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3598.0 Safari/537.36',
- firefox63:
- 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10.13; rv:63.0) Gecko/20100101 Firefox/63.0',
- safari11:
- 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_13_6) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/11.1.2 Safari/605.1.15',
- edge17: 'Mozilla/5.0 (Windows NT 10.0; WebView/3.0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/64.0.3282.140 Safari/537.36 Edge/17.17134',
- ie11: 'Mozilla/5.0 (Windows NT 6.3; Trident/7.0; rv:11.0) like Gecko'
- }
-}
-
let consoleLog
let consoleWarn
let consoleError
@@ -367,74 +322,6 @@ describe('utils/ssr-server tests', () => {
})
)
})
-
- describe('detectDeviceType', () => {
- const tests = [
- // Test all mobile user agents
- ...Object.keys(userAgents.phone).map((key) => ({
- name: `test for user agent key ${key}`,
- headers: {'user-agent': userAgents.phone[key]},
- expected: PHONE
- })),
-
- // Test all tablet user agents
- ...Object.keys(userAgents.tablet).map((key) => ({
- name: `test for user agent key ${key}`,
- headers: {'user-agent': userAgents.tablet[key]},
- expected: TABLET
- })),
-
- // Test all desktop user agents
- ...Object.keys(userAgents.desktop).map((key) => ({
- name: `test for user agent key ${key}`,
- headers: {'user-agent': userAgents.desktop[key]},
- expected: DESKTOP
- })),
- {
- name: 'iphone CloudFront header',
- headers: {
- 'CloudFront-Is-Mobile-Viewer': 'true'
- },
- expected: PHONE
- },
- {
- name: 'ipad CloudFront header',
- headers: {
- 'CloudFront-Is-Mobile-Viewer': 'true', // Tablets are also mobile devices
- 'CloudFront-Is-Tablet-Viewer': 'true'
- },
- expected: TABLET
- },
- {
- name: 'desktop CloudFront header',
- headers: {
- 'CloudFront-Is-Desktop-Viewer': 'true'
- },
- expected: DESKTOP
- }
- ]
-
- tests.forEach((testConfig) => {
- test(`detectDeviceTypes (${testConfig.name})`, () => {
- const req = {
- get: (key) => testConfig.headers[key],
- query: {}
- }
- expect(detectDeviceType(req)).toEqual(testConfig.expected)
- })
- })
-
- test('should allow users to force a device type, using the "mobify_devicetype" query param', () => {
- const headers = {'user-agent': userAgents.phone.iphoneX}
- const req = {
- get: (key) => headers[key],
- query: {
- mobify_devicetype: TABLET
- }
- }
- expect(detectDeviceType(req)).toEqual(TABLET)
- })
- })
})
describe('utils/ssr-shared tests', () => {
diff --git a/packages/pwa-kit-runtime/src/utils/ssr-server/detect-device-type.js b/packages/pwa-kit-runtime/src/utils/ssr-server/detect-device-type.js
deleted file mode 100644
index 230a1449f4..0000000000
--- a/packages/pwa-kit-runtime/src/utils/ssr-server/detect-device-type.js
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright (c) 2022, Salesforce, Inc.
- * All rights reserved.
- * SPDX-License-Identifier: BSD-3-Clause
- * For full license text, see the LICENSE file in the repo root or https://opensource.org/licenses/BSD-3-Clause
- */
-import UserAgentParser from 'ua-parser-js'
-
-const MOBIFY_DEVICETYPE = 'mobify_devicetype'
-
-export const DESKTOP = 'DESKTOP'
-export const PHONE = 'PHONE'
-export const TABLET = 'TABLET'
-
-export const detectDeviceType = (request) => {
- const forced = request.query[MOBIFY_DEVICETYPE]
- if (forced && [DESKTOP, PHONE, TABLET].includes(forced.toUpperCase())) {
- return forced
- }
-
- const cfMobile = `CloudFront-Is-${'Mobile'}-Viewer`
- const cfTablet = `CloudFront-Is-${'Tablet'}-Viewer`
- const cfDesktop = `CloudFront-Is-${'Desktop'}-Viewer`
-
- const useCloudfront = [cfMobile, cfTablet, cfDesktop].some(
- (header) => request.get(header) !== undefined
- )
-
- if (useCloudfront) {
- // CloudFront takes precedence, if any header was set.
- if (request.get(cfTablet) === 'true') {
- return TABLET
- } else if (request.get(cfMobile) === 'true') {
- return PHONE
- } else {
- return DESKTOP
- }
- } else {
- // Fall back to user-agent
- const device = new UserAgentParser(request.get('user-agent')).getDevice()
- const type = device && device.type
- switch (type) {
- case 'mobile':
- return PHONE
- case 'tablet':
- return TABLET
- default:
- return DESKTOP
- }
- }
-}