mirror of
https://github.com/FrankerFaceZ/FrankerFaceZ.git
synced 2025-08-06 06:10:54 +00:00
Fix Auto Host Management (#830)
Since Twitch has removed their old v4 endpoints for auto host related stuff this needed to be switched over to GQL.
This commit is contained in:
parent
ed0577f09e
commit
fa5333d462
6 changed files with 131 additions and 127 deletions
13
src/sites/twitch-twilight/modules/autohost_list.gql
Normal file
13
src/sites/twitch-twilight/modules/autohost_list.gql
Normal file
|
@ -0,0 +1,13 @@
|
||||||
|
query FFZ_AutoHostList($id: ID, $login: String) {
|
||||||
|
user(id: $id, login: $login) {
|
||||||
|
id,
|
||||||
|
autohostChannels {
|
||||||
|
nodes {
|
||||||
|
id
|
||||||
|
login
|
||||||
|
displayName
|
||||||
|
profileImageURL(width: 50)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
17
src/sites/twitch-twilight/modules/autohost_list_mutate.gql
Normal file
17
src/sites/twitch-twilight/modules/autohost_list_mutate.gql
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
mutation FFZ_AutoHostListUpdate($userID: ID!, $channelIDs: [ID!]!) {
|
||||||
|
setAutohostChannels(input: {
|
||||||
|
userID: $userID,
|
||||||
|
channelIDs: $channelIDs
|
||||||
|
}) {
|
||||||
|
user {
|
||||||
|
autohostChannels {
|
||||||
|
nodes {
|
||||||
|
id
|
||||||
|
login
|
||||||
|
displayName
|
||||||
|
profileImageURL(width: 50)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
11
src/sites/twitch-twilight/modules/autohost_settings.gql
Normal file
11
src/sites/twitch-twilight/modules/autohost_settings.gql
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
query FFZ_AutoHostSettings($id: ID, $login: String) {
|
||||||
|
user(id: $id, login: $login) {
|
||||||
|
id,
|
||||||
|
autohostSettings {
|
||||||
|
deprioritizeVodcast,
|
||||||
|
enabled,
|
||||||
|
strategy,
|
||||||
|
teamHost
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,24 @@
|
||||||
|
mutation FFZ_AutoHostSettingsUpdate(
|
||||||
|
$userID: ID!,
|
||||||
|
$isEnabled: Boolean,
|
||||||
|
$strategy: AutohostSettingsStrategy,
|
||||||
|
$willAutohostTeam: Boolean,
|
||||||
|
$willPrioritizeAutohost: Boolean
|
||||||
|
) {
|
||||||
|
updateAutohostSettings(input: {
|
||||||
|
userID: $userID,
|
||||||
|
isEnabled: $isEnabled,
|
||||||
|
strategy: $strategy,
|
||||||
|
willAutohostTeam: $willAutohostTeam,
|
||||||
|
willPrioritizeAutohost: $willPrioritizeAutohost,
|
||||||
|
}) {
|
||||||
|
user {
|
||||||
|
autohostSettings {
|
||||||
|
deprioritizeVodcast,
|
||||||
|
enabled,
|
||||||
|
strategy,
|
||||||
|
teamHost
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -22,18 +22,18 @@
|
||||||
>
|
>
|
||||||
<div
|
<div
|
||||||
v-for="host in hosts"
|
v-for="host in hosts"
|
||||||
:key="host._id"
|
:key="host.id"
|
||||||
:data-id="host._id"
|
:data-id="host.id"
|
||||||
class="tw-border-t ffz--host-user"
|
class="tw-border-t ffz--host-user"
|
||||||
>
|
>
|
||||||
<div class="tw-interactable tw-interactable--inverted">
|
<div class="tw-interactable tw-interactable--inverted">
|
||||||
<div class="tw-align-items-center tw-flex tw-flex-row tw-flex-nowrap tw-mg-x-1">
|
<div class="tw-align-items-center tw-flex tw-flex-row tw-flex-nowrap tw-mg-x-1">
|
||||||
<figure class="ffz-i-ellipsis-vert handle" />
|
<figure class="ffz-i-ellipsis-vert handle" />
|
||||||
<div class="ffz-channel-avatar">
|
<div class="ffz-channel-avatar">
|
||||||
<img :src="host.logo" :alt="host.display_name + '(' + host.name + ')'">
|
<img :src="host.profileImageURL" :alt="host.displayName + '(' + host.login + ')'">
|
||||||
</div>
|
</div>
|
||||||
<p class="tw-ellipsis tw-flex-grow-1 tw-mg-l-1 tw-font-size-5">
|
<p class="tw-ellipsis tw-flex-grow-1 tw-mg-l-1 tw-font-size-5">
|
||||||
{{ host.name }}
|
{{ host.login }}
|
||||||
</p>
|
</p>
|
||||||
<div class="tw-flex-grow-1 tw-pd-x-2" />
|
<div class="tw-flex-grow-1 tw-pd-x-2" />
|
||||||
<button class="tw-button-icon tw-mg-x-05 ffz--host-remove-user" @click="removeFromHosts">
|
<button class="tw-button-icon tw-mg-x-05 ffz--host-remove-user" @click="removeFromHosts">
|
||||||
|
@ -91,14 +91,14 @@
|
||||||
<div class="ffz--widget ffz--checkbox">
|
<div class="ffz--widget ffz--checkbox">
|
||||||
<div class="tw-flex tw-align-items-center tw-checkbox">
|
<div class="tw-flex tw-align-items-center tw-checkbox">
|
||||||
<input
|
<input
|
||||||
id="autoHostSettings:team_host"
|
id="autoHostSettings:teamHost"
|
||||||
:checked="autoHostSettings.team_host"
|
:checked="autoHostSettings.teamHost"
|
||||||
type="checkbox"
|
type="checkbox"
|
||||||
class="tw-checkbox__input"
|
class="tw-checkbox__input"
|
||||||
data-setting="team_host"
|
data-setting="teamHost"
|
||||||
@change="updateCheckbox"
|
@change="updateCheckbox"
|
||||||
>
|
>
|
||||||
<label for="autoHostSettings:team_host" class="tw-checkbox__label">
|
<label for="autoHostSettings:teamHost" class="tw-checkbox__label">
|
||||||
<span class="tw-mg-l-1">
|
<span class="tw-mg-l-1">
|
||||||
{{ t('metadata.host.setting.team-hosting.title', 'Team Hosting') }}
|
{{ t('metadata.host.setting.team-hosting.title', 'Team Hosting') }}
|
||||||
</span>
|
</span>
|
||||||
|
@ -113,14 +113,14 @@
|
||||||
<div class="ffz--widget ffz--checkbox">
|
<div class="ffz--widget ffz--checkbox">
|
||||||
<div class="tw-flex tw-align-items-center tw-checkbox">
|
<div class="tw-flex tw-align-items-center tw-checkbox">
|
||||||
<input
|
<input
|
||||||
id="autoHostSettings:vodcast_hosting"
|
id="autoHostSettings:deprioritizeVodcast"
|
||||||
:checked="!autoHostSettings.deprioritize_vodcast"
|
:checked="!autoHostSettings.deprioritizeVodcast"
|
||||||
type="checkbox"
|
type="checkbox"
|
||||||
class="tw-checkbox__input"
|
class="tw-checkbox__input"
|
||||||
data-setting="deprioritize_vodcast"
|
data-setting="deprioritizeVodcast"
|
||||||
@change="updateCheckbox"
|
@change="updateCheckbox"
|
||||||
>
|
>
|
||||||
<label for="autoHostSettings:vodcast_hosting" class="tw-checkbox__label">
|
<label for="autoHostSettings:deprioritizeVodcast" class="tw-checkbox__label">
|
||||||
<span class="tw-mg-l-1">
|
<span class="tw-mg-l-1">
|
||||||
{{ t('metadata.host.setting.vodcast-hosting.title', 'Vodcast Hosting') }}
|
{{ t('metadata.host.setting.vodcast-hosting.title', 'Vodcast Hosting') }}
|
||||||
</span>
|
</span>
|
||||||
|
@ -131,26 +131,6 @@
|
||||||
<a href="https://blog.twitch.tv/vodcast-brings-the-twitch-community-experience-to-uploads-54098498715" target="_blank" rel="noopener">{{ t('metadata.host.setting.vodcast-hosting.link', 'Learn about Vodcasts') }}</a>
|
<a href="https://blog.twitch.tv/vodcast-brings-the-twitch-community-experience-to-uploads-54098498715" target="_blank" rel="noopener">{{ t('metadata.host.setting.vodcast-hosting.link', 'Learn about Vodcasts') }}</a>
|
||||||
</section>
|
</section>
|
||||||
</div>
|
</div>
|
||||||
<div class="ffz--widget ffz--checkbox">
|
|
||||||
<div class="tw-flex tw-align-items-center tw-checkbox">
|
|
||||||
<input
|
|
||||||
id="autoHostSettings:recommended_host"
|
|
||||||
:checked="autoHostSettings.recommended_host"
|
|
||||||
type="checkbox"
|
|
||||||
class="tw-checkbox__input"
|
|
||||||
data-setting="recommended_host"
|
|
||||||
@change="updateCheckbox"
|
|
||||||
>
|
|
||||||
<label for="autoHostSettings:recommended_host" class="tw-checkbox__label">
|
|
||||||
<span class="tw-mg-l-1">
|
|
||||||
{{ t('metadata.host.setting.recommended-hosting.title', 'Auto Host Channels Similar To Yours') }}
|
|
||||||
</span>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
<section class="tw-c-text-alt-2 ffz-checkbox-description">
|
|
||||||
{{ t('metadata.host.setting.recommended-hosting.description', 'Streamers on your primary team & host list will always be hosted first') }}
|
|
||||||
</section>
|
|
||||||
</div>
|
|
||||||
<div class="ffz--widget ffz--checkbox">
|
<div class="ffz--widget ffz--checkbox">
|
||||||
<div class="tw-flex tw-align-items-center tw-checkbox">
|
<div class="tw-flex tw-align-items-center tw-checkbox">
|
||||||
<input
|
<input
|
||||||
|
|
|
@ -5,6 +5,7 @@
|
||||||
// ============================================================================
|
// ============================================================================
|
||||||
|
|
||||||
import Module from 'utilities/module';
|
import Module from 'utilities/module';
|
||||||
|
import {get} from 'utilities/object';
|
||||||
import {createElement} from 'utilities/dom';
|
import {createElement} from 'utilities/dom';
|
||||||
|
|
||||||
const HOST_ERRORS = {
|
const HOST_ERRORS = {
|
||||||
|
@ -27,6 +28,7 @@ export default class HostButton extends Module {
|
||||||
this.inject('site');
|
this.inject('site');
|
||||||
this.inject('site.fine');
|
this.inject('site.fine');
|
||||||
this.inject('site.chat');
|
this.inject('site.chat');
|
||||||
|
this.inject('site.twitch_data');
|
||||||
this.inject('i18n');
|
this.inject('i18n');
|
||||||
this.inject('metadata');
|
this.inject('metadata');
|
||||||
this.inject('settings');
|
this.inject('settings');
|
||||||
|
@ -224,14 +226,20 @@ export default class HostButton extends Module {
|
||||||
if (this._auto_host_tip) this._auto_host_tip.update();
|
if (this._auto_host_tip) this._auto_host_tip.update();
|
||||||
},
|
},
|
||||||
updateCheckbox: e => {
|
updateCheckbox: e => {
|
||||||
const t = e.target,
|
const t = e.target;
|
||||||
setting = t.dataset.setting;
|
let setting = t.dataset.setting,
|
||||||
let state = t.checked;
|
state = t.checked;
|
||||||
|
|
||||||
if ( setting === 'strategy' )
|
if ( setting === 'enabled' )
|
||||||
|
setting = 'isEnabled';
|
||||||
|
else if ( setting === 'teamHost' )
|
||||||
|
setting = 'willAutohostTeam';
|
||||||
|
else if ( setting === 'strategy' )
|
||||||
state = state ? 'random' : 'ordered';
|
state = state ? 'random' : 'ordered';
|
||||||
else if ( setting === 'deprioritize_vodcast' )
|
else if ( setting === 'deprioritizeVodcast' ) {
|
||||||
|
setting = 'willPrioritizeAutohost';
|
||||||
state = ! state;
|
state = ! state;
|
||||||
|
}
|
||||||
|
|
||||||
this.updateAutoHostSetting(setting, state);
|
this.updateAutoHostSetting(setting, state);
|
||||||
}
|
}
|
||||||
|
@ -246,26 +254,17 @@ export default class HostButton extends Module {
|
||||||
if ( ! user )
|
if ( ! user )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
let data;
|
const result = await this.twitch_data.queryApollo(
|
||||||
try {
|
await import(/* webpackChunkName: 'queries' */ './autohost_list.gql'),
|
||||||
data = await fetch('https://api.twitch.tv/kraken/autohost/list', {
|
{
|
||||||
headers: {
|
id: user.id
|
||||||
'Accept': 'application/vnd.twitchtv.v4+json',
|
},
|
||||||
'Authorization': `OAuth ${user.authToken}`
|
{
|
||||||
}
|
fetchPolicy: 'network-only'
|
||||||
}).then(r => {
|
}
|
||||||
if ( r.ok )
|
);
|
||||||
return r.json();
|
|
||||||
|
|
||||||
throw r.status;
|
return this.autoHosts = get('data.user.autohostChannels.nodes', result);
|
||||||
});
|
|
||||||
|
|
||||||
} catch(err) {
|
|
||||||
this.log.error('Error loading auto host list.', err);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
return this.autoHosts = data.targets;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async fetchAutoHostSettings() {
|
async fetchAutoHostSettings() {
|
||||||
|
@ -273,26 +272,17 @@ export default class HostButton extends Module {
|
||||||
if ( ! user )
|
if ( ! user )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
let data;
|
const result = await this.twitch_data.queryApollo(
|
||||||
try {
|
await import(/* webpackChunkName: 'queries' */ './autohost_settings.gql'),
|
||||||
data = await fetch('https://api.twitch.tv/kraken/autohost/settings', {
|
{
|
||||||
headers: {
|
id: user.id
|
||||||
'Accept': 'application/vnd.twitchtv.v4+json',
|
},
|
||||||
'Authorization': `OAuth ${user.authToken}`
|
{
|
||||||
}
|
fetchPolicy: 'network-only'
|
||||||
}).then(r => {
|
}
|
||||||
if ( r.ok )
|
);
|
||||||
return r.json();
|
|
||||||
|
|
||||||
throw r.status;
|
return this.autoHostSettings = get('data.user.autohostSettings', result);
|
||||||
});
|
|
||||||
|
|
||||||
} catch(err) {
|
|
||||||
this.log.error('Error loading auto host settings.', err);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
return this.autoHostSettings = data.settings;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
queueHostUpdate() {
|
queueHostUpdate() {
|
||||||
|
@ -312,12 +302,12 @@ export default class HostButton extends Module {
|
||||||
}
|
}
|
||||||
|
|
||||||
currentRoomInHosts() {
|
currentRoomInHosts() {
|
||||||
return this.getAutoHostIDs(this.autoHosts).includes(parseInt(this._current_channel_id, 10));
|
return this.getAutoHostIDs(this.autoHosts).includes(this._current_channel_id);
|
||||||
}
|
}
|
||||||
|
|
||||||
addCurrentRoomToHosts() {
|
addCurrentRoomToHosts() {
|
||||||
const newHosts = this.autoHosts.slice(0);
|
const newHosts = this.autoHosts.slice(0);
|
||||||
newHosts.push({ _id: parseInt(this._current_channel_id, 10)});
|
newHosts.push({ id: this._current_channel_id});
|
||||||
|
|
||||||
this.updateAutoHosts(newHosts);
|
this.updateAutoHosts(newHosts);
|
||||||
}
|
}
|
||||||
|
@ -327,7 +317,7 @@ export default class HostButton extends Module {
|
||||||
|
|
||||||
const newHosts = [];
|
const newHosts = [];
|
||||||
for (let i = 0; i < this.autoHosts.length; i++) {
|
for (let i = 0; i < this.autoHosts.length; i++) {
|
||||||
if (this.autoHosts[i]._id != id) newHosts.push(this.autoHosts[i]);
|
if (this.autoHosts[i].id != id) newHosts.push(this.autoHosts[i]);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.updateAutoHosts(newHosts);
|
this.updateAutoHosts(newHosts);
|
||||||
|
@ -337,7 +327,7 @@ export default class HostButton extends Module {
|
||||||
const ids = [];
|
const ids = [];
|
||||||
if (hosts) {
|
if (hosts) {
|
||||||
for (let i = 0; i < hosts.length; i++) {
|
for (let i = 0; i < hosts.length; i++) {
|
||||||
ids.push(hosts[i]._id);
|
ids.push(hosts[i].id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return ids;
|
return ids;
|
||||||
|
@ -348,32 +338,17 @@ export default class HostButton extends Module {
|
||||||
if ( ! user )
|
if ( ! user )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
let data;
|
const autoHosts = this.getAutoHostIDs(newHosts);
|
||||||
try {
|
|
||||||
const form = new URLSearchParams();
|
|
||||||
const autoHosts = this.getAutoHostIDs(newHosts);
|
|
||||||
form.append('targets', autoHosts.join(','));
|
|
||||||
|
|
||||||
data = await fetch('https://api.twitch.tv/kraken/autohost/list', {
|
const result = await this.twitch_data.mutate({
|
||||||
headers: {
|
mutation: await import(/* webpackChunkName: 'queries' */ './autohost_list_mutate.gql'),
|
||||||
'Accept': 'application/vnd.twitchtv.v4+json',
|
variables: {
|
||||||
'Authorization': `OAuth ${user.authToken}`
|
userID: user.id,
|
||||||
},
|
channelIDs: autoHosts
|
||||||
method: autoHosts.length ? 'PUT' : 'DELETE',
|
}
|
||||||
body: autoHosts.length ? form : undefined
|
});
|
||||||
}).then(r => {
|
|
||||||
if ( r.ok )
|
|
||||||
return r.json();
|
|
||||||
|
|
||||||
throw r.status;
|
this.autoHosts = get('data.setAutohostChannels.user.autohostChannels.nodes', result);
|
||||||
});
|
|
||||||
|
|
||||||
} catch(err) {
|
|
||||||
this.log.error('Error updating auto host list.', err);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
this.autoHosts = data.targets;
|
|
||||||
if (this.vueHostMenu) {
|
if (this.vueHostMenu) {
|
||||||
this.vueHostMenu.data.hosts = this.autoHosts;
|
this.vueHostMenu.data.hosts = this.autoHosts;
|
||||||
this.vueHostMenu.data.addedToHosts = this.currentRoomInHosts();
|
this.vueHostMenu.data.addedToHosts = this.currentRoomInHosts();
|
||||||
|
@ -385,31 +360,15 @@ export default class HostButton extends Module {
|
||||||
if ( ! user )
|
if ( ! user )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
let data;
|
const result = await this.twitch_data.mutate({
|
||||||
try {
|
mutation: await import(/* webpackChunkName: 'queries' */ './autohost_settings_mutate.gql'),
|
||||||
const form = new URLSearchParams();
|
variables: {
|
||||||
form.append(setting, newValue);
|
userID: user.id,
|
||||||
|
[setting]: newValue
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
data = await fetch('https://api.twitch.tv/kraken/autohost/settings', {
|
this.autoHostSettings = get('data.updateAutohostSettings.user.autohostSettings', result);
|
||||||
headers: {
|
|
||||||
'Accept': 'application/vnd.twitchtv.v4+json',
|
|
||||||
'Authorization': `OAuth ${user.authToken}`
|
|
||||||
},
|
|
||||||
method: 'PUT',
|
|
||||||
body: form
|
|
||||||
}).then(r => {
|
|
||||||
if ( r.ok )
|
|
||||||
return r.json();
|
|
||||||
|
|
||||||
throw r.status;
|
|
||||||
});
|
|
||||||
|
|
||||||
} catch(err) {
|
|
||||||
this.log.error('Error updating auto host setting.', err);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
this.autoHostSettings = data.settings;
|
|
||||||
if (this.vueHostMenu) {
|
if (this.vueHostMenu) {
|
||||||
this.vueHostMenu.data.autoHostSettings = this.autoHostSettings;
|
this.vueHostMenu.data.autoHostSettings = this.autoHostSettings;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue