This repository has been archived on 2024-09-13. You can view files and clone it, but cannot push or open issues or pull requests.
BetterRaid_OLD/App.axaml.cs

211 lines
7.9 KiB
C#

using System;
using System.IO;
using System.Linq;
using Avalonia;
using Avalonia.Controls.ApplicationLifetimes;
using Avalonia.Data.Core.Plugins;
using Avalonia.Markup.Xaml;
using BetterRaid.Extensions;
using BetterRaid.Services;
using BetterRaid.Services.Implementations;
using BetterRaid.ViewModels;
using BetterRaid.Views;
using Microsoft.Extensions.DependencyInjection;
using TwitchLib.Api;
using TwitchLib.PubSub;
namespace BetterRaid;
public partial class App : Application
{
private readonly ServiceCollection _services = [];
private ServiceProvider? _provider;
private static TwitchAPI? _twitchApi;
private static bool _hasUserZnSubbed;
private static string _betterRaidDataPath = "";
private static string _twitchBroadcasterId = "";
private static string _twitchOAuthAccessToken = "";
private static string _twitchOAuthAccessTokenFilePath = "";
private const string TokenClientId = "kkxu4jorjrrc5jch1ito5i61hbev2o";
private const string TwitchOAuthRedirectUrl = "http://localhost:9900";
private const string TwitchOAuthResponseType = "token";
private static readonly string[] TwitchOAuthScopes = [
"channel:manage:raids",
"user:read:subscriptions"
];
internal static readonly string TwitchOAuthUrl = $"https://id.twitch.tv/oauth2/authorize"
+ $"?client_id={TokenClientId}"
+ $"&redirect_uri={TwitchOAuthRedirectUrl}"
+ $"&response_type={TwitchOAuthResponseType}"
+ $"&scope={string.Join("+", TwitchOAuthScopes)}";
public const string ChannelPlaceholderImageUrl = "https://cdn.pixabay.com/photo/2018/11/13/22/01/avatar-3814081_1280.png";
public static TwitchAPI? TwitchApi => _twitchApi;
public static bool HasUserZnSubbed => _hasUserZnSubbed;
public static string BetterRaidDataPath => _betterRaidDataPath;
public IServiceProvider? Provider => _provider;
public static string? TwitchBroadcasterId => _twitchBroadcasterId;
public static string TwitchOAuthAccessToken
{
get => _twitchOAuthAccessToken;
set
{
_twitchOAuthAccessToken = value;
InitTwitchClient(true);
}
}
public override void Initialize()
{
LoadTwitchToken();
InitializeServices();
AvaloniaXamlLoader.Load(_provider, this);
}
private void LoadTwitchToken()
{
var userHomeDir = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile);
_betterRaidDataPath = Environment.OSVersion.Platform switch
{
PlatformID.Win32NT => Path.Combine(userHomeDir, "AppData", "Roaming", "BetterRaid"),
PlatformID.Unix => Path.Combine(userHomeDir, ".config", "BetterRaid"),
PlatformID.MacOSX => Path.Combine(userHomeDir, "Library", "Application Support", "BetterRaid"),
_ => throw new PlatformNotSupportedException($"Your platform '{Environment.OSVersion.Platform}' is not supported. Please report this issue here: https://www.github.com/zion-networks/BetterRaid/issues")
};
if (!Directory.Exists(_betterRaidDataPath))
{
var di = Directory.CreateDirectory(_betterRaidDataPath);
if (di.Exists == false)
{
throw new Exception($"Failed to create directory '{_betterRaidDataPath}'");
}
}
_twitchOAuthAccessTokenFilePath = Path.Combine(_betterRaidDataPath, ".access_token");
if (!File.Exists(_twitchOAuthAccessTokenFilePath))
return;
_twitchOAuthAccessToken = File.ReadAllText(_twitchOAuthAccessTokenFilePath);
InitTwitchClient();
}
private void InitializeServices()
{
_services.AddSingleton<ITwitchDataService, TwitchDataService>();
_services.AddSingleton<ITwitchPubSubService, TwitchPubSubService>();
_services.AddTransient<MainWindowViewModel>();
_provider = _services.BuildServiceProvider();
}
public static void InitTwitchClient(bool overrideToken = false)
{
Console.WriteLine("[INFO] Initializing Twitch Client...");
if (string.IsNullOrEmpty(_twitchOAuthAccessToken))
{
Console.WriteLine("[ERROR] Failed to initialize Twitch Client: Access Token is empty!");
return;
}
_twitchApi = new TwitchAPI
{
Settings =
{
ClientId = TokenClientId,
AccessToken = _twitchOAuthAccessToken
}
};
Console.WriteLine("[INFO] Testing Twitch API connection...");
var user = _twitchApi.Helix.Users.GetUsersAsync().Result.Users.FirstOrDefault();
if (user == null)
{
_twitchApi = null;
Console.WriteLine("[ERROR] Failed to connect to Twitch API!");
return;
}
var channel = _twitchApi.Helix.Search
.SearchChannelsAsync(user.Login).Result.Channels
.FirstOrDefault(c => c.BroadcasterLogin == user.Login);
var userSubs = _twitchApi.Helix.Subscriptions.CheckUserSubscriptionAsync(
userId: user.Id,
broadcasterId: "1120558409"
).Result.Data;
if (userSubs is { Length: > 0 } && userSubs.Any(s => s.BroadcasterId == "1120558409"))
{
_hasUserZnSubbed = true;
}
if (channel == null)
{
Console.WriteLine($"[ERROR] Failed to get channel information for '{user.Login}'!");
return;
}
_twitchBroadcasterId = channel.Id;
Console.WriteLine("[INFO] Connected to Twitch API as '{0}'!", user.DisplayName);
if (!overrideToken)
return;
File.WriteAllText(_twitchOAuthAccessTokenFilePath, _twitchOAuthAccessToken);
switch (Environment.OSVersion.Platform)
{
case PlatformID.Win32NT:
File.SetAttributes(_twitchOAuthAccessTokenFilePath, File.GetAttributes(_twitchOAuthAccessTokenFilePath) | FileAttributes.Hidden);
break;
case PlatformID.Unix:
#pragma warning disable CA1416 // Validate platform compatibility
File.SetUnixFileMode(_twitchOAuthAccessTokenFilePath, UnixFileMode.UserRead);
#pragma warning restore CA1416 // Validate platform compatibility
break;
case PlatformID.MacOSX:
File.SetAttributes(_twitchOAuthAccessTokenFilePath, File.GetAttributes(_twitchOAuthAccessTokenFilePath) | FileAttributes.Hidden);
break;
default:
throw new PlatformNotSupportedException($"Your platform '{Environment.OSVersion.Platform}' is not supported. Please report this issue here: https://www.github.com/zion-networks/BetterRaid/issues");
}
}
public override void OnFrameworkInitializationCompleted()
{
BindingPlugins.DataValidators.RemoveAt(0);
switch (ApplicationLifetime)
{
case IClassicDesktopStyleApplicationLifetime desktop:
desktop.MainWindow = new MainWindow();
desktop.MainWindow.InjectDataContext<MainWindowViewModel>();
break;
case ISingleViewApplicationLifetime singleViewPlatform:
singleViewPlatform.MainView = new MainWindow();
singleViewPlatform.MainView.InjectDataContext<MainWindowViewModel>();
break;
}
base.OnFrameworkInitializationCompleted();
}
}