Skip to content

Commit f71a0d7

Browse files
committed
Merge branch 'release-candidate' into release
2 parents a5b699f + 33ce641 commit f71a0d7

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

42 files changed

+302
-181
lines changed

CHANGELOG.md

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,19 @@
1+
## [6.6.0](https://github.com/jwplayer/ott-web-app/compare/v6.5.0...v6.6.0) (2024-09-06)
2+
3+
4+
### Features
5+
6+
* **project:** add injectable wrapper to common components ([#598](https://github.com/jwplayer/ott-web-app/issues/598)) ([a6ad0d8](https://github.com/jwplayer/ott-web-app/commit/a6ad0d88b0e7cdc36548867870c8eb3c014f1ad2))
7+
* **project:** app metadata insertion ([3753a9c](https://github.com/jwplayer/ott-web-app/commit/3753a9c352289620af6ec597fb5f474d7b8ac6d4))
8+
* **project:** remove free and productIds from content-types.json ([#605](https://github.com/jwplayer/ott-web-app/issues/605)) ([2268447](https://github.com/jwplayer/ott-web-app/commit/226844726061184252af24fabc8340e8539230b6))
9+
10+
11+
### Bug Fixes
12+
13+
* **e2e:** fix tests after cleeng api update ([#606](https://github.com/jwplayer/ott-web-app/issues/606)) ([9062dba](https://github.com/jwplayer/ott-web-app/commit/9062dba9184561b5af399e25632f4fe132960223))
14+
* **search:** override search query cache ([#594](https://github.com/jwplayer/ott-web-app/issues/594)) ([1c25ad2](https://github.com/jwplayer/ott-web-app/commit/1c25ad2cd2ecfc1d388e5f8094006f7d961c93a0))
15+
* wrong protocol and url path ([#588](https://github.com/jwplayer/ott-web-app/issues/588)) ([de75eb7](https://github.com/jwplayer/ott-web-app/commit/de75eb7eaca51d4fef9be4a40f13d043437bf3f0))
16+
117
## [6.5.0](https://github.com/jwplayer/ott-web-app/compare/v6.4.0...v6.5.0) (2024-07-25)
218

319

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@jwp/ott",
3-
"version": "6.5.0",
3+
"version": "6.6.0",
44
"private": true,
55
"license": "Apache-2.0",
66
"repository": "https://github.com/jwplayer/ott-web-app.git",

packages/common/src/controllers/CheckoutController.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ import { useCheckoutStore } from '../stores/CheckoutStore';
2727
import { useAccountStore } from '../stores/AccountStore';
2828
import { FormValidationError } from '../errors/FormValidationError';
2929
import { determineSwitchDirection } from '../utils/subscription';
30+
import { findDefaultCardMethodId } from '../utils/payments';
3031

3132
@injectable()
3233
export default class CheckoutController {
@@ -70,7 +71,7 @@ export default class CheckoutController {
7071
const { customer } = getAccountInfo();
7172

7273
const paymentMethods = await this.getPaymentMethods();
73-
const paymentMethodId = paymentMethods[0]?.id;
74+
const paymentMethodId = parseInt(findDefaultCardMethodId(paymentMethods));
7475

7576
const createOrderArgs: CreateOrderArgs = {
7677
offer,

packages/common/src/services/ApiService.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -28,14 +28,14 @@ export default class ApiService {
2828
* We use playlistLabel prop to define the label used for all media items inside.
2929
* That way we can change the behavior of the same media items being in different playlists
3030
*/
31-
private generateAlternateImageURL = ({ mediaId, label, playlistLabel }: { mediaId: string; label: string; playlistLabel?: string }) => {
31+
protected generateAlternateImageURL = ({ mediaId, label, playlistLabel }: { mediaId: string; label: string; playlistLabel?: string }) => {
3232
const pathname = `/v2/media/${mediaId}/images/${playlistLabel || label}.webp`;
3333
const url = createURL(`${env.APP_API_BASE_URL}${pathname}`, { poster_fallback: 1, fallback: playlistLabel ? label : null });
3434

3535
return url;
3636
};
3737

38-
private parseDate = (item: PlaylistItem, prop: string) => {
38+
protected parseDate = (item: PlaylistItem, prop: string) => {
3939
const date = item[prop] as string | undefined;
4040

4141
if (date && !isValid(new Date(date))) {
@@ -49,7 +49,7 @@ export default class ApiService {
4949
/**
5050
* Transform incoming content lists
5151
*/
52-
private transformContentList = (contentList: ContentList): Playlist => {
52+
protected transformContentList = (contentList: ContentList): Playlist => {
5353
const { list, ...rest } = contentList;
5454

5555
const playlist: Playlist = { ...rest, playlist: [] };
@@ -80,7 +80,7 @@ export default class ApiService {
8080
/**
8181
* Transform incoming playlists
8282
*/
83-
private transformPlaylist = (playlist: Playlist, relatedMediaId?: string) => {
83+
protected transformPlaylist = (playlist: Playlist, relatedMediaId?: string) => {
8484
playlist.playlist = playlist.playlist.map((item) => this.transformMediaItem(item, playlist));
8585

8686
// remove the related media item (when this is a recommendations playlist)

packages/common/src/services/ConfigService.ts

Lines changed: 3 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -7,18 +7,16 @@ import { AppError } from '../utils/error';
77
import type { Config } from '../../types/config';
88
import env from '../env';
99

10-
import ApiService from './ApiService';
11-
1210
/**
1311
* Set config setup changes in both config.service.ts and config.d.ts
1412
* */
1513

1614
@injectable()
1715
export default class ConfigService {
18-
private CONFIG_HOST = env.APP_API_BASE_URL;
16+
protected CONFIG_HOST = env.APP_API_BASE_URL;
1917
// Explicitly set default config here as a local variable,
2018
// otherwise if it's a module level const, the merge below causes changes to nested properties
21-
private DEFAULT_CONFIG: Config = {
19+
protected DEFAULT_CONFIG: Config = {
2220
id: '',
2321
siteName: '',
2422
description: '',
@@ -35,13 +33,7 @@ export default class ConfigService {
3533
features: {},
3634
};
3735

38-
private readonly apiService: ApiService;
39-
40-
constructor(apiService: ApiService) {
41-
this.apiService = apiService;
42-
}
43-
44-
private enrichConfig = (config: Config): Config => {
36+
protected enrichConfig = (config: Config): Config => {
4537
const { content, siteName } = config;
4638
const updatedContent = content.map((content) => Object.assign({ featured: false }, content));
4739

@@ -70,10 +62,6 @@ export default class ConfigService {
7062
return source;
7163
};
7264

73-
loadAdSchedule = async (adScheduleId: string | undefined | null) => {
74-
return this.apiService.getAdSchedule(adScheduleId);
75-
};
76-
7765
loadConfig = async (configLocation: string | undefined) => {
7866
const i18n = getI18n();
7967

packages/common/src/services/FavoriteService.ts

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -23,31 +23,35 @@ const schema = array(
2323
export default class FavoriteService {
2424
private PERSIST_KEY_FAVORITES = 'favorites';
2525

26-
private readonly apiService;
27-
private readonly storageService;
28-
private readonly accountService;
29-
30-
constructor(@inject(INTEGRATION_TYPE) integrationType: string, apiService: ApiService, storageService: StorageService) {
26+
protected readonly apiService;
27+
protected readonly storageService;
28+
protected readonly accountService;
29+
30+
constructor(
31+
@inject(INTEGRATION_TYPE) integrationType: string,
32+
@inject(ApiService) apiService: ApiService,
33+
@inject(StorageService) storageService: StorageService,
34+
) {
3135
this.apiService = apiService;
3236
this.storageService = storageService;
3337
this.accountService = getNamedModule(AccountService, integrationType, false);
3438
}
3539

36-
private validateFavorites(favorites: unknown) {
40+
protected validateFavorites(favorites: unknown) {
3741
if (favorites && schema.validateSync(favorites)) {
3842
return favorites as SerializedFavorite[];
3943
}
4044

4145
return [];
4246
}
4347

44-
private async getFavoritesFromAccount(user: Customer) {
48+
protected async getFavoritesFromAccount(user: Customer) {
4549
const favorites = await this.accountService?.getFavorites({ user });
4650

4751
return this.validateFavorites(favorites);
4852
}
4953

50-
private async getFavoritesFromStorage() {
54+
protected async getFavoritesFromStorage() {
5155
const favorites = await this.storageService.getItem(this.PERSIST_KEY_FAVORITES, true);
5256

5357
return this.validateFavorites(favorites);

packages/common/src/services/GenericEntitlementService.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import type { GetTokenResponse } from '../../types/entitlement';
55

66
@injectable()
77
export default class GenericEntitlementService {
8-
private getToken = async <T>(url: string, body: unknown = {}, jwt?: string): Promise<T> => {
8+
protected getToken = async <T>(url: string, body: unknown = {}, jwt?: string): Promise<T> => {
99
const response = await fetch(url, {
1010
method: 'POST',
1111
headers: {

packages/common/src/services/JWPEntitlementService.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ import JWPAPIService from './integrations/jwp/JWPAPIService';
55

66
@injectable()
77
export default class JWPEntitlementService {
8-
private readonly apiService;
8+
protected readonly apiService;
99

1010
constructor(@inject(JWPAPIService) apiService: JWPAPIService) {
1111
this.apiService = apiService;
@@ -14,7 +14,7 @@ export default class JWPEntitlementService {
1414
getJWPMediaToken = async (configId: string = '', mediaId: string) => {
1515
try {
1616
const data = await this.apiService.get<SignedMediaResponse>(
17-
'v2/items/jw-media/token',
17+
'/v2/items/jw-media/token',
1818
{
1919
withAuthentication: true,
2020
},

packages/common/src/services/SettingsService.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { injectable } from 'inversify';
1+
import { inject, injectable } from 'inversify';
22
import ini from 'ini';
33
import { getI18n } from 'react-i18next';
44

@@ -12,9 +12,9 @@ import StorageService from './StorageService';
1212

1313
@injectable()
1414
export default class SettingsService {
15-
private readonly storageService;
15+
protected readonly storageService;
1616

17-
constructor(storageService: StorageService) {
17+
constructor(@inject(StorageService) storageService: StorageService) {
1818
this.storageService = storageService;
1919
}
2020

packages/common/src/services/WatchHistoryService.ts

Lines changed: 14 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -22,28 +22,32 @@ const schema = array(
2222

2323
@injectable()
2424
export default class WatchHistoryService {
25-
private PERSIST_KEY_WATCH_HISTORY = 'history';
25+
protected PERSIST_KEY_WATCH_HISTORY = 'history';
2626

27-
private readonly apiService;
28-
private readonly storageService;
29-
private readonly accountService;
27+
protected readonly apiService;
28+
protected readonly storageService;
29+
protected readonly accountService;
3030

31-
constructor(@inject(INTEGRATION_TYPE) integrationType: string, apiService: ApiService, storageService: StorageService) {
31+
constructor(
32+
@inject(INTEGRATION_TYPE) integrationType: string,
33+
@inject(ApiService) apiService: ApiService,
34+
@inject(StorageService) storageService: StorageService,
35+
) {
3236
this.apiService = apiService;
3337
this.storageService = storageService;
3438
this.accountService = getNamedModule(AccountService, integrationType);
3539
}
3640

3741
// Retrieve watch history media items info using a provided watch list
38-
private getWatchHistoryItems = async (continueWatchingList: string, ids: string[]): Promise<Record<string, PlaylistItem>> => {
42+
protected getWatchHistoryItems = async (continueWatchingList: string, ids: string[]): Promise<Record<string, PlaylistItem>> => {
3943
const watchHistoryItems = await this.apiService.getMediaByWatchlist(continueWatchingList, ids);
4044
const watchHistoryItemsDict = Object.fromEntries((watchHistoryItems || []).map((item) => [item.mediaid, item]));
4145

4246
return watchHistoryItemsDict;
4347
};
4448

4549
// We store separate episodes in the watch history and to show series card in the Continue Watching shelf we need to get their parent media items
46-
private getWatchHistorySeriesItems = async (continueWatchingList: string, ids: string[]): Promise<Record<string, PlaylistItem | undefined>> => {
50+
protected getWatchHistorySeriesItems = async (continueWatchingList: string, ids: string[]): Promise<Record<string, PlaylistItem | undefined>> => {
4751
const mediaWithSeries = await this.apiService.getSeriesByMediaIds(ids);
4852
const seriesIds = Object.keys(mediaWithSeries || {})
4953
.map((key) => mediaWithSeries?.[key]?.[0]?.series_id)
@@ -62,21 +66,21 @@ export default class WatchHistoryService {
6266
return seriesItemsDict;
6367
};
6468

65-
private validateWatchHistory(history: unknown) {
69+
protected validateWatchHistory(history: unknown) {
6670
if (history && schema.validateSync(history)) {
6771
return history as SerializedWatchHistoryItem[];
6872
}
6973

7074
return [];
7175
}
7276

73-
private async getWatchHistoryFromAccount(user: Customer) {
77+
protected async getWatchHistoryFromAccount(user: Customer) {
7478
const history = await this.accountService.getWatchHistory({ user });
7579

7680
return this.validateWatchHistory(history);
7781
}
7882

79-
private async getWatchHistoryFromStorage() {
83+
protected async getWatchHistoryFromStorage() {
8084
const history = await this.storageService.getItem(this.PERSIST_KEY_WATCH_HISTORY, true);
8185

8286
return this.validateWatchHistory(history);

0 commit comments

Comments
 (0)