@playkit-js/playkit-js-providers 2.40.1 → 2.40.2-canary.0-c7a43ae
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/dist/index.d.ts +1624 -0
- package/dist/playkit-analytics-service.js +1 -1
- package/dist/playkit-analytics-service.js.map +1 -1
- package/dist/playkit-bookmark-service.js +1 -1
- package/dist/playkit-bookmark-service.js.map +1 -1
- package/dist/playkit-ott-provider.js +1 -1
- package/dist/playkit-ott-provider.js.map +1 -1
- package/dist/playkit-ovp-provider.js +1 -1
- package/dist/playkit-ovp-provider.js.map +1 -1
- package/dist/playkit-stats-service.js +1 -1
- package/dist/playkit-stats-service.js.map +1 -1
- package/dist/tsdoc-metadata.json +11 -0
- package/flow-typed/types/media-config-sources.js +1 -1
- package/flow-typed/types/media-sources.js +1 -1
- package/package.json +49 -46
- package/playkit-analytics-service/package.json +5 -0
- package/playkit-bookmark-service/package.json +5 -0
- package/playkit-ott-provider/package.json +5 -0
- package/playkit-ovp-provider/package.json +5 -0
- package/playkit-stats-service/package.json +5 -0
- package/src/entities/bumper.ts +21 -0
- package/src/entities/drm.ts +47 -0
- package/src/entities/entry-list.ts +13 -0
- package/src/entities/image-source.ts +36 -0
- package/src/entities/media-entry.ts +104 -0
- package/src/entities/media-format.ts +47 -0
- package/src/entities/media-source.ts +70 -0
- package/src/entities/media-sources.ts +79 -0
- package/src/entities/playlist.ts +41 -0
- package/src/k-provider/common/base-provider-parser.ts +0 -0
- package/src/k-provider/common/base-provider.ts +112 -0
- package/src/k-provider/common/base-service-result.ts +56 -0
- package/src/k-provider/common/data-loader-manager.ts +115 -0
- package/src/k-provider/common/multi-request-builder.ts +111 -0
- package/src/k-provider/common/response-types/kaltura-access-control-message.ts +21 -0
- package/src/k-provider/common/response-types/kaltura-drm-playback-plugin-data.ts +38 -0
- package/src/k-provider/ott/config.ts +22 -0
- package/src/k-provider/ott/index.ts +14 -0
- package/src/k-provider/ott/loaders/asset-list-loader.ts +68 -0
- package/src/k-provider/ott/loaders/asset-loader.ts +69 -0
- package/src/k-provider/ott/loaders/data-loader-manager.ts +15 -0
- package/src/k-provider/ott/loaders/session-loader.ts +62 -0
- package/src/k-provider/ott/provider-parser.ts +285 -0
- package/src/k-provider/ott/provider.ts +252 -0
- package/src/k-provider/ott/response-types/kaltura-asset.ts +105 -0
- package/src/k-provider/ott/response-types/kaltura-bumper-playback-plugin-data.ts +27 -0
- package/src/k-provider/ott/response-types/kaltura-playback-context.ts +73 -0
- package/src/k-provider/ott/response-types/kaltura-playback-source.ts +62 -0
- package/src/k-provider/ott/response-types/kaltura-rule-action.ts +25 -0
- package/src/k-provider/ott/services/asset-service.ts +50 -0
- package/src/k-provider/ott/services/bookmark/bookmark-service.ts +48 -0
- package/src/k-provider/ott/services/bookmark/index.ts +11 -0
- package/src/k-provider/ott/services/ott-service.ts +33 -0
- package/src/k-provider/ott/services/user-service.ts +31 -0
- package/src/k-provider/ovp/config.ts +28 -0
- package/src/k-provider/ovp/external-captions-builder.ts +37 -0
- package/src/k-provider/ovp/index.ts +13 -0
- package/src/k-provider/ovp/loaders/data-loader-manager.ts +17 -0
- package/src/k-provider/ovp/loaders/entry-list-loader.ts +69 -0
- package/src/k-provider/ovp/loaders/media-entry-loader.ts +84 -0
- package/src/k-provider/ovp/loaders/playlist-loader.ts +69 -0
- package/src/k-provider/ovp/loaders/session-loader.ts +62 -0
- package/src/k-provider/ovp/loaders/ui-config-loader.ts +71 -0
- package/src/k-provider/ovp/play-source-url-builder.ts +59 -0
- package/src/k-provider/ovp/provider-parser.ts +461 -0
- package/src/k-provider/ovp/provider.ts +358 -0
- package/src/k-provider/ovp/regex-action-handler.ts +149 -0
- package/src/k-provider/ovp/request-params/base-entry-response-profile.ts +28 -0
- package/src/k-provider/ovp/response-types/index.ts +21 -0
- package/src/k-provider/ovp/response-types/kaltura-access-control-modify-request-host-regex-action.ts +35 -0
- package/src/k-provider/ovp/response-types/kaltura-base-entry-list-response.ts +30 -0
- package/src/k-provider/ovp/response-types/kaltura-bumper.ts +25 -0
- package/src/k-provider/ovp/response-types/kaltura-flavor-asset.ts +108 -0
- package/src/k-provider/ovp/response-types/kaltura-media-entries.ts +28 -0
- package/src/k-provider/ovp/response-types/kaltura-media-entry.ts +189 -0
- package/src/k-provider/ovp/response-types/kaltura-metadata-list-response.ts +22 -0
- package/src/k-provider/ovp/response-types/kaltura-metadata.ts +50 -0
- package/src/k-provider/ovp/response-types/kaltura-playback-context.ts +95 -0
- package/src/k-provider/ovp/response-types/kaltura-playback-source.ts +89 -0
- package/src/k-provider/ovp/response-types/kaltura-playlist.ts +33 -0
- package/src/k-provider/ovp/response-types/kaltura-rule-action.ts +27 -0
- package/src/k-provider/ovp/response-types/kaltura-ui-conf-response.ts +89 -0
- package/src/k-provider/ovp/response-types/kaltura-user-entry-list-response.ts +30 -0
- package/src/k-provider/ovp/response-types/kaltura-user-entry.ts +57 -0
- package/src/k-provider/ovp/services/analytics/analytics-service.ts +58 -0
- package/src/k-provider/ovp/services/analytics/index.ts +11 -0
- package/src/k-provider/ovp/services/base-entry-service.ts +75 -0
- package/src/k-provider/ovp/services/meta-data-service.ts +29 -0
- package/src/k-provider/ovp/services/ovp-service.ts +32 -0
- package/src/k-provider/ovp/services/playlist-service.ts +95 -0
- package/src/k-provider/ovp/services/session-service.ts +27 -0
- package/src/k-provider/ovp/services/stats/index.ts +11 -0
- package/src/k-provider/ovp/services/stats/stats-service.ts +32 -0
- package/src/k-provider/ovp/services/ui-conf-service.ts +32 -0
- package/src/types/adapter-data-config.ts +1 -0
- package/src/types/caption-type.ts +1 -0
- package/src/types/drm-data.ts +5 -0
- package/src/types/entry-list.ts +6 -0
- package/src/types/env-config.ts +7 -0
- package/src/types/external-caption-object.ts +7 -0
- package/src/types/filter-options.ts +3 -0
- package/src/types/index.ts +34 -0
- package/src/types/loader.ts +7 -0
- package/src/types/media-config-metadata.ts +13 -0
- package/src/types/media-config-session.ts +6 -0
- package/src/types/media-config-sources.ts +20 -0
- package/src/types/media-config.ts +8 -0
- package/src/types/media-entry.ts +16 -0
- package/src/types/media-format.ts +5 -0
- package/src/types/media-info.ts +21 -0
- package/src/types/media-source.ts +12 -0
- package/src/types/media-sources.ts +11 -0
- package/src/types/network-retry-parameters.ts +5 -0
- package/src/types/playback-context.ts +10 -0
- package/src/types/playlist-info.ts +4 -0
- package/src/types/playlist-item.ts +5 -0
- package/src/types/playlist-metadata.ts +4 -0
- package/src/types/playlist.ts +10 -0
- package/src/types/poster.ts +5 -0
- package/src/types/provider-options.ts +17 -0
- package/src/types/request-loader.ts +6 -0
- package/src/util/clone.ts +23 -0
- package/src/util/error/category.ts +11 -0
- package/src/util/error/code.ts +77 -0
- package/src/util/error/error.ts +47 -0
- package/src/util/error/severity.ts +21 -0
- package/src/util/logger.ts +108 -0
- package/src/util/param.ts +45 -0
- package/src/util/request-builder.ts +187 -0
- package/src/util/xml-parser.ts +39 -0
- package/CHANGELOG.md +0 -959
- package/samples/ott/bookmark.html +0 -23
- package/samples/ott/provider.html +0 -28
- package/samples/ovp/provider.html +0 -30
- package/samples/ovp/stats.html +0 -17
|
@@ -0,0 +1,285 @@
|
|
|
1
|
+
import getLogger from '../../util/logger';
|
|
2
|
+
import KalturaPlaybackSource from './response-types/kaltura-playback-source';
|
|
3
|
+
import KalturaPlaybackContext from './response-types/kaltura-playback-context';
|
|
4
|
+
import KalturaAsset from './response-types/kaltura-asset';
|
|
5
|
+
import MediaEntry from '../../entities/media-entry';
|
|
6
|
+
import Drm from '../../entities/drm';
|
|
7
|
+
import MediaSource from '../../entities/media-source';
|
|
8
|
+
import MediaSources from '../../entities/media-sources';
|
|
9
|
+
import EntryList from '../../entities/entry-list';
|
|
10
|
+
import Bumper from '../../entities/bumper';
|
|
11
|
+
import {SupportedStreamFormat, isProgressiveSource} from '../../entities/media-format';
|
|
12
|
+
import {KalturaDrmPlaybackPluginData} from '../common/response-types/kaltura-drm-playback-plugin-data';
|
|
13
|
+
import KalturaRuleAction from './response-types/kaltura-rule-action';
|
|
14
|
+
import {KalturaAccessControlMessage} from '../common/response-types/kaltura-access-control-message';
|
|
15
|
+
import type {OTTAssetLoaderResponse} from './loaders/asset-loader';
|
|
16
|
+
import KalturaBumpersPlaybackPluginData from './response-types/kaltura-bumper-playback-plugin-data';
|
|
17
|
+
import {ProviderMediaInfoObject, Poster} from '../../types';
|
|
18
|
+
|
|
19
|
+
const LIVE_ASST_OBJECT_TYPE: string = 'KalturaLiveAsset';
|
|
20
|
+
|
|
21
|
+
const MediaTypeCombinations: {[mediaType: string]: any} = {
|
|
22
|
+
[KalturaAsset.Type.MEDIA]: {
|
|
23
|
+
[KalturaPlaybackContext.Type.TRAILER]: () => ({type: MediaEntry.Type.VOD}),
|
|
24
|
+
[KalturaPlaybackContext.Type.PLAYBACK]: mediaAssetData => {
|
|
25
|
+
if (mediaAssetData.objectType === LIVE_ASST_OBJECT_TYPE) {
|
|
26
|
+
return {type: MediaEntry.Type.LIVE, dvrStatus: mediaAssetData.enableTrickPlay ? MediaEntry.DvrStatus.ON : MediaEntry.DvrStatus.OFF};
|
|
27
|
+
} else if (parseInt(mediaAssetData.externalIds) > 0) {
|
|
28
|
+
return {type: MediaEntry.Type.LIVE, dvrStatus: MediaEntry.DvrStatus.OFF};
|
|
29
|
+
}
|
|
30
|
+
return {type: MediaEntry.Type.VOD};
|
|
31
|
+
}
|
|
32
|
+
},
|
|
33
|
+
[KalturaAsset.Type.EPG]: {
|
|
34
|
+
[KalturaPlaybackContext.Type.CATCHUP]: () => ({type: MediaEntry.Type.VOD}),
|
|
35
|
+
[KalturaPlaybackContext.Type.START_OVER]: () => ({type: MediaEntry.Type.LIVE, dvrStatus: MediaEntry.DvrStatus.ON})
|
|
36
|
+
},
|
|
37
|
+
[KalturaAsset.Type.RECORDING]: {
|
|
38
|
+
[KalturaPlaybackContext.Type.PLAYBACK]: () => ({type: MediaEntry.Type.VOD})
|
|
39
|
+
}
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
export default class OTTProviderParser {
|
|
43
|
+
private static _logger = getLogger('OTTProviderParser');
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Returns parsed media entry by given OTT response objects.
|
|
47
|
+
* @function getMediaEntry
|
|
48
|
+
* @param {any} assetResponse - The asset response.
|
|
49
|
+
* @param {Object} requestData - The request data object.
|
|
50
|
+
* @returns {MediaEntry} - The media entry
|
|
51
|
+
* @static
|
|
52
|
+
* @public
|
|
53
|
+
*/
|
|
54
|
+
public static getMediaEntry(assetResponse: any, requestData: any): MediaEntry {
|
|
55
|
+
const mediaEntry = new MediaEntry();
|
|
56
|
+
OTTProviderParser._fillBaseData(mediaEntry, assetResponse, requestData);
|
|
57
|
+
const playbackContext = assetResponse.playBackContextResult;
|
|
58
|
+
const mediaAsset = assetResponse.mediaDataResult;
|
|
59
|
+
const kalturaSources = playbackContext.sources;
|
|
60
|
+
const filteredKalturaSources = OTTProviderParser._filterSourcesByFormats(kalturaSources, requestData.formats);
|
|
61
|
+
mediaEntry.sources = OTTProviderParser._getParsedSources(filteredKalturaSources);
|
|
62
|
+
const typeData = OTTProviderParser._getMediaType(mediaAsset.data, requestData.mediaType, requestData.contextType);
|
|
63
|
+
mediaEntry.type = typeData.type;
|
|
64
|
+
mediaEntry.dvrStatus = typeData.dvrStatus;
|
|
65
|
+
// eslint-disable-next-line prefer-spread
|
|
66
|
+
mediaEntry.duration = Math.max.apply(
|
|
67
|
+
Math,
|
|
68
|
+
kalturaSources.map(source => source.duration)
|
|
69
|
+
);
|
|
70
|
+
return mediaEntry;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
/**
|
|
74
|
+
* Returns parsed entry list by given OTT response objects
|
|
75
|
+
* @function getEntryList
|
|
76
|
+
* @param {any} playlistResponse - response
|
|
77
|
+
* @param {Array<ProviderMediaInfoObject>} requestEntries - entries list
|
|
78
|
+
* @returns {Playlist} - The entry list
|
|
79
|
+
* @static
|
|
80
|
+
* @public
|
|
81
|
+
*/
|
|
82
|
+
public static getEntryList(playlistResponse: any, requestEntries: Array<ProviderMediaInfoObject>): EntryList {
|
|
83
|
+
const entryList = new EntryList();
|
|
84
|
+
const playlistItems = playlistResponse.playlistItems.entries;
|
|
85
|
+
playlistItems.forEach(entry => {
|
|
86
|
+
const mediaEntry = new MediaEntry();
|
|
87
|
+
const requestData = requestEntries.find(requestEntry => requestEntry.entryId === entry.mediaDataResult.id);
|
|
88
|
+
OTTProviderParser._fillBaseData(mediaEntry, entry, requestData);
|
|
89
|
+
entryList.items.push(mediaEntry);
|
|
90
|
+
});
|
|
91
|
+
return entryList;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
/**
|
|
95
|
+
* Returns parsed bumper by given OTT response objects.
|
|
96
|
+
* @function getBumper
|
|
97
|
+
* @param {any} assetResponse - The asset response.
|
|
98
|
+
* @returns {?Bumper} - The bumper
|
|
99
|
+
* @static
|
|
100
|
+
* @public
|
|
101
|
+
*/
|
|
102
|
+
public static getBumper(assetResponse: any): Bumper | unknown {
|
|
103
|
+
const playbackContext = assetResponse.playBackContextResult;
|
|
104
|
+
const progressiveBumper = playbackContext.plugins.find(
|
|
105
|
+
bumper => bumper.streamertype === KalturaBumpersPlaybackPluginData.StreamerType.PROGRESSIVE
|
|
106
|
+
);
|
|
107
|
+
if (progressiveBumper) {
|
|
108
|
+
return new Bumper(progressiveBumper);
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
private static _fillBaseData(mediaEntry: MediaEntry, assetResponse: any, requestData: any): MediaEntry {
|
|
113
|
+
const mediaAsset = assetResponse.mediaDataResult;
|
|
114
|
+
const metaData = OTTProviderParser.reconstructMetadata(mediaAsset);
|
|
115
|
+
metaData.description = mediaAsset.description;
|
|
116
|
+
metaData.name = mediaAsset.name;
|
|
117
|
+
if (mediaAsset.createDate) metaData.createdAt = mediaAsset.createDate;
|
|
118
|
+
if (mediaAsset.endDate) metaData.endDate = mediaAsset.endDate;
|
|
119
|
+
if (mediaAsset.data.entryId) metaData.entryId = mediaAsset.data.entryId;
|
|
120
|
+
if (mediaAsset.data.epgId) metaData.epgId = mediaAsset.data.epgId;
|
|
121
|
+
if (mediaAsset.data.recordingId) metaData.recordingId = mediaAsset.data.recordingId;
|
|
122
|
+
if (requestData && requestData.mediaType) metaData.mediaType = requestData.mediaType;
|
|
123
|
+
if (requestData && requestData.contextType) metaData.contextType = requestData.contextType;
|
|
124
|
+
mediaEntry.metadata = metaData;
|
|
125
|
+
mediaEntry.poster = OTTProviderParser._getPoster(mediaAsset.pictures);
|
|
126
|
+
mediaEntry.id = mediaAsset.id;
|
|
127
|
+
return mediaEntry;
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
/**
|
|
131
|
+
* reconstruct the metadata
|
|
132
|
+
* @param {Object} mediaAsset the mediaAsset that contains the response with the metadata.
|
|
133
|
+
* @returns {Object} reconstructed metadata object
|
|
134
|
+
*/
|
|
135
|
+
public static reconstructMetadata(mediaAsset: any): any {
|
|
136
|
+
const metadata = {
|
|
137
|
+
metas: OTTProviderParser.addToMetaObject(mediaAsset.metas),
|
|
138
|
+
tags: OTTProviderParser.addToMetaObject(mediaAsset.tags)
|
|
139
|
+
};
|
|
140
|
+
return metadata;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
/**
|
|
144
|
+
* transform an array of [{key: value},{key: value}...] to an object
|
|
145
|
+
* @param {Array<Object>} list a list of objects
|
|
146
|
+
* @returns {Object} an mapped object of the arrayed list.
|
|
147
|
+
*/
|
|
148
|
+
public static addToMetaObject(list: Array<any>): any {
|
|
149
|
+
const categoryObj = {};
|
|
150
|
+
if (list) {
|
|
151
|
+
list.forEach(item => {
|
|
152
|
+
categoryObj[item.key] = item.value;
|
|
153
|
+
});
|
|
154
|
+
}
|
|
155
|
+
return categoryObj;
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
/**
|
|
159
|
+
* Gets the poster url without width and height.
|
|
160
|
+
* @param {Array<Object>} pictures - Media pictures.
|
|
161
|
+
* @returns {string | Array<Object>} - Poster base url or array of poster candidates.
|
|
162
|
+
* @private
|
|
163
|
+
*/
|
|
164
|
+
public static _getPoster(pictures: Poster[]): string | Poster[] {
|
|
165
|
+
if (pictures && pictures.length > 0) {
|
|
166
|
+
const picObj = pictures[0];
|
|
167
|
+
const url = picObj.url;
|
|
168
|
+
// Search for thumbnail service
|
|
169
|
+
const regex = /.*\/thumbnail\/.*(?:width|height)\/\d+\/(?:height|width)\/\d+/;
|
|
170
|
+
if (regex.test(url)) {
|
|
171
|
+
return url;
|
|
172
|
+
}
|
|
173
|
+
return pictures.map(pic => ({url: pic.url, width: pic.width, height: pic.height}));
|
|
174
|
+
}
|
|
175
|
+
return '';
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/**
|
|
179
|
+
* Gets the media type (LIVE/VOD)
|
|
180
|
+
* @param {Object} mediaAssetData - The media asset data.
|
|
181
|
+
* @param {string} mediaType - The asset media type.
|
|
182
|
+
* @param {string} contextType - The asset context type.
|
|
183
|
+
* @returns {Object} - The type data object.
|
|
184
|
+
* @private
|
|
185
|
+
*/
|
|
186
|
+
public static _getMediaType(mediaAssetData: any, mediaType: string, contextType: string): any {
|
|
187
|
+
let typeData = {type: MediaEntry.Type.UNKNOWN};
|
|
188
|
+
if (MediaTypeCombinations[mediaType] && MediaTypeCombinations[mediaType][contextType]) {
|
|
189
|
+
typeData = MediaTypeCombinations[mediaType][contextType](mediaAssetData);
|
|
190
|
+
}
|
|
191
|
+
return typeData;
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
/**
|
|
195
|
+
* Filtered the kalturaSources array by device type.
|
|
196
|
+
* @param {Array<KalturaPlaybackSource>} kalturaSources - The kaltura sources.
|
|
197
|
+
* @param {Array<string>} formats - Partner device formats.
|
|
198
|
+
* @returns {Array<KalturaPlaybackSource>} - Filtered kalturaSources array.
|
|
199
|
+
* @private
|
|
200
|
+
*/
|
|
201
|
+
public static _filterSourcesByFormats(kalturaSources: Array<KalturaPlaybackSource>, formats: Array<string>): Array<KalturaPlaybackSource> {
|
|
202
|
+
if (formats.length > 0) {
|
|
203
|
+
kalturaSources = kalturaSources.filter(source => formats.includes(source.type));
|
|
204
|
+
}
|
|
205
|
+
return kalturaSources;
|
|
206
|
+
}
|
|
207
|
+
|
|
208
|
+
/**
|
|
209
|
+
* Returns the parsed sources
|
|
210
|
+
* @function _getParsedSources
|
|
211
|
+
* @param {Array<KalturaPlaybackSource>} kalturaSources - The kaltura sources
|
|
212
|
+
* @param {Object} playbackContext - The playback context
|
|
213
|
+
* @return {MediaSources} - A media sources
|
|
214
|
+
* @static
|
|
215
|
+
* @private
|
|
216
|
+
*/
|
|
217
|
+
public static _getParsedSources(kalturaSources: Array<KalturaPlaybackSource>): MediaSources {
|
|
218
|
+
const sources = new MediaSources();
|
|
219
|
+
const addAdaptiveSource = (source: KalturaPlaybackSource): void => {
|
|
220
|
+
const parsedSource = OTTProviderParser._parseAdaptiveSource(source);
|
|
221
|
+
if (parsedSource) {
|
|
222
|
+
const sourceFormat = SupportedStreamFormat.get(source.format);
|
|
223
|
+
sources.map(parsedSource, sourceFormat);
|
|
224
|
+
}
|
|
225
|
+
};
|
|
226
|
+
const parseAdaptiveSources = (): void => {
|
|
227
|
+
kalturaSources.filter(source => !isProgressiveSource(source.format)).forEach(addAdaptiveSource);
|
|
228
|
+
};
|
|
229
|
+
const parseProgressiveSources = (): void => {
|
|
230
|
+
kalturaSources.filter(source => isProgressiveSource(source.format)).forEach(addAdaptiveSource);
|
|
231
|
+
};
|
|
232
|
+
if (kalturaSources && kalturaSources.length > 0) {
|
|
233
|
+
parseAdaptiveSources();
|
|
234
|
+
parseProgressiveSources();
|
|
235
|
+
}
|
|
236
|
+
return sources;
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
/**
|
|
240
|
+
* Returns a parsed adaptive source
|
|
241
|
+
* @function _parseAdaptiveSource
|
|
242
|
+
* @param {KalturaPlaybackSource} kalturaSource - A kaltura source
|
|
243
|
+
* @returns {?MediaSource} - The parsed adaptive kalturaSource
|
|
244
|
+
* @static
|
|
245
|
+
* @private
|
|
246
|
+
*/
|
|
247
|
+
public static _parseAdaptiveSource(kalturaSource?: KalturaPlaybackSource): MediaSource | null {
|
|
248
|
+
const mediaSource = new MediaSource();
|
|
249
|
+
if (kalturaSource) {
|
|
250
|
+
const playUrl = kalturaSource.url;
|
|
251
|
+
const mediaFormat = SupportedStreamFormat.get(kalturaSource.format);
|
|
252
|
+
if (mediaFormat) {
|
|
253
|
+
mediaSource.mimetype = mediaFormat.mimeType;
|
|
254
|
+
}
|
|
255
|
+
if (!playUrl) {
|
|
256
|
+
OTTProviderParser._logger.error(
|
|
257
|
+
`failed to create play url from source, discarding source: (${kalturaSource.fileId}), ${kalturaSource.format}.`
|
|
258
|
+
);
|
|
259
|
+
return null;
|
|
260
|
+
}
|
|
261
|
+
mediaSource.url = playUrl;
|
|
262
|
+
mediaSource.id = kalturaSource.fileId + ',' + kalturaSource.format;
|
|
263
|
+
if (kalturaSource.hasDrmData()) {
|
|
264
|
+
const drmParams: Array<Drm> = [];
|
|
265
|
+
kalturaSource.drm.forEach(drm => {
|
|
266
|
+
drmParams.push(new Drm(drm.licenseURL, KalturaDrmPlaybackPluginData.Scheme[drm.scheme], drm.certificate));
|
|
267
|
+
});
|
|
268
|
+
mediaSource.drmData = drmParams;
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
return mediaSource;
|
|
272
|
+
}
|
|
273
|
+
|
|
274
|
+
public static hasBlockAction(response: OTTAssetLoaderResponse): boolean {
|
|
275
|
+
return response.playBackContextResult.hasBlockAction();
|
|
276
|
+
}
|
|
277
|
+
|
|
278
|
+
public static getBlockAction(response: OTTAssetLoaderResponse): KalturaRuleAction | undefined {
|
|
279
|
+
return response.playBackContextResult.getBlockAction();
|
|
280
|
+
}
|
|
281
|
+
|
|
282
|
+
public static getErrorMessages(response: OTTAssetLoaderResponse): Array<KalturaAccessControlMessage> {
|
|
283
|
+
return response.playBackContextResult.getErrorMessages();
|
|
284
|
+
}
|
|
285
|
+
}
|
|
@@ -0,0 +1,252 @@
|
|
|
1
|
+
import BaseProvider from '../common/base-provider';
|
|
2
|
+
import getLogger from '../../util/logger';
|
|
3
|
+
import OTTConfiguration from './config';
|
|
4
|
+
import OTTDataLoaderManager from './loaders/data-loader-manager';
|
|
5
|
+
import OTTSessionLoader from './loaders/session-loader';
|
|
6
|
+
import OTTAssetLoader from './loaders/asset-loader';
|
|
7
|
+
import OTTAssetListLoader from './loaders/asset-list-loader';
|
|
8
|
+
import OTTProviderParser from './provider-parser';
|
|
9
|
+
import KalturaAsset from './response-types/kaltura-asset';
|
|
10
|
+
import KalturaPlaybackContext from './response-types/kaltura-playback-context';
|
|
11
|
+
import MediaEntry from '../../entities/media-entry';
|
|
12
|
+
import Error from '../../util/error/error';
|
|
13
|
+
import {
|
|
14
|
+
ILoader,
|
|
15
|
+
OTTProviderMediaInfoObject,
|
|
16
|
+
ProviderEntryListObject,
|
|
17
|
+
ProviderMediaConfigObject,
|
|
18
|
+
ProviderMediaConfigSourcesObject, ProviderMediaInfoObject,
|
|
19
|
+
ProviderOptionsObject,
|
|
20
|
+
ProviderPlaybackContextOptions,
|
|
21
|
+
ProviderPlaylistObject
|
|
22
|
+
} from '../../types';
|
|
23
|
+
|
|
24
|
+
export default class OTTProvider extends BaseProvider<OTTProviderMediaInfoObject> {
|
|
25
|
+
/**
|
|
26
|
+
* @constructor
|
|
27
|
+
* @param {ProviderOptionsObject} options - provider options
|
|
28
|
+
* @param {string} playerVersion - player version
|
|
29
|
+
*/
|
|
30
|
+
constructor(options: ProviderOptionsObject, playerVersion: string) {
|
|
31
|
+
super(options, playerVersion);
|
|
32
|
+
this._logger = getLogger('OTTProvider');
|
|
33
|
+
OTTConfiguration.set(options.env);
|
|
34
|
+
this._networkRetryConfig = Object.assign(this._networkRetryConfig, options.networkRetryParameters);
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
public get env(): any {
|
|
38
|
+
return OTTConfiguration.get();
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
/**
|
|
42
|
+
* Gets the backend media config.
|
|
43
|
+
* @param {OTTProviderMediaInfoObject} mediaInfo - ott media info
|
|
44
|
+
* @returns {Promise<ProviderMediaConfigObject>} - The provider media config
|
|
45
|
+
*/
|
|
46
|
+
public getMediaConfig(mediaInfo: OTTProviderMediaInfoObject): Promise<ProviderMediaConfigObject> {
|
|
47
|
+
if (mediaInfo.ks) {
|
|
48
|
+
this.ks = mediaInfo.ks;
|
|
49
|
+
this._isAnonymous = false;
|
|
50
|
+
}
|
|
51
|
+
this._dataLoader = new OTTDataLoaderManager(this.partnerId, this.ks, this._networkRetryConfig);
|
|
52
|
+
return new Promise((resolve, reject) => {
|
|
53
|
+
const entryId = mediaInfo.entryId;
|
|
54
|
+
if (entryId) {
|
|
55
|
+
let ks: string = this.ks;
|
|
56
|
+
if (!ks) {
|
|
57
|
+
ks = '{1:result:ks}';
|
|
58
|
+
this._dataLoader.add(OTTSessionLoader, {partnerId: this.partnerId});
|
|
59
|
+
}
|
|
60
|
+
const contextType = mediaInfo.contextType || KalturaPlaybackContext.Type.PLAYBACK;
|
|
61
|
+
const mediaType = mediaInfo.mediaType || KalturaAsset.Type.MEDIA;
|
|
62
|
+
const assetReferenceType = mediaInfo.assetReferenceType || KalturaAsset.AssetReferenceType.MEDIA;
|
|
63
|
+
const playbackContext: ProviderPlaybackContextOptions = {
|
|
64
|
+
mediaProtocol: mediaInfo.protocol,
|
|
65
|
+
assetFileIds: mediaInfo.fileIds,
|
|
66
|
+
context: contextType
|
|
67
|
+
};
|
|
68
|
+
if (mediaInfo.streamerType) {
|
|
69
|
+
playbackContext.streamerType = mediaInfo.streamerType;
|
|
70
|
+
}
|
|
71
|
+
if (mediaInfo.urlType) {
|
|
72
|
+
playbackContext.urlType = mediaInfo.urlType;
|
|
73
|
+
}
|
|
74
|
+
if (mediaInfo.adapterData) {
|
|
75
|
+
playbackContext.adapterData = mediaInfo.adapterData;
|
|
76
|
+
}
|
|
77
|
+
this._dataLoader.add(OTTAssetLoader, {
|
|
78
|
+
entryId: entryId,
|
|
79
|
+
ks: ks,
|
|
80
|
+
type: mediaType,
|
|
81
|
+
playbackContext: playbackContext,
|
|
82
|
+
assetReferenceType: assetReferenceType
|
|
83
|
+
});
|
|
84
|
+
const requestData = {
|
|
85
|
+
contextType: contextType,
|
|
86
|
+
mediaType: mediaType,
|
|
87
|
+
formats: mediaInfo.formats || []
|
|
88
|
+
};
|
|
89
|
+
return this._dataLoader.fetchData().then(
|
|
90
|
+
response => {
|
|
91
|
+
try {
|
|
92
|
+
resolve(this._parseDataFromResponse(response, requestData));
|
|
93
|
+
} catch (err) {
|
|
94
|
+
reject(err);
|
|
95
|
+
}
|
|
96
|
+
},
|
|
97
|
+
err => {
|
|
98
|
+
reject(err);
|
|
99
|
+
}
|
|
100
|
+
);
|
|
101
|
+
} else {
|
|
102
|
+
reject(new Error(Error.Severity.CRITICAL, Error.Category.PROVIDER, Error.Code.MISSING_MANDATORY_PARAMS, {message: 'missing entry id'}));
|
|
103
|
+
}
|
|
104
|
+
});
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
private _parseDataFromResponse(data: Map<string, ILoader>, requestData: any): ProviderMediaConfigObject {
|
|
108
|
+
this._logger.debug('Data parsing started');
|
|
109
|
+
const mediaConfig: ProviderMediaConfigObject = {
|
|
110
|
+
session: {
|
|
111
|
+
isAnonymous: this._isAnonymous,
|
|
112
|
+
partnerId: this.partnerId
|
|
113
|
+
},
|
|
114
|
+
sources: this._getDefaultSourcesObject(),
|
|
115
|
+
plugins: {}
|
|
116
|
+
} as ProviderMediaConfigObject;
|
|
117
|
+
if (this.uiConfId) {
|
|
118
|
+
mediaConfig.session.uiConfId = this.uiConfId;
|
|
119
|
+
}
|
|
120
|
+
if (data) {
|
|
121
|
+
if (data.has(OTTSessionLoader.id)) {
|
|
122
|
+
const sessionLoader = data.get(OTTSessionLoader.id);
|
|
123
|
+
if (sessionLoader && sessionLoader.response) {
|
|
124
|
+
mediaConfig.session.ks = sessionLoader.response;
|
|
125
|
+
}
|
|
126
|
+
} else {
|
|
127
|
+
mediaConfig.session.ks = this.ks;
|
|
128
|
+
}
|
|
129
|
+
if (data.has(OTTAssetLoader.id)) {
|
|
130
|
+
const assetLoader = data.get(OTTAssetLoader.id);
|
|
131
|
+
if (assetLoader && assetLoader.response && Object.keys(assetLoader.response).length) {
|
|
132
|
+
const response = (assetLoader as unknown as OTTAssetLoader).response;
|
|
133
|
+
if (OTTProviderParser.hasBlockAction(response)) {
|
|
134
|
+
throw new Error(Error.Severity.CRITICAL, Error.Category.SERVICE, Error.Code.BLOCK_ACTION, {
|
|
135
|
+
action: OTTProviderParser.getBlockAction(response),
|
|
136
|
+
messages: OTTProviderParser.getErrorMessages(response)
|
|
137
|
+
});
|
|
138
|
+
}
|
|
139
|
+
const mediaEntry = OTTProviderParser.getMediaEntry(response, requestData);
|
|
140
|
+
Object.assign(mediaConfig.sources, this._getSourcesObject(mediaEntry));
|
|
141
|
+
this._verifyHasSources(mediaConfig.sources);
|
|
142
|
+
const bumper = OTTProviderParser.getBumper(response);
|
|
143
|
+
if (bumper) {
|
|
144
|
+
Object.assign(mediaConfig.plugins, {bumper});
|
|
145
|
+
}
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
}
|
|
149
|
+
this._logger.debug('Data parsing finished', mediaConfig);
|
|
150
|
+
return mediaConfig;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* Gets the playlist config from entry list.
|
|
155
|
+
* @param {ProviderEntryListObject} entryListInfo - ott entry list info
|
|
156
|
+
* @returns {Promise<ProviderPlaylistObject>} - The provider playlist config
|
|
157
|
+
*/
|
|
158
|
+
public getEntryListConfig(entryListInfo: ProviderEntryListObject): Promise<ProviderPlaylistObject> {
|
|
159
|
+
if (entryListInfo.ks) {
|
|
160
|
+
this.ks = entryListInfo.ks;
|
|
161
|
+
this._isAnonymous = false;
|
|
162
|
+
}
|
|
163
|
+
this._dataLoader = new OTTDataLoaderManager(this.partnerId, this.ks, this._networkRetryConfig);
|
|
164
|
+
return new Promise((resolve, reject) => {
|
|
165
|
+
const entries = entryListInfo.entries;
|
|
166
|
+
if (entries && entries.length) {
|
|
167
|
+
let ks: string = this.ks;
|
|
168
|
+
if (!ks) {
|
|
169
|
+
ks = '{1:result:ks}';
|
|
170
|
+
this._dataLoader.add(OTTSessionLoader, {partnerId: this.partnerId});
|
|
171
|
+
}
|
|
172
|
+
this._dataLoader.add(OTTAssetListLoader, {entries, ks});
|
|
173
|
+
this._dataLoader.fetchData(false).then(
|
|
174
|
+
response => {
|
|
175
|
+
resolve(this._parseEntryListDataFromResponse(response, entries));
|
|
176
|
+
},
|
|
177
|
+
err => {
|
|
178
|
+
reject(err);
|
|
179
|
+
}
|
|
180
|
+
);
|
|
181
|
+
} else {
|
|
182
|
+
reject({success: false, data: 'Missing mandatory parameter'});
|
|
183
|
+
}
|
|
184
|
+
});
|
|
185
|
+
}
|
|
186
|
+
|
|
187
|
+
private _parseEntryListDataFromResponse(data: Map<string, ILoader>, requestEntries: Array<ProviderMediaInfoObject>): ProviderPlaylistObject {
|
|
188
|
+
this._logger.debug('Data parsing started');
|
|
189
|
+
const playlistConfig: ProviderPlaylistObject = {
|
|
190
|
+
id: '',
|
|
191
|
+
metadata: {
|
|
192
|
+
name: '',
|
|
193
|
+
description: ''
|
|
194
|
+
},
|
|
195
|
+
poster: '',
|
|
196
|
+
items: [],
|
|
197
|
+
playlistLastEntryId: ''
|
|
198
|
+
};
|
|
199
|
+
if (data && data.has(OTTAssetListLoader.id)) {
|
|
200
|
+
const playlistLoader = data.get(OTTAssetListLoader.id);
|
|
201
|
+
if (playlistLoader && playlistLoader.response) {
|
|
202
|
+
const entryList = OTTProviderParser.getEntryList(playlistLoader.response, requestEntries);
|
|
203
|
+
entryList.items.forEach(i => playlistConfig.items.push({sources: this._getSourcesObject(i)}));
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
this._logger.debug('Data parsing finished', playlistConfig);
|
|
207
|
+
return playlistConfig;
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
private _getDefaultSourcesObject(): ProviderMediaConfigSourcesObject {
|
|
211
|
+
return {
|
|
212
|
+
hls: [],
|
|
213
|
+
dash: [],
|
|
214
|
+
progressive: [],
|
|
215
|
+
image: [],
|
|
216
|
+
id: '',
|
|
217
|
+
duration: 0,
|
|
218
|
+
type: MediaEntry.Type.UNKNOWN,
|
|
219
|
+
poster: '',
|
|
220
|
+
dvr: false,
|
|
221
|
+
vr: null,
|
|
222
|
+
metadata: {
|
|
223
|
+
name: '',
|
|
224
|
+
description: '',
|
|
225
|
+
tags: ''
|
|
226
|
+
}
|
|
227
|
+
};
|
|
228
|
+
}
|
|
229
|
+
|
|
230
|
+
private _getSourcesObject(mediaEntry: MediaEntry): ProviderMediaConfigSourcesObject {
|
|
231
|
+
const sourcesObject: ProviderMediaConfigSourcesObject = this._getDefaultSourcesObject();
|
|
232
|
+
const mediaSources = mediaEntry.sources.toJSON();
|
|
233
|
+
sourcesObject.hls = mediaSources.hls;
|
|
234
|
+
sourcesObject.dash = mediaSources.dash;
|
|
235
|
+
sourcesObject.progressive = mediaSources.progressive;
|
|
236
|
+
sourcesObject.id = mediaEntry.id;
|
|
237
|
+
sourcesObject.duration = mediaEntry.duration;
|
|
238
|
+
sourcesObject.type = mediaEntry.type;
|
|
239
|
+
sourcesObject.dvr = !!mediaEntry.dvrStatus;
|
|
240
|
+
sourcesObject.poster = mediaEntry.poster;
|
|
241
|
+
if (
|
|
242
|
+
mediaEntry.metadata &&
|
|
243
|
+
mediaEntry.metadata.metas &&
|
|
244
|
+
typeof mediaEntry.metadata.metas.tags === 'string' &&
|
|
245
|
+
mediaEntry.metadata.metas.tags.indexOf('360') > -1
|
|
246
|
+
) {
|
|
247
|
+
sourcesObject.vr = {};
|
|
248
|
+
}
|
|
249
|
+
Object.assign(sourcesObject.metadata, mediaEntry.metadata);
|
|
250
|
+
return sourcesObject;
|
|
251
|
+
}
|
|
252
|
+
}
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
import ServiceResult from '../../common/base-service-result';
|
|
2
|
+
import {Poster} from '../../../types';
|
|
3
|
+
|
|
4
|
+
export default class KalturaAsset extends ServiceResult {
|
|
5
|
+
public static Type: {[type: string]: string} = {
|
|
6
|
+
MEDIA: 'media',
|
|
7
|
+
RECORDING: 'recording',
|
|
8
|
+
EPG: 'epg'
|
|
9
|
+
};
|
|
10
|
+
|
|
11
|
+
public static AssetReferenceType: {[type: string]: string} = {
|
|
12
|
+
MEDIA: 'media',
|
|
13
|
+
EPG_INTERNAL: 'epg_internal',
|
|
14
|
+
EPG_EXTERNAL: 'epg_external',
|
|
15
|
+
NPVR: 'nPVR'
|
|
16
|
+
};
|
|
17
|
+
/**
|
|
18
|
+
* @member - The asset id
|
|
19
|
+
* @type {number}
|
|
20
|
+
*/
|
|
21
|
+
public id!: number;
|
|
22
|
+
/**
|
|
23
|
+
* @member - The asset createDate - Specifies when was the Asset was created. Date and time represented as epoch
|
|
24
|
+
* @type {number}
|
|
25
|
+
*/
|
|
26
|
+
public createDate!: number;
|
|
27
|
+
/**
|
|
28
|
+
* @member - The asset endDate - epoch For VOD: till when the asset be available in the catalog. For EPG/Linear: program end time and date
|
|
29
|
+
* @type {number}
|
|
30
|
+
*/
|
|
31
|
+
public endDate!: number;
|
|
32
|
+
/**
|
|
33
|
+
* @member - The asset name
|
|
34
|
+
* @type {string}
|
|
35
|
+
*/
|
|
36
|
+
public name: string = '';
|
|
37
|
+
/**
|
|
38
|
+
* @member - The asset name description
|
|
39
|
+
* @type {string}
|
|
40
|
+
*/
|
|
41
|
+
public description: string = '';
|
|
42
|
+
/**
|
|
43
|
+
* @member - The asset tags
|
|
44
|
+
* @type {Array<Object>}
|
|
45
|
+
*/
|
|
46
|
+
public tags: Array<any> = [];
|
|
47
|
+
/**
|
|
48
|
+
* @member - The asset metas
|
|
49
|
+
* @type {Array<Object>}
|
|
50
|
+
*/
|
|
51
|
+
public metas: Array<any> = [];
|
|
52
|
+
/**
|
|
53
|
+
* @member - The asset images
|
|
54
|
+
* @type {Array<any>}
|
|
55
|
+
*/
|
|
56
|
+
public pictures: Array<Poster> = [];
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* @member - Number of plays
|
|
60
|
+
* @type {number}
|
|
61
|
+
*/
|
|
62
|
+
public plays!: number;
|
|
63
|
+
|
|
64
|
+
/**
|
|
65
|
+
* @member - Number of views
|
|
66
|
+
* @type {number}
|
|
67
|
+
*/
|
|
68
|
+
public views!: number;
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* @constructor
|
|
72
|
+
* @param {Object} response The response
|
|
73
|
+
*/
|
|
74
|
+
constructor(response: any) {
|
|
75
|
+
super(response);
|
|
76
|
+
if (!this.hasError) {
|
|
77
|
+
this.id = response.id;
|
|
78
|
+
this.name = response.name;
|
|
79
|
+
this.description = response.description;
|
|
80
|
+
this.createDate = response.createDate;
|
|
81
|
+
this.endDate = response.endDate;
|
|
82
|
+
this.plays = response.plays;
|
|
83
|
+
this.views = response.views;
|
|
84
|
+
this.metas = this._formatTagsMetas(response.metas);
|
|
85
|
+
this.tags = this._formatTagsMetas(response.tags);
|
|
86
|
+
this.pictures = response.images;
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
private _formatTagsMetas(objectToParse: any): Array<any> {
|
|
91
|
+
const parsed: { key: string; value: any; }[] = [];
|
|
92
|
+
Object.keys(objectToParse).forEach((key) => {
|
|
93
|
+
if (objectToParse[key].objects) {
|
|
94
|
+
let value = '';
|
|
95
|
+
objectToParse[key].objects.forEach((object) => {
|
|
96
|
+
value += object.value + '|';
|
|
97
|
+
});
|
|
98
|
+
parsed.push({key: key, value: value});
|
|
99
|
+
} else {
|
|
100
|
+
parsed.push({key: key, value: objectToParse[key].value});
|
|
101
|
+
}
|
|
102
|
+
});
|
|
103
|
+
return parsed;
|
|
104
|
+
}
|
|
105
|
+
}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
export default class KalturaBumpersPlaybackPluginData {
|
|
2
|
+
public static StreamerType: {[type: string]: string} = {
|
|
3
|
+
HLS: 'hls',
|
|
4
|
+
DASH: 'dash',
|
|
5
|
+
PROGRESSIVE: 'progressive'
|
|
6
|
+
};
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* @member - The streamer type
|
|
10
|
+
* @type {string}
|
|
11
|
+
*/
|
|
12
|
+
public streamertype: string;
|
|
13
|
+
/**
|
|
14
|
+
* @member - The url
|
|
15
|
+
* @type {string}
|
|
16
|
+
*/
|
|
17
|
+
public url: string;
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* @constructor
|
|
21
|
+
* @param {Object} data - The response
|
|
22
|
+
*/
|
|
23
|
+
constructor(data: any) {
|
|
24
|
+
this.streamertype = data.streamertype;
|
|
25
|
+
this.url = data.url;
|
|
26
|
+
}
|
|
27
|
+
}
|