Started adding authentication to extension settings.

dashboard
Pat Hartl 2023-01-05 01:07:17 -06:00
parent c18cb1d94b
commit 40ea196594
9 changed files with 184 additions and 48 deletions

View File

@ -3,6 +3,7 @@ using RestSharp;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Net;
using System.Text; using System.Text;
using System.Threading.Tasks; using System.Threading.Tasks;
@ -11,12 +12,55 @@ namespace LANCommander.Playnite.Extension
internal class LANCommanderClient internal class LANCommanderClient
{ {
private readonly RestClient Client; private readonly RestClient Client;
private AuthToken Token;
public LANCommanderClient() public LANCommanderClient()
{ {
Client = new RestClient("https://localhost:7087"); Client = new RestClient("https://localhost:7087");
} }
private T PostRequest<T>(string route, object body)
{
var request = new RestRequest(route)
.AddJsonBody(body)
.AddHeader("Authorization", $"Bearer {Token.AccessToken}");
var response = Client.Post<T>(request);
return response.Data;
}
public AuthResponse Authenticate(string username, string password)
{
var response = Client.Post<AuthResponse>(new RestRequest("/api/Auth").AddJsonBody(new AuthRequest()
{
UserName = username,
Password = password
}));
return response.Data;
}
public AuthResponse RefreshToken(AuthToken token)
{
var request = new RestRequest("/api/Auth/Refresh")
.AddJsonBody(token);
var response = Client.Post<AuthResponse>(request);
return response.Data;
}
public bool ValidateToken(AuthToken token)
{
var request = new RestRequest("/api/Auth/Validate")
.AddHeader("Authorization", $"Bearer {token.AccessToken}");
var response = Client.Post(request);
return response.StatusCode == HttpStatusCode.OK;
}
public IEnumerable<Game> GetGames() public IEnumerable<Game> GetGames()
{ {
var response = Client.Get<IEnumerable<Game>>(new RestRequest("/api/Games")); var response = Client.Get<IEnumerable<Game>>(new RestRequest("/api/Games"));

View File

@ -13,7 +13,8 @@ namespace LANCommander.Playnite.Extension
public override void Open() public override void Open()
{ {
throw new NotImplementedException();
System.Diagnostics.Process.Start("https://localhost:7087");
} }
} }
} }

View File

@ -13,8 +13,8 @@ namespace LANCommander.Playnite.Extension
public class PlayniteLibraryPlugin : LibraryPlugin public class PlayniteLibraryPlugin : LibraryPlugin
{ {
public static readonly ILogger Logger = LogManager.GetLogger(); public static readonly ILogger Logger = LogManager.GetLogger();
private SettingsViewModel Settings { get; set; } private PlayniteSettingsViewModel Settings { get; set; }
private LANCommanderClient LANCommander { get; set; } internal LANCommanderClient LANCommander { get; set; }
public override Guid Id { get; } = Guid.Parse("48e1bac7-e0a0-45d7-ba83-36f5e9e959fc"); public override Guid Id { get; } = Guid.Parse("48e1bac7-e0a0-45d7-ba83-36f5e9e959fc");
public override string Name => "LANCommander"; public override string Name => "LANCommander";
@ -23,7 +23,7 @@ namespace LANCommander.Playnite.Extension
public PlayniteLibraryPlugin(IPlayniteAPI api) : base(api) public PlayniteLibraryPlugin(IPlayniteAPI api) : base(api)
{ {
LANCommander = new LANCommanderClient(); LANCommander = new LANCommanderClient();
Settings = new SettingsViewModel(this); Settings = new PlayniteSettingsViewModel(this);
Properties = new LibraryPluginProperties Properties = new LibraryPluginProperties
{ {
HasSettings = true, HasSettings = true,
@ -31,6 +31,8 @@ namespace LANCommander.Playnite.Extension
} }
public override IEnumerable<GameMetadata> GetGames(LibraryGetGamesArgs args) public override IEnumerable<GameMetadata> GetGames(LibraryGetGamesArgs args)
{
try
{ {
// Implement LANCommander client here // Implement LANCommander client here
var games = LANCommander.GetGames().Select(g => new GameMetadata() var games = LANCommander.GetGames().Select(g => new GameMetadata()
@ -45,15 +47,36 @@ namespace LANCommander.Playnite.Extension
return games; return games;
} }
catch
{
return new List<GameMetadata>();
}
}
public override ISettings GetSettings(bool firstRunSettings) public override ISettings GetSettings(bool firstRunSettings)
{ {
return base.GetSettings(firstRunSettings); return Settings;
} }
public override UserControl GetSettingsView(bool firstRunView) public override UserControl GetSettingsView(bool firstRunView)
{ {
return base.GetSettingsView(firstRunView); return new PlayniteSettingsView(this);
}
public void ShowAuthenticationWindow()
{
var window = PlayniteApi.Dialogs.CreateWindow(new WindowCreationOptions()
{
ShowMinimizeButton = false,
});
window.Title = "Authenticate to LANCommander";
window.Content = new PlayniteSettingsView(this);
window.Owner = PlayniteApi.Dialogs.GetCurrentAppWindow();
window.WindowStartupLocation = System.Windows.WindowStartupLocation.CenterOwner;
window.ShowDialog();
} }
} }
} }

View File

@ -8,44 +8,44 @@ using System.Threading.Tasks;
namespace LANCommander.Playnite.Extension namespace LANCommander.Playnite.Extension
{ {
public class PlayniteSettings : ObservableObject public class PlayniteSettingsViewModel : ObservableObject, ISettings
{
private string Option1 = String.Empty;
private bool Option2 = false;
private bool OptionThatWontBeSaved = false;
}
public class SettingsViewModel : ObservableObject, ISettings
{ {
private readonly PlayniteLibraryPlugin Plugin; private readonly PlayniteLibraryPlugin Plugin;
private PlayniteSettings EditingClone { get; set; }
private PlayniteSettings Settings { get; set; }
public SettingsViewModel(PlayniteLibraryPlugin plugin) public string ServerUrl { get; set; } = String.Empty;
public string AccessToken { get; set; } = String.Empty;
public string RefreshToken { get; set; } = String.Empty;
public PlayniteSettingsViewModel()
{
}
public PlayniteSettingsViewModel(PlayniteLibraryPlugin plugin)
{ {
Plugin = plugin; Plugin = plugin;
var savedSettings = Plugin.LoadPluginSettings<PlayniteSettings>(); var savedSettings = Plugin.LoadPluginSettings<PlayniteSettingsViewModel>();
if (savedSettings != null) if (savedSettings != null)
Settings = savedSettings; {
else ServerUrl = savedSettings.ServerUrl;
Settings = new PlayniteSettings(); }
} }
public void BeginEdit() public void BeginEdit()
{ {
EditingClone = Serialization.GetClone(Settings);
} }
public void CancelEdit() public void CancelEdit()
{ {
Settings = EditingClone;
} }
public void EndEdit() public void EndEdit()
{ {
Plugin.SavePluginSettings(Settings); Plugin.SavePluginSettings(this);
} }
public bool VerifySettings(out List<string> errors) public bool VerifySettings(out List<string> errors)

View File

@ -3,12 +3,19 @@
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:sys="clr-namespace:System;assembly=mscorlib"
mc:Ignorable="d" mc:Ignorable="d"
d:DesignHeight="400" d:DesignWidth="600"> d:DesignHeight="400" d:DesignWidth="600">
<StackPanel> <d:DesignerProperties.DesignStyle>
<TextBlock Text="Description for Option1:"/> <Style TargetType="UserControl">
<TextBox Text="{Binding Settings.Option1}"/> <Setter Property="Background" Value="White" />
</Style>
</d:DesignerProperties.DesignStyle>
<StackPanel Margin="20">
<TextBlock Text="LANCommander Server URL"/>
<TextBox Text="{Binding ServerUrl}"/>
<Button Click="AuthenticateButton_Click" Name="AuthenticateButton">Authenticate</Button>
<TextBlock Text="Description for Option2:"/> <TextBlock Text="Description for Option2:"/>
<CheckBox IsChecked="{Binding Settings.Option2}"/> <CheckBox IsChecked="{Binding Option2}"/>
</StackPanel> </StackPanel>
</UserControl> </UserControl>

View File

@ -1,4 +1,6 @@
using System; using LANCommander.SDK.Models;
using Playnite.SDK;
using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Text; using System.Text;
@ -17,9 +19,31 @@ namespace LANCommander.Playnite.Extension
{ {
public partial class PlayniteSettingsView : UserControl public partial class PlayniteSettingsView : UserControl
{ {
public PlayniteSettingsView() private PlayniteLibraryPlugin Plugin;
{
public PlayniteSettingsView(PlayniteLibraryPlugin plugin)
{
Plugin = plugin;
InitializeComponent();
var settings = Plugin.GetSettings(false) as PlayniteSettingsViewModel;
if (Plugin.LANCommander.ValidateToken(new AuthToken()
{
AccessToken = settings.AccessToken,
RefreshToken = settings.RefreshToken,
}))
{
var authenticateButton = FindName("AuthenticateButton") as Button;
authenticateButton.Visibility = Visibility.Hidden;
}
}
private void AuthenticateButton_Click(object sender, RoutedEventArgs e)
{
Plugin.ShowAuthenticationWindow();
} }
} }
} }

View File

@ -0,0 +1,12 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace LANCommander.SDK.Models
{
public class AuthRequest
{
public string UserName { get; set; }
public string Password { get; set; }
}
}

View File

@ -0,0 +1,13 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace LANCommander.SDK.Models
{
public class AuthResponse
{
public string AccessToken { get; set; }
public string RefreshToken { get; set; }
public DateTime Expiration { get; set; }
}
}

View File

@ -0,0 +1,12 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace LANCommander.SDK.Models
{
public class AuthToken
{
public string AccessToken { get; set; }
public string RefreshToken { get; set; }
}
}