@applicaster/zapp-react-native-utils 14.0.0-alpha.8419134002 → 14.0.0-alpha.9848043301
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/actionsExecutor/ActionExecutorContext.tsx +1 -1
- package/analyticsUtils/AnalyticsEvents/helper.ts +0 -81
- package/analyticsUtils/AnalyticsEvents/sendOnClickEvent.ts +4 -14
- package/analyticsUtils/__tests__/analyticsUtils.test.js +0 -14
- package/analyticsUtils/events.ts +0 -8
- package/appUtils/accessibilityManager/index.ts +3 -3
- package/arrayUtils/__tests__/isFilledArray.test.ts +1 -1
- package/arrayUtils/index.ts +2 -7
- package/configurationUtils/__tests__/configurationUtils.test.js +31 -0
- package/configurationUtils/index.ts +34 -63
- package/focusManager/FocusManager.ts +6 -4
- package/manifestUtils/{_internals/index.js → _internals.js} +25 -2
- package/manifestUtils/createConfig.js +1 -4
- package/manifestUtils/defaultManifestConfigurations/player.js +200 -1239
- package/manifestUtils/progressBar/__tests__/mobileProgressBar.test.js +30 -0
- package/package.json +2 -2
- package/playerUtils/__tests__/configurationUtils.test.ts +65 -1
- package/playerUtils/configurationGenerator.ts +2572 -0
- package/playerUtils/configurationUtils.ts +44 -0
- package/playerUtils/index.ts +51 -2
- package/playerUtils/useValidatePlayerConfig.tsx +19 -22
- package/reactHooks/feed/useBatchLoading.ts +3 -3
- package/reactHooks/feed/usePipesCacheReset.ts +1 -1
- package/reactHooks/navigation/useIsScreenActive.ts +5 -9
- package/reactHooks/screen/useScreenContext.ts +1 -1
- package/reactHooks/state/__tests__/ZStoreProvider.test.tsx +1 -2
- package/riverComponetsMeasurementProvider/index.tsx +1 -1
- package/services/js2native.ts +0 -1
- package/time/BackgroundTimer.ts +3 -5
- package/utils/index.ts +1 -16
- package/arrayUtils/__tests__/isEmptyArray.test.ts +0 -63
- package/audioPlayerUtils/__tests__/getArtworkImage.test.ts +0 -144
- package/audioPlayerUtils/__tests__/getBackgroundImage.test.ts +0 -72
- package/audioPlayerUtils/__tests__/getImageFromEntry.test.ts +0 -110
- package/audioPlayerUtils/assets/index.ts +0 -2
- package/audioPlayerUtils/index.ts +0 -242
- package/conf/player/__tests__/selectors.test.ts +0 -34
- package/conf/player/selectors.ts +0 -10
- package/configurationUtils/__tests__/getMediaItems.test.ts +0 -65
- package/configurationUtils/__tests__/imageSrcFromMediaItem.test.ts +0 -34
- package/manifestUtils/_internals/getDefaultConfiguration.js +0 -28
- package/playerUtils/__tests__/getPlayerActionButtons.test.ts +0 -54
- package/playerUtils/_internals/__tests__/utils.test.ts +0 -71
- package/playerUtils/_internals/index.ts +0 -1
- package/playerUtils/_internals/utils.ts +0 -31
- package/playerUtils/getPlayerActionButtons.ts +0 -17
|
@@ -1,6 +1,50 @@
|
|
|
1
1
|
import { parseJsonIfNeeded } from "../functionUtils";
|
|
2
2
|
import * as R from "ramda";
|
|
3
3
|
|
|
4
|
+
import { getNativeName as nativeNameUtil } from "../localizationUtils/localeLanguage";
|
|
5
|
+
|
|
6
|
+
export const modifyDefaultConfigValues = (
|
|
7
|
+
configuration: ConfigurationKeys,
|
|
8
|
+
mapping: ConfigValuesMapping
|
|
9
|
+
): DefaultConfiguration => {
|
|
10
|
+
return R.mapObjIndexed((value, key) => {
|
|
11
|
+
const isFieldlessKey = key === "custom_configuration_fields";
|
|
12
|
+
const keyMapping = mapping[key];
|
|
13
|
+
const fields = value?.fields || value;
|
|
14
|
+
|
|
15
|
+
if (!keyMapping) {
|
|
16
|
+
return value;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
const mapper = (obj) => {
|
|
20
|
+
if (obj.fields) {
|
|
21
|
+
return R.mergeLeft({ fields: R.map(mapper)(obj.fields) })(obj);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
return R.mergeLeft(keyMapping?.[obj.key])(obj);
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
const mappedFields = R.map(mapper)(fields);
|
|
28
|
+
|
|
29
|
+
return R.unless(() => isFieldlessKey, R.objOf("fields"))(mappedFields);
|
|
30
|
+
})(configuration);
|
|
31
|
+
};
|
|
32
|
+
|
|
33
|
+
export function nativeName(localeCode) {
|
|
34
|
+
try {
|
|
35
|
+
const {
|
|
36
|
+
getNativeName,
|
|
37
|
+
} = require("@applicaster/zapp-react-native-utils/localizationUtils/localeLanguage");
|
|
38
|
+
|
|
39
|
+
return getNativeName(localeCode);
|
|
40
|
+
} catch (error) {
|
|
41
|
+
// eslint-disable-next-line no-console
|
|
42
|
+
console.warn("Could not load localeLanguage utils from QB", error);
|
|
43
|
+
|
|
44
|
+
return nativeNameUtil(localeCode);
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
|
|
4
48
|
const setTrackType = R.curry(
|
|
5
49
|
(
|
|
6
50
|
type: QuickBrickPlayer.TrackType,
|
package/playerUtils/index.ts
CHANGED
|
@@ -5,8 +5,7 @@ import { isFilledArray } from "@applicaster/zapp-react-native-utils/arrayUtils";
|
|
|
5
5
|
import { isTV } from "@applicaster/zapp-react-native-utils/reactUtils";
|
|
6
6
|
|
|
7
7
|
import { getBoolFromConfigValue } from "../configurationUtils";
|
|
8
|
-
|
|
9
|
-
export { getPlayerActionButtons } from "./getPlayerActionButtons";
|
|
8
|
+
import { Dimensions } from "react-native";
|
|
10
9
|
|
|
11
10
|
/**
|
|
12
11
|
* Gets duration value from player manager, and from extensions
|
|
@@ -97,3 +96,53 @@ export const isAudioItem = (item: Option<ZappEntry>) => {
|
|
|
97
96
|
export const isInlineTV = (screenData) => {
|
|
98
97
|
return isTV() && isFilledArray(screenData?.ui_components);
|
|
99
98
|
};
|
|
99
|
+
|
|
100
|
+
const isPercentage = (value: string | number): boolean => {
|
|
101
|
+
if (typeof value === "string") {
|
|
102
|
+
return value.includes("%");
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
return false;
|
|
106
|
+
};
|
|
107
|
+
|
|
108
|
+
const getPercentageOf = (percent: string, value: number) => {
|
|
109
|
+
const percentageValue = parseFloat(percent.replace("%", ""));
|
|
110
|
+
|
|
111
|
+
if (isNaN(percentageValue)) {
|
|
112
|
+
return value;
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
return (value * percentageValue) / 100;
|
|
116
|
+
};
|
|
117
|
+
|
|
118
|
+
type DimensionsT = {
|
|
119
|
+
width: number | string;
|
|
120
|
+
height: number | string | undefined;
|
|
121
|
+
aspectRatio?: number;
|
|
122
|
+
};
|
|
123
|
+
|
|
124
|
+
export const getTabletWidth = (
|
|
125
|
+
tablet_landscape_sidebar_width,
|
|
126
|
+
dimensions: DimensionsT
|
|
127
|
+
) => {
|
|
128
|
+
const { width: SCREEN_WIDTH } = Dimensions.get("screen");
|
|
129
|
+
|
|
130
|
+
const { width } = dimensions;
|
|
131
|
+
let widthValue = Number(width);
|
|
132
|
+
|
|
133
|
+
if (isPercentage(width)) {
|
|
134
|
+
widthValue = getPercentageOf(width.toString(), SCREEN_WIDTH);
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
const sidebarWidth = Number(tablet_landscape_sidebar_width?.replace("%", ""));
|
|
138
|
+
|
|
139
|
+
if (tablet_landscape_sidebar_width?.includes("%")) {
|
|
140
|
+
return widthValue * (1 - sidebarWidth / 100);
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
if (Number.isNaN(sidebarWidth)) {
|
|
144
|
+
return widthValue * 0.65;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
return widthValue - sidebarWidth;
|
|
148
|
+
};
|
|
@@ -1,37 +1,34 @@
|
|
|
1
1
|
import * as React from "react";
|
|
2
|
+
import * as R from "ramda";
|
|
3
|
+
import generateConfiguration from "./configurationGenerator";
|
|
2
4
|
import { createLogger } from "../logger";
|
|
3
|
-
import { createConfig } from "../manifestUtils/createConfig";
|
|
4
|
-
import { getAllFields, getConfigurationDiff } from "./_internals";
|
|
5
5
|
|
|
6
6
|
export const logger = createLogger({
|
|
7
7
|
category: "useValidatePlayerConfig",
|
|
8
8
|
subsystem: "useValidatePlayerConfig",
|
|
9
9
|
});
|
|
10
10
|
|
|
11
|
-
|
|
12
|
-
const {
|
|
13
|
-
styles,
|
|
14
|
-
general,
|
|
15
|
-
localizations,
|
|
16
|
-
custom_configuration_fields,
|
|
17
|
-
}: DefaultConfiguration = createConfig(
|
|
18
|
-
() => {
|
|
19
|
-
return {};
|
|
20
|
-
},
|
|
21
|
-
{ extend: "player" }
|
|
22
|
-
) as any;
|
|
23
|
-
|
|
24
|
-
const QBPlayerConfigFields = getAllFields(
|
|
25
|
-
styles,
|
|
26
|
-
general,
|
|
27
|
-
localizations,
|
|
28
|
-
custom_configuration_fields
|
|
29
|
-
);
|
|
11
|
+
const configuration = generateConfiguration();
|
|
30
12
|
|
|
31
13
|
export const useValidatePlayerConfig = (config) => {
|
|
32
14
|
React.useEffect(() => {
|
|
33
15
|
try {
|
|
34
|
-
const
|
|
16
|
+
const QBPlayerConfigFields = R.compose(
|
|
17
|
+
R.map(R.prop("key")),
|
|
18
|
+
R.flatten,
|
|
19
|
+
R.map(R.compose(R.when(R.propEq("group", true), R.prop("fields")))),
|
|
20
|
+
R.concat
|
|
21
|
+
)(
|
|
22
|
+
configuration.styles.fields,
|
|
23
|
+
configuration.general.fields,
|
|
24
|
+
configuration.localizations.fields,
|
|
25
|
+
configuration.custom_configuration_fields
|
|
26
|
+
);
|
|
27
|
+
|
|
28
|
+
const diff = R.compose(
|
|
29
|
+
R.difference(QBPlayerConfigFields),
|
|
30
|
+
R.keys
|
|
31
|
+
)(config);
|
|
35
32
|
|
|
36
33
|
logger.log_info(
|
|
37
34
|
"Missing following configuration properties. Some elements of the player may not work correctly. Check QuickBrickPlayerPlugin for the configuration reference https://github.com/applicaster/QuickBrick/tree/main/plugins/zapp-react-native-default-player/manifests",
|
|
@@ -10,7 +10,7 @@ import {
|
|
|
10
10
|
getSearchContext,
|
|
11
11
|
} from "@applicaster/zapp-react-native-utils/reactHooks";
|
|
12
12
|
import { isGallery } from "@applicaster/zapp-react-native-utils/componentsUtils";
|
|
13
|
-
import { useScreenContext } from "../screen";
|
|
13
|
+
import { useScreenContext } from "../screen/useScreenContext";
|
|
14
14
|
|
|
15
15
|
type Options = {
|
|
16
16
|
initialBatchSize?: number;
|
|
@@ -144,11 +144,11 @@ export const useBatchLoading = (
|
|
|
144
144
|
}
|
|
145
145
|
}
|
|
146
146
|
});
|
|
147
|
-
}, [feedUrls
|
|
147
|
+
}, [feedUrls]);
|
|
148
148
|
|
|
149
149
|
React.useEffect(() => {
|
|
150
150
|
runBatchLoading();
|
|
151
|
-
}, [
|
|
151
|
+
}, []);
|
|
152
152
|
|
|
153
153
|
React.useEffect(() => {
|
|
154
154
|
// check if all feeds are ready and set hasEverBeenReady to true
|
|
@@ -5,7 +5,7 @@ import { getDatasourceUrl } from "@applicaster/zapp-react-native-ui-components/D
|
|
|
5
5
|
import { usePipesContexts } from "@applicaster/zapp-react-native-ui-components/Decorators/RiverFeedLoader/utils/usePipesContexts";
|
|
6
6
|
import { clearPipesData } from "@applicaster/zapp-react-native-redux/ZappPipes";
|
|
7
7
|
|
|
8
|
-
import { useRoute } from "../navigation";
|
|
8
|
+
import { useRoute } from "../navigation/useRoute";
|
|
9
9
|
|
|
10
10
|
/**
|
|
11
11
|
* reset river components cache when screen is unmounted
|
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
import { ROUTE_TYPES } from "@applicaster/zapp-react-native-utils/navigationUtils/routeTypes";
|
|
2
1
|
import { useNavigation } from "./useNavigation";
|
|
3
2
|
import { usePathname } from "./usePathname";
|
|
4
3
|
|
|
@@ -7,14 +6,11 @@ export const useIsScreenActive = () => {
|
|
|
7
6
|
const pathname = usePathname();
|
|
8
7
|
const { currentRoute, videoModalState } = useNavigation();
|
|
9
8
|
|
|
10
|
-
if (
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
if (["FULLSCREEN", "MAXIMIZED", "PIP"].includes(videoModalState.mode)) {
|
|
16
|
-
return false;
|
|
17
|
-
}
|
|
9
|
+
if (
|
|
10
|
+
videoModalState.visible &&
|
|
11
|
+
["FULLSCREEN", "MAXIMIZED", "PIP"].includes(videoModalState.mode)
|
|
12
|
+
) {
|
|
13
|
+
return false;
|
|
18
14
|
}
|
|
19
15
|
|
|
20
16
|
return pathname === currentRoute;
|
|
@@ -2,7 +2,7 @@ import { useContext, useMemo } from "react";
|
|
|
2
2
|
|
|
3
3
|
import { useModalNavigationContext } from "@applicaster/zapp-react-native-ui-components/Contexts/ModalNavigationContext";
|
|
4
4
|
import { useNestedNavigationContext } from "@applicaster/zapp-react-native-ui-components/Contexts/NestedNavigationContext";
|
|
5
|
-
import { useNavigation } from "../navigation";
|
|
5
|
+
import { useNavigation } from "../navigation/useNavigation";
|
|
6
6
|
|
|
7
7
|
import { ScreenContext } from "@applicaster/zapp-react-native-ui-components/Contexts/ScreenContext";
|
|
8
8
|
import { ScreenDataContext } from "@applicaster/zapp-react-native-ui-components/Contexts/ScreenDataContext";
|
|
@@ -1,8 +1,7 @@
|
|
|
1
|
-
/* eslint-disable no-console */
|
|
2
1
|
import React from "react";
|
|
3
2
|
import { render, screen } from "@testing-library/react-native";
|
|
4
3
|
import { Text } from "react-native";
|
|
5
|
-
import {
|
|
4
|
+
import { ZStoreProvider, useZStore } from "../ZStoreProvider";
|
|
6
5
|
import { useStore } from "zustand";
|
|
7
6
|
|
|
8
7
|
interface TestState {
|
|
@@ -3,7 +3,7 @@ import { NativeModules, StyleSheet, View } from "react-native";
|
|
|
3
3
|
import { getXray } from "@applicaster/zapp-react-native-utils/logger";
|
|
4
4
|
|
|
5
5
|
import { isApplePlatform, isWeb } from "../reactUtils";
|
|
6
|
-
import { useRivers } from "../reactHooks";
|
|
6
|
+
import { useRivers } from "../reactHooks/state";
|
|
7
7
|
|
|
8
8
|
const layoutReducer = (state, { payload }) => {
|
|
9
9
|
return state.map((item, index, _state) => ({
|
package/services/js2native.ts
CHANGED
|
@@ -496,7 +496,6 @@ async function removeStorageListenerHandler(payload: { listenerId?: string }) {
|
|
|
496
496
|
function log({ level, messages }) {
|
|
497
497
|
try {
|
|
498
498
|
const parsedMessages = parseJsonIfNeeded(messages);
|
|
499
|
-
// eslint-disable-next-line no-console
|
|
500
499
|
const logFn = console[level] || console.log;
|
|
501
500
|
|
|
502
501
|
if (Array.isArray(parsedMessages)) {
|
package/time/BackgroundTimer.ts
CHANGED
|
@@ -13,15 +13,13 @@ class BackgroundTimer {
|
|
|
13
13
|
|
|
14
14
|
const EventEmitter = platformSelect({
|
|
15
15
|
android: DeviceEventEmitter,
|
|
16
|
-
|
|
17
|
-
amazon: DeviceEventEmitter, // probably does not exist and uses android_tv
|
|
16
|
+
ios: undefined,
|
|
18
17
|
default: undefined,
|
|
19
18
|
});
|
|
20
19
|
|
|
21
20
|
EventEmitter?.addListener("BackgroundTimer.timer.fired", (id: number) => {
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
if (callback) {
|
|
21
|
+
if (this.callbacks[id]) {
|
|
22
|
+
const callback = this.callbacks[id];
|
|
25
23
|
delete this.callbacks[id];
|
|
26
24
|
callback();
|
|
27
25
|
}
|
package/utils/index.ts
CHANGED
|
@@ -2,19 +2,4 @@ export { chunk } from "./chunk";
|
|
|
2
2
|
|
|
3
3
|
export { times } from "./times";
|
|
4
4
|
|
|
5
|
-
export {
|
|
6
|
-
cloneDeep as clone,
|
|
7
|
-
flatten,
|
|
8
|
-
drop,
|
|
9
|
-
size,
|
|
10
|
-
isNil,
|
|
11
|
-
isEmpty,
|
|
12
|
-
get,
|
|
13
|
-
has,
|
|
14
|
-
flatMap,
|
|
15
|
-
difference,
|
|
16
|
-
take,
|
|
17
|
-
map,
|
|
18
|
-
trim,
|
|
19
|
-
toString,
|
|
20
|
-
} from "lodash";
|
|
5
|
+
export { cloneDeep as clone, flatten, drop, size, isNil } from "lodash";
|
|
@@ -1,63 +0,0 @@
|
|
|
1
|
-
import { isEmptyArray } from "..";
|
|
2
|
-
|
|
3
|
-
describe("isEmptyArray", () => {
|
|
4
|
-
it("non-empty array is not empty", () => {
|
|
5
|
-
const value = [1, 2, 3];
|
|
6
|
-
|
|
7
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
8
|
-
});
|
|
9
|
-
|
|
10
|
-
it("empty array is empty", () => {
|
|
11
|
-
const value = [];
|
|
12
|
-
|
|
13
|
-
expect(isEmptyArray(value)).toBe(true);
|
|
14
|
-
});
|
|
15
|
-
|
|
16
|
-
it("number is not array", () => {
|
|
17
|
-
const value = 123;
|
|
18
|
-
|
|
19
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
20
|
-
});
|
|
21
|
-
|
|
22
|
-
it("string is not array", () => {
|
|
23
|
-
const value = "vfnjdk";
|
|
24
|
-
|
|
25
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
26
|
-
});
|
|
27
|
-
|
|
28
|
-
it("empty string is not array", () => {
|
|
29
|
-
const value = "";
|
|
30
|
-
|
|
31
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
32
|
-
});
|
|
33
|
-
|
|
34
|
-
it("NaN is not array", () => {
|
|
35
|
-
const value = NaN;
|
|
36
|
-
|
|
37
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
38
|
-
});
|
|
39
|
-
|
|
40
|
-
it("object is not array", () => {
|
|
41
|
-
const value = { test: 1 };
|
|
42
|
-
|
|
43
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
44
|
-
});
|
|
45
|
-
|
|
46
|
-
it("empty object is not array", () => {
|
|
47
|
-
const value = {};
|
|
48
|
-
|
|
49
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
50
|
-
});
|
|
51
|
-
|
|
52
|
-
it("undefined is not array", () => {
|
|
53
|
-
const value = undefined;
|
|
54
|
-
|
|
55
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
56
|
-
});
|
|
57
|
-
|
|
58
|
-
it("null is not array", () => {
|
|
59
|
-
const value = null;
|
|
60
|
-
|
|
61
|
-
expect(isEmptyArray(value)).toBe(false);
|
|
62
|
-
});
|
|
63
|
-
});
|
|
@@ -1,144 +0,0 @@
|
|
|
1
|
-
import { getArtworkImage } from "..";
|
|
2
|
-
import { DEFAULT_IMAGE } from "../assets";
|
|
3
|
-
|
|
4
|
-
describe("getArtworkImage", () => {
|
|
5
|
-
const entryWithImage = {
|
|
6
|
-
media_group: [
|
|
7
|
-
{
|
|
8
|
-
type: "image",
|
|
9
|
-
media_item: [
|
|
10
|
-
{ key: "artwork_key", src: "image_from_entry" },
|
|
11
|
-
{ key: "other_key", src: "other_image" },
|
|
12
|
-
],
|
|
13
|
-
},
|
|
14
|
-
],
|
|
15
|
-
extensions: {
|
|
16
|
-
artwork_key: "artwork_key",
|
|
17
|
-
},
|
|
18
|
-
};
|
|
19
|
-
|
|
20
|
-
const entryWithoutImage = {
|
|
21
|
-
media_group: [
|
|
22
|
-
{
|
|
23
|
-
type: "image",
|
|
24
|
-
media_item: [{ key: "other_key", src: "other_image" }],
|
|
25
|
-
},
|
|
26
|
-
],
|
|
27
|
-
extensions: {
|
|
28
|
-
artwork_key: "artwork_key",
|
|
29
|
-
},
|
|
30
|
-
};
|
|
31
|
-
|
|
32
|
-
const pluginConfigWithImage = {
|
|
33
|
-
artwork_key: "plugin_artwork_key",
|
|
34
|
-
};
|
|
35
|
-
|
|
36
|
-
it("returns image from entry extensions key", () => {
|
|
37
|
-
const result = getArtworkImage({
|
|
38
|
-
key: "artwork_key",
|
|
39
|
-
entry: entryWithImage,
|
|
40
|
-
plugin_configuration: {},
|
|
41
|
-
});
|
|
42
|
-
|
|
43
|
-
expect(result).toBe("image_from_entry");
|
|
44
|
-
});
|
|
45
|
-
|
|
46
|
-
it("returns image from plugin configuration key if not in entry", () => {
|
|
47
|
-
const entryNoMatch = {
|
|
48
|
-
...entryWithoutImage,
|
|
49
|
-
extensions: { artwork_key: "not_found_key" },
|
|
50
|
-
};
|
|
51
|
-
|
|
52
|
-
const pluginConfig = {
|
|
53
|
-
artwork_key: "plugin_artwork_key",
|
|
54
|
-
};
|
|
55
|
-
|
|
56
|
-
const entryWithPluginImage = {
|
|
57
|
-
...entryNoMatch,
|
|
58
|
-
media_group: [
|
|
59
|
-
{
|
|
60
|
-
type: "image",
|
|
61
|
-
media_item: [{ key: "plugin_artwork_key", src: "image_from_plugin" }],
|
|
62
|
-
},
|
|
63
|
-
],
|
|
64
|
-
};
|
|
65
|
-
|
|
66
|
-
const result = getArtworkImage({
|
|
67
|
-
key: "artwork_key",
|
|
68
|
-
entry: entryWithPluginImage,
|
|
69
|
-
plugin_configuration: pluginConfig,
|
|
70
|
-
});
|
|
71
|
-
|
|
72
|
-
expect(result).toBe("image_from_plugin");
|
|
73
|
-
});
|
|
74
|
-
|
|
75
|
-
it("returns DEFAULT_IMAGE if neither entry nor plugin configuration has image", () => {
|
|
76
|
-
const entryNoImage = {
|
|
77
|
-
media_group: [
|
|
78
|
-
{
|
|
79
|
-
type: "image",
|
|
80
|
-
media_item: [{ key: "other_key", src: "other_image" }],
|
|
81
|
-
},
|
|
82
|
-
],
|
|
83
|
-
extensions: { artwork_key: "not_found_key" },
|
|
84
|
-
};
|
|
85
|
-
|
|
86
|
-
const pluginConfig = { artwork_key: "not_found_key" };
|
|
87
|
-
|
|
88
|
-
const result = getArtworkImage({
|
|
89
|
-
key: "artwork_key",
|
|
90
|
-
entry: entryNoImage,
|
|
91
|
-
plugin_configuration: pluginConfig,
|
|
92
|
-
});
|
|
93
|
-
|
|
94
|
-
expect(result).toBe(DEFAULT_IMAGE);
|
|
95
|
-
});
|
|
96
|
-
|
|
97
|
-
it("handles undefined key gracefully", () => {
|
|
98
|
-
const result = getArtworkImage({
|
|
99
|
-
key: undefined,
|
|
100
|
-
entry: entryWithImage,
|
|
101
|
-
plugin_configuration: pluginConfigWithImage,
|
|
102
|
-
});
|
|
103
|
-
|
|
104
|
-
expect(result).toBe(DEFAULT_IMAGE);
|
|
105
|
-
});
|
|
106
|
-
|
|
107
|
-
it("handles missing entry or plugin_configuration gracefully", () => {
|
|
108
|
-
const result = getArtworkImage({
|
|
109
|
-
key: "artwork_key",
|
|
110
|
-
entry: undefined,
|
|
111
|
-
plugin_configuration: undefined,
|
|
112
|
-
});
|
|
113
|
-
|
|
114
|
-
expect(result).toBe(DEFAULT_IMAGE);
|
|
115
|
-
});
|
|
116
|
-
|
|
117
|
-
it("handles empty media_group", () => {
|
|
118
|
-
const entryEmptyMedia = {
|
|
119
|
-
media_group: [],
|
|
120
|
-
extensions: { artwork_key: "artwork_key" },
|
|
121
|
-
};
|
|
122
|
-
|
|
123
|
-
const result = getArtworkImage({
|
|
124
|
-
key: "artwork_key",
|
|
125
|
-
entry: entryEmptyMedia,
|
|
126
|
-
plugin_configuration: pluginConfigWithImage,
|
|
127
|
-
});
|
|
128
|
-
|
|
129
|
-
expect(result).toBe(DEFAULT_IMAGE);
|
|
130
|
-
});
|
|
131
|
-
|
|
132
|
-
it("handles missing extensions/config keys", () => {
|
|
133
|
-
const entryNoExt = { media_group: [], extensions: {} };
|
|
134
|
-
const pluginConfig = {};
|
|
135
|
-
|
|
136
|
-
const result = getArtworkImage({
|
|
137
|
-
key: "artwork_key",
|
|
138
|
-
entry: entryNoExt,
|
|
139
|
-
plugin_configuration: pluginConfig,
|
|
140
|
-
});
|
|
141
|
-
|
|
142
|
-
expect(result).toBe(DEFAULT_IMAGE);
|
|
143
|
-
});
|
|
144
|
-
});
|
|
@@ -1,72 +0,0 @@
|
|
|
1
|
-
import { getBackgroundImage } from "..";
|
|
2
|
-
import { DEFAULT_IMAGE } from "../assets";
|
|
3
|
-
|
|
4
|
-
describe("getBackgroundImage", () => {
|
|
5
|
-
const entryBase = {
|
|
6
|
-
media_group: [
|
|
7
|
-
{
|
|
8
|
-
media_item: [
|
|
9
|
-
{ key: "image_key_1", src: "image_src_1" },
|
|
10
|
-
{ key: "image_key_2", src: "image_src_2" },
|
|
11
|
-
],
|
|
12
|
-
type: "image",
|
|
13
|
-
},
|
|
14
|
-
],
|
|
15
|
-
extensions: {},
|
|
16
|
-
};
|
|
17
|
-
|
|
18
|
-
const pluginConfigBase = {};
|
|
19
|
-
|
|
20
|
-
it("returns image from entry.extensions.image_key if present", () => {
|
|
21
|
-
const entry = {
|
|
22
|
-
...entryBase,
|
|
23
|
-
extensions: { image_key: "image_key_2" },
|
|
24
|
-
};
|
|
25
|
-
|
|
26
|
-
const result = getBackgroundImage({
|
|
27
|
-
entry,
|
|
28
|
-
plugin_configuration: pluginConfigBase,
|
|
29
|
-
});
|
|
30
|
-
|
|
31
|
-
expect(result).toBe("image_src_2");
|
|
32
|
-
});
|
|
33
|
-
|
|
34
|
-
it("returns audio_player_background_image from entry.extensions if present and no image_key image", () => {
|
|
35
|
-
const entry = {
|
|
36
|
-
...entryBase,
|
|
37
|
-
extensions: { audio_player_background_image: "audio_img_ext" },
|
|
38
|
-
};
|
|
39
|
-
|
|
40
|
-
const result = getBackgroundImage({
|
|
41
|
-
entry,
|
|
42
|
-
plugin_configuration: pluginConfigBase,
|
|
43
|
-
});
|
|
44
|
-
|
|
45
|
-
expect(result).toBe("audio_img_ext");
|
|
46
|
-
});
|
|
47
|
-
|
|
48
|
-
it("returns image from plugin_configuration.audio_player_image_key if present and not found in entry.extensions", () => {
|
|
49
|
-
const entry = { ...entryBase };
|
|
50
|
-
const plugin_configuration = { audio_player_image_key: "image_key_1" };
|
|
51
|
-
const result = getBackgroundImage({ entry, plugin_configuration });
|
|
52
|
-
expect(result).toBe("image_src_1");
|
|
53
|
-
});
|
|
54
|
-
|
|
55
|
-
it("returns audio_player_background_image from plugin_configuration if present and not found in entry/extensions", () => {
|
|
56
|
-
const entry = { ...entryBase };
|
|
57
|
-
|
|
58
|
-
const plugin_configuration = {
|
|
59
|
-
audio_player_background_image: "audio_img_conf",
|
|
60
|
-
};
|
|
61
|
-
|
|
62
|
-
const result = getBackgroundImage({ entry, plugin_configuration });
|
|
63
|
-
expect(result).toBe("audio_img_conf");
|
|
64
|
-
});
|
|
65
|
-
|
|
66
|
-
it("returns DEFAULT_IMAGE if nothing is found", () => {
|
|
67
|
-
const entry = { media_group: [], extensions: {} };
|
|
68
|
-
const plugin_configuration = {};
|
|
69
|
-
const result = getBackgroundImage({ entry, plugin_configuration });
|
|
70
|
-
expect(result).toBe(DEFAULT_IMAGE);
|
|
71
|
-
});
|
|
72
|
-
});
|