2024-03-03 03:14:07 +01:00
|
|
|
|
using System.Diagnostics;
|
|
|
|
|
|
using VDownload.Services.Data.Configuration;
|
2024-02-14 02:07:22 +01:00
|
|
|
|
using VDownload.Services.Utility.HttpClient;
|
2024-03-03 03:14:07 +01:00
|
|
|
|
using VDownload.Sources.Twitch.Api.GQL.GetClipToken.Request;
|
|
|
|
|
|
using VDownload.Sources.Twitch.Api.GQL.GetClipToken.Response;
|
2024-02-13 02:59:40 +01:00
|
|
|
|
using VDownload.Sources.Twitch.Api.GQL.GetVideoToken.Response;
|
2024-03-03 03:14:07 +01:00
|
|
|
|
using VDownload.Sources.Twitch.Api.Helix.GetClips.Response;
|
2024-02-28 01:22:13 +01:00
|
|
|
|
using VDownload.Sources.Twitch.Api.Helix.GetUsers.Response;
|
2024-02-13 02:59:40 +01:00
|
|
|
|
using VDownload.Sources.Twitch.Api.Helix.GetVideos.Response;
|
2024-03-03 03:14:07 +01:00
|
|
|
|
using VDownload.Sources.Twitch.Configuration.Models;
|
2024-02-13 02:59:40 +01:00
|
|
|
|
using VDownload.Sources.Twitch.Search.Models.GetVideoToken.Request;
|
|
|
|
|
|
|
|
|
|
|
|
namespace VDownload.Sources.Twitch.Api
|
|
|
|
|
|
{
|
|
|
|
|
|
public interface ITwitchApiService
|
|
|
|
|
|
{
|
|
|
|
|
|
Task<string> AuthValidate(byte[] token);
|
|
|
|
|
|
Task<GetVideoTokenResponse> GQLGetVideoToken(string id);
|
2024-03-03 03:14:07 +01:00
|
|
|
|
Task<GetClipTokenResponse> GQLGetClipToken(string id);
|
2024-02-28 01:22:13 +01:00
|
|
|
|
Task<GetUsersResponse> HelixGetUser(string login, byte[] token);
|
|
|
|
|
|
Task<GetVideosResponse> HelixGetVideo(string id, byte[] token);
|
|
|
|
|
|
Task<GetVideosResponse> HelixGetUserVideos(string user_id, byte[] token, int count, string? cursor = null);
|
2024-03-03 03:14:07 +01:00
|
|
|
|
Task<GetClipsResponse> HelixGetClip(string id, byte[] token);
|
2024-02-13 02:59:40 +01:00
|
|
|
|
Task<string> UsherGetVideoPlaylist(string id, string videoToken, string videoTokenSignature);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
public class TwitchApiService : ITwitchApiService
|
|
|
|
|
|
{
|
|
|
|
|
|
#region SERVICES
|
|
|
|
|
|
|
2024-02-14 02:07:22 +01:00
|
|
|
|
protected readonly IConfigurationService _configurationService;
|
|
|
|
|
|
protected readonly IHttpClientService _httpClientService;
|
2024-02-13 02:59:40 +01:00
|
|
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#region CONSTRUCTORS
|
|
|
|
|
|
|
2024-02-14 02:07:22 +01:00
|
|
|
|
public TwitchApiService(IConfigurationService configurationService, IHttpClientService httpClientService)
|
2024-02-13 02:59:40 +01:00
|
|
|
|
{
|
2024-02-14 02:07:22 +01:00
|
|
|
|
_configurationService = configurationService;
|
2024-02-13 02:59:40 +01:00
|
|
|
|
_httpClientService = httpClientService;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
#region PUBLIC METHODS
|
|
|
|
|
|
|
|
|
|
|
|
public async Task<string> AuthValidate(byte[] token)
|
|
|
|
|
|
{
|
2024-02-14 02:07:22 +01:00
|
|
|
|
Token tokenData = new Token(_configurationService.Twitch.Api.Auth.TokenSchema, token);
|
|
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.GET, _configurationService.Twitch.Api.Auth.Endpoints.Validate);
|
2024-02-13 02:59:40 +01:00
|
|
|
|
request.Headers.Add("Authorization", $"{tokenData}");
|
|
|
|
|
|
return await _httpClientService.SendRequestAsync(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2024-02-28 01:22:13 +01:00
|
|
|
|
public async Task<GetUsersResponse> HelixGetUser(string login, byte[] token)
|
|
|
|
|
|
{
|
|
|
|
|
|
Token tokenData = new Token(_configurationService.Twitch.Api.Helix.TokenSchema, token);
|
|
|
|
|
|
|
|
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.GET, _configurationService.Twitch.Api.Helix.Endpoints.GetUsers);
|
|
|
|
|
|
|
|
|
|
|
|
request.Query.Add("login", login);
|
|
|
|
|
|
|
|
|
|
|
|
request.Headers.Add("Authorization", $"{tokenData}");
|
|
|
|
|
|
request.Headers.Add("Client-Id", _configurationService.Twitch.Api.Helix.ClientId);
|
|
|
|
|
|
|
|
|
|
|
|
return await _httpClientService.SendRequestAsync<GetUsersResponse>(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
public async Task<GetVideosResponse> HelixGetVideo(string id, byte[] token)
|
2024-02-13 02:59:40 +01:00
|
|
|
|
{
|
2024-02-14 02:07:22 +01:00
|
|
|
|
Token tokenData = new Token(_configurationService.Twitch.Api.Helix.TokenSchema, token);
|
2024-02-13 02:59:40 +01:00
|
|
|
|
|
2024-02-14 02:07:22 +01:00
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.GET, _configurationService.Twitch.Api.Helix.Endpoints.GetVideos);
|
2024-02-28 01:22:13 +01:00
|
|
|
|
|
2024-02-13 02:59:40 +01:00
|
|
|
|
request.Query.Add("id", id);
|
2024-02-28 01:22:13 +01:00
|
|
|
|
|
|
|
|
|
|
request.Headers.Add("Authorization", tokenData.ToString());
|
|
|
|
|
|
request.Headers.Add("Client-Id", _configurationService.Twitch.Api.Helix.ClientId);
|
|
|
|
|
|
|
|
|
|
|
|
return await _httpClientService.SendRequestAsync<GetVideosResponse>(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
public async Task<GetVideosResponse> HelixGetUserVideos(string user_id, byte[] token, int count, string? cursor = null)
|
|
|
|
|
|
{
|
|
|
|
|
|
Token tokenData = new Token(_configurationService.Twitch.Api.Helix.TokenSchema, token);
|
|
|
|
|
|
|
|
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.GET, _configurationService.Twitch.Api.Helix.Endpoints.GetVideos);
|
|
|
|
|
|
|
|
|
|
|
|
request.Query.Add("user_id", user_id);
|
|
|
|
|
|
request.Query.Add("first", count);
|
|
|
|
|
|
if (cursor is not null)
|
|
|
|
|
|
{
|
|
|
|
|
|
request.Query.Add("after", cursor);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2024-02-13 02:59:40 +01:00
|
|
|
|
request.Headers.Add("Authorization", tokenData.ToString());
|
2024-02-14 02:07:22 +01:00
|
|
|
|
request.Headers.Add("Client-Id", _configurationService.Twitch.Api.Helix.ClientId);
|
2024-02-13 02:59:40 +01:00
|
|
|
|
|
|
|
|
|
|
return await _httpClientService.SendRequestAsync<GetVideosResponse>(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2024-03-03 03:14:07 +01:00
|
|
|
|
public async Task<GetClipsResponse> HelixGetClip(string id, byte[] token)
|
|
|
|
|
|
{
|
|
|
|
|
|
Token tokenData = new Token(_configurationService.Twitch.Api.Helix.TokenSchema, token);
|
|
|
|
|
|
|
|
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.GET, _configurationService.Twitch.Api.Helix.Endpoints.GetClips);
|
|
|
|
|
|
|
|
|
|
|
|
request.Query.Add("id", id);
|
|
|
|
|
|
|
|
|
|
|
|
request.Headers.Add("Authorization", tokenData.ToString());
|
|
|
|
|
|
request.Headers.Add("Client-Id", _configurationService.Twitch.Api.Helix.ClientId);
|
|
|
|
|
|
|
|
|
|
|
|
return await _httpClientService.SendRequestAsync<GetClipsResponse>(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2024-02-13 02:59:40 +01:00
|
|
|
|
public async Task<GetVideoTokenResponse> GQLGetVideoToken(string id)
|
|
|
|
|
|
{
|
|
|
|
|
|
GetVideoTokenRequest requestBody = new GetVideoTokenRequest
|
|
|
|
|
|
{
|
2024-02-14 02:07:22 +01:00
|
|
|
|
OperationName = _configurationService.Twitch.Api.Gql.Queries.GetVideoToken.OperationName,
|
|
|
|
|
|
Query = _configurationService.Twitch.Api.Gql.Queries.GetVideoToken.Query,
|
2024-02-13 02:59:40 +01:00
|
|
|
|
Variables = new GetVideoTokenVariables
|
|
|
|
|
|
{
|
|
|
|
|
|
IsLive = false,
|
|
|
|
|
|
Login = string.Empty,
|
|
|
|
|
|
IsVod = true,
|
|
|
|
|
|
VodID = id,
|
|
|
|
|
|
PlayerType = "embed"
|
|
|
|
|
|
}
|
|
|
|
|
|
};
|
|
|
|
|
|
|
2024-02-14 02:07:22 +01:00
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.POST, _configurationService.Twitch.Api.Gql.Endpoint)
|
2024-02-13 02:59:40 +01:00
|
|
|
|
{
|
|
|
|
|
|
Body = requestBody,
|
|
|
|
|
|
};
|
2024-02-14 02:07:22 +01:00
|
|
|
|
request.Headers.Add("Client-Id", _configurationService.Twitch.Api.Gql.ClientId);
|
2024-02-13 02:59:40 +01:00
|
|
|
|
return await _httpClientService.SendRequestAsync<GetVideoTokenResponse>(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2024-03-03 03:14:07 +01:00
|
|
|
|
public async Task<GetClipTokenResponse> GQLGetClipToken(string id)
|
|
|
|
|
|
{
|
|
|
|
|
|
Gql config = _configurationService.Twitch.Api.Gql;
|
|
|
|
|
|
|
|
|
|
|
|
GetClipTokenRequest requestBody = new GetClipTokenRequest
|
|
|
|
|
|
{
|
|
|
|
|
|
OperationName = config.Queries.GetClipToken.OperationName,
|
|
|
|
|
|
Variables = new GetClipTokenVariables
|
|
|
|
|
|
{
|
|
|
|
|
|
Slug = id
|
|
|
|
|
|
},
|
|
|
|
|
|
Extensions = new GQL.GetClipToken.Request.GetClipTokenExtensions
|
|
|
|
|
|
{
|
|
|
|
|
|
PersistedQuery = new GetClipTokenPersistedQuery
|
|
|
|
|
|
{
|
|
|
|
|
|
Version = config.Queries.GetClipToken.PersistedQueryVersion,
|
|
|
|
|
|
Sha256Hash = config.Queries.GetClipToken.PersistedQueryHash,
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.POST, config.Endpoint)
|
|
|
|
|
|
{
|
|
|
|
|
|
Body = requestBody,
|
|
|
|
|
|
};
|
|
|
|
|
|
request.Headers.Add("Client-Id", config.ClientId);
|
|
|
|
|
|
|
|
|
|
|
|
return await _httpClientService.SendRequestAsync<GetClipTokenResponse>(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2024-02-13 02:59:40 +01:00
|
|
|
|
public async Task<string> UsherGetVideoPlaylist(string id, string videoToken, string videoTokenSignature)
|
|
|
|
|
|
{
|
2024-02-14 02:07:22 +01:00
|
|
|
|
string url = string.Format(_configurationService.Twitch.Api.Usher.Endpoints.GetVideoPlaylist, id);
|
2024-02-13 02:59:40 +01:00
|
|
|
|
HttpRequest request = new HttpRequest(HttpMethodType.GET, url);
|
|
|
|
|
|
request.Query.Add("token", videoToken);
|
|
|
|
|
|
request.Query.Add("sig", videoTokenSignature);
|
|
|
|
|
|
request.Query.Add("allow_source", true);
|
|
|
|
|
|
request.Query.Add("allow_audio_only", true);
|
|
|
|
|
|
request.Query.Add("platform", "web");
|
|
|
|
|
|
request.Query.Add("player_backend", "mediaplayer");
|
|
|
|
|
|
request.Query.Add("playlist_include_framerate", true);
|
|
|
|
|
|
request.Query.Add("supported_codecs", "av1,h264");
|
|
|
|
|
|
return await _httpClientService.SendRequestAsync(request);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
}
|
|
|
|
|
|
}
|