diff --git a/KillTeam/Controllers/TeamsController.cs b/KillTeam/Controllers/TeamsController.cs index 897ad6a..29faa4e 100644 --- a/KillTeam/Controllers/TeamsController.cs +++ b/KillTeam/Controllers/TeamsController.cs @@ -5,7 +5,8 @@ using System.Windows.Input; using KillTeam.Commands; using KillTeam.Commands.Handlers; - +using KillTeam.Queries; +using KillTeam.Queries.Handlers; using KillTeam.Services; using KillTeam.ViewModels; using Microsoft.EntityFrameworkCore; @@ -23,9 +24,11 @@ public class TeamsController public ICommand OpenTeam { get; private set; } public ICommand DeleteTeam { get; private set; } - public TeamsController(IList toolbarItems, + public TeamsController( + IList toolbarItems, IHandleCommands deleteTeamCommandHandler, - IHandleCommands reorderTeamsCommandHandler) + IHandleCommands reorderTeamsCommandHandler, + IQueryProcessor queryProcessor) { Items = new ObservableCollection(); @@ -34,6 +37,7 @@ public TeamsController(IList toolbarItems, _reorderTeamsCommandHandler = reorderTeamsCommandHandler; _deleteTeamCommandHandler = deleteTeamCommandHandler; + _queryProcessor = queryProcessor; } public async Task Refresh() @@ -76,13 +80,10 @@ private void InitializeCommands() private async Task UpdateItems() { Items.Clear(); - var teams = await KTContext.Db.Teams - .Include(e => e.Faction) - .Include(e => e.Members) - .AsNoTracking() - .OrderBy(post => post.Position) - .ToListAsync(); - teams.ForEach(i => Items.Add(new TeamsViewModel(i.Id, i.Name, i.Cost, i.FactionNameAndMembersCount))); + + var teams = await _queryProcessor.Execute>(new AllTeamsQuery()); + + teams.ForEach(t => Items.Add(t)); } private void AddTeamExecuted() @@ -124,5 +125,6 @@ private async Task VersionExecuted() private readonly IHandleCommands _reorderTeamsCommandHandler; private readonly IHandleCommands _deleteTeamCommandHandler; + private readonly IQueryProcessor _queryProcessor; } } diff --git a/KillTeam/Models/Team.cs b/KillTeam/Models/Team.cs index 25081e8..e98a169 100644 --- a/KillTeam/Models/Team.cs +++ b/KillTeam/Models/Team.cs @@ -179,16 +179,6 @@ public List Errors return liste; } } - - [JsonIgnore] - public string FactionNameAndMembersCount - { - get - { - int count = GetSelectedMembers().Count(); - return Faction.Name + " - " + count + " " + (count <= 1 ? Properties.Resources.Membre : Properties.Resources.Membres); - } - } #endregion Calculated Properties diff --git a/KillTeam/Queries/AllTeamsQuery.cs b/KillTeam/Queries/AllTeamsQuery.cs new file mode 100644 index 0000000..f60064f --- /dev/null +++ b/KillTeam/Queries/AllTeamsQuery.cs @@ -0,0 +1,7 @@ +namespace KillTeam.Queries +{ + public class AllTeamsQuery : IQuery + { + + } +} \ No newline at end of file diff --git a/KillTeam/Queries/Handlers/AllTeamsQueryHandler.cs b/KillTeam/Queries/Handlers/AllTeamsQueryHandler.cs new file mode 100644 index 0000000..2fad92b --- /dev/null +++ b/KillTeam/Queries/Handlers/AllTeamsQueryHandler.cs @@ -0,0 +1,42 @@ +using System.Collections.Generic; +using System.Linq; +using System.Threading.Tasks; +using KillTeam.Services; +using KillTeam.ViewModels; +using Microsoft.EntityFrameworkCore; + +namespace KillTeam.Queries.Handlers +{ + public class AllTeamsQueryHandler : IQueryHandler> + { + public async Task> Execute(AllTeamsQuery query) + { + var teams = await KTContext.Db.Teams + .Include(e => e.Faction) + .Include(e => e.Members) + .AsNoTracking() + .OrderBy(post => post.Position) + .Select(t => new + { + t.Id, + t.Name, + t.Members, + t.Faction, + t.Roster + }) + .ToListAsync(); + + return teams + .Select(t => + { + var selectedMembers = t.Members.Where(m => m.Selected || !t.Roster).ToList(); + var count = selectedMembers.Count(); + var cost = selectedMembers.Sum(m => m.Cost); + var subtitle = $"{t.Faction.Name} - {count} {(count <= 1 ? Properties.Resources.Membre : Properties.Resources.Membres)}"; + + return new TeamsViewModel(t.Id, t.Name, cost, subtitle); + }) + .ToList(); + } + } +} \ No newline at end of file diff --git a/KillTeam/Queries/Handlers/IQueryHandler.cs b/KillTeam/Queries/Handlers/IQueryHandler.cs new file mode 100644 index 0000000..9b777f0 --- /dev/null +++ b/KillTeam/Queries/Handlers/IQueryHandler.cs @@ -0,0 +1,9 @@ +using System.Threading.Tasks; + +namespace KillTeam.Queries.Handlers +{ + public interface IQueryHandler where TQuery : IQuery + { + Task Execute(TQuery query); + } +} \ No newline at end of file diff --git a/KillTeam/Queries/Handlers/IQueryProcessor.cs b/KillTeam/Queries/Handlers/IQueryProcessor.cs new file mode 100644 index 0000000..5b53af6 --- /dev/null +++ b/KillTeam/Queries/Handlers/IQueryProcessor.cs @@ -0,0 +1,35 @@ +using System; +using System.Linq; +using System.Reflection; +using System.Threading.Tasks; + +namespace KillTeam.Queries.Handlers +{ + public interface IQueryProcessor + { + Task Execute(TQuery query) where TQuery : IQuery; + } + + public class QueryProcessor : IQueryProcessor + { + public static IQueryProcessor Instance() => _queryProcessor; + + private static readonly IQueryProcessor _queryProcessor = new QueryProcessor(); + + public async Task Execute(TQuery query) where TQuery : IQuery + { + var handlerType = + Assembly + .GetAssembly(typeof(TQuery)) + .DefinedTypes + .FirstOrDefault(t => t.ImplementedInterfaces.Contains(typeof(IQueryHandler))); + + if (handlerType is null) + throw new InvalidOperationException($"No query handler for Query {typeof(TQuery)} for result {typeof(TResult)}"); + + var handler = Activator.CreateInstance(handlerType) as IQueryHandler; + + return await handler.Execute(query); + } + } +} \ No newline at end of file diff --git a/KillTeam/Queries/IQuery.cs b/KillTeam/Queries/IQuery.cs new file mode 100644 index 0000000..dae158c --- /dev/null +++ b/KillTeam/Queries/IQuery.cs @@ -0,0 +1,7 @@ +namespace KillTeam.Queries +{ + public interface IQuery + { + + } +} \ No newline at end of file diff --git a/KillTeam/Views/TeamsView.xaml.cs b/KillTeam/Views/TeamsView.xaml.cs index a3e29c5..1d4367a 100644 --- a/KillTeam/Views/TeamsView.xaml.cs +++ b/KillTeam/Views/TeamsView.xaml.cs @@ -1,5 +1,6 @@ using KillTeam.Commands.Handlers; using KillTeam.Controllers; +using KillTeam.Queries.Handlers; using Xamarin.Forms.PlatformConfiguration.iOSSpecific; using Xamarin.Forms.Xaml; @@ -13,7 +14,11 @@ public TeamsView() InitializeComponent(); On().SetUseSafeArea(true); - BindingContext = new TeamsController(ToolbarItems, new DeleteTeamCommandHandler(), new ReorderTeamsCommandHandler()); + BindingContext = new TeamsController( + ToolbarItems, + new DeleteTeamCommandHandler(), + new ReorderTeamsCommandHandler(), + QueryProcessor.Instance()); } protected override async void OnAppearing()