Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Got most aspects of TV2 play scrobble to work except the activation to fetch token #318

Draft
wants to merge 4 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
125 changes: 122 additions & 3 deletions src/services/tv2-play/Tv2PlayApi.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,22 @@
import { ServiceApi } from '@apis/ServiceApi';
import { EpisodeItem, MovieItem, ScrobbleItem } from '@models/Item';
import { Tv2PlayService } from '@/tv2-play/Tv2PlayService';
import { Requests } from '@common/Requests';
import { Requests, withHeaders } from '@common/Requests';
import { EpisodeItem, MovieItem, ScrobbleItem, ScrobbleItemValues } from '@models/Item';
import { Tv2PlayService } from '@/services/tv2-play/Tv2PlayService';
import { Utils } from '@common/Utils';

interface Asset {
id: number;
path: string;
title: string;
}

export interface Tv2PlayHistoryItem {
id: number;
date: string;
asset: Asset;
season: Asset;
show: Asset;
}

type TV2SumoMetadataResponse = TV2SumoMetadataResponseEpisode | TV2SumoMetadataResponseMovie;

Expand All @@ -24,9 +39,113 @@ interface TV2SumoMetadataResponseMovie {
asset_type: 'movie';
}

interface TV2PlayUserInfo {
email: string;
firstname: string;
lastname: string;
}

interface TokenResponse {
access_token: string;
}
// Define any types you need here

class _Tv2PlayApi extends ServiceApi {
HISTORY_URL: string;
TOKEN_URL: string;
PROFILE_URL: string;
token: string;
isActivated: boolean;
pageSize = 10;

authRequests = Requests;

constructor() {
super(Tv2PlayService.id);
this.HISTORY_URL = 'https://ai.sumo.tv2.no/v4/viewinghistory/?start=0&size=10';
this.TOKEN_URL = 'https://id.tv2.no/oauth/token';
this.PROFILE_URL = 'https://api.sumo.tv2.no/user/';
this.token = '';
this.isActivated = false;
}

async activate() {
// const authData = await Requests.send({
// url: this.TOKEN_URL,
// method: 'GET',
// body: {
// },
// });

//TODO find a way to get the token automatically
this.token =
'log into tv2 play and inspect other network calls to manually paste the token here';
console.log('token got', this.token);
this.authRequests = withHeaders({
Authorization: `Bearer ${this.token}`,
});
const profileData = await this.authRequests.send({
url: this.PROFILE_URL,
method: 'GET',
});
const profile = JSON.parse(profileData) as TV2PlayUserInfo;
this.session = {
profileName: profile.firstname + ' ' + profile.lastname,
};
this.isActivated = true;
}
async checkLogin() {
if (!this.isActivated) {
await this.activate();
}
return !!this.session && this.session.profileName !== null;
}

async loadHistoryItems(): Promise<Tv2PlayHistoryItem[]> {
if (!this.isActivated) {
await this.activate();
}

// Retrieve the history items
const responseText = await this.authRequests.send({
url: `https://ai.sumo.tv2.no/v4/viewinghistory/?start=${
this.nextHistoryPage * this.pageSize
}&size=${this.pageSize}`,
method: 'GET',
});
const historyItems = JSON.parse(responseText) as Tv2PlayHistoryItem[];

this.nextHistoryPage += 1;
// Check if it has reached the history end
this.hasReachedHistoryEnd = historyItems.length === 0;

return historyItems;
}

isNewHistoryItem(historyItem: Tv2PlayHistoryItem, lastSync: number, lastSyncId: string) {
return new Date(historyItem.date).getTime() > lastSync;
}

getHistoryItemId(historyItem: Tv2PlayHistoryItem) {
return historyItem.id.toString();
}

async convertHistoryItems(historyItems: Tv2PlayHistoryItem[]) {
const promises = historyItems.map(async (historyItem) => {
const item = await this.getItem(`${historyItem.id}`);
await this.updateItemFromHistory(item, historyItem);
return item;
});

return Promise.all(promises);
}

updateItemFromHistory(
item: ScrobbleItemValues,
historyItem: Tv2PlayHistoryItem
): Promisable<void> {
item.watchedAt = historyItem.date ? Utils.unix(historyItem.date) : undefined;
item.progress = 100; //TODO not present in API. There might be a separate progress API.
}

async getItem(id: string): Promise<ScrobbleItem> {
Expand Down
2 changes: 1 addition & 1 deletion src/services/tv2-play/Tv2PlayParser.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { ScrobbleParser } from '@common/ScrobbleParser';
import { Tv2PlayApi } from '@/tv2-play/Tv2PlayApi';
import { Tv2PlayApi } from '@/services/tv2-play/Tv2PlayApi';

class _Tv2PlayParser extends ScrobbleParser {
constructor() {
Expand Down
4 changes: 2 additions & 2 deletions src/services/tv2-play/Tv2PlayService.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,6 @@ export const Tv2PlayService = new Service({
homePage: 'https://play.tv2.no',
hostPatterns: ['*://*.tv2.no/*'],
hasScrobbler: true,
hasSync: false,
hasAutoSync: false,
hasSync: true,
hasAutoSync: true,
});
2 changes: 1 addition & 1 deletion src/services/tv2-play/tv2-play.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { init } from '@service';
import '@/tv2-play/Tv2PlayParser';
import '@/services/tv2-play/Tv2PlayParser';

void init('tv2-play');