This commit is contained in:
Christian Kauer 2023-12-29 16:01:08 +01:00
parent a2e432a9c2
commit a373efefbd
11 changed files with 112 additions and 51 deletions

View File

@ -17,11 +17,16 @@ namespace GameData
{
public sealed class ApiClient : IDisposable
{
private class Wrapper<T>
private class WrapperArray<T>
{
public T[] Data { get; set; }
}
private class WrapperSingle<T>
{
public T Data { get; set; }
}
private readonly HttpClient client;
private readonly ILogger<ApiClient> _logger;
private readonly AppSettings _appSettings;
@ -145,13 +150,13 @@ namespace GameData
/// <param name="serviceUrl"></param>
/// <param name="suppressExceptions"></param>
/// <returns></returns>
public T Post<T>(object payload, string serviceUrl, bool suppressExceptions = false)
public async Task<T> Post<T>(object payload, string serviceUrl, bool suppressExceptions = false)
{
T res = default;
try
{
var response = client.Send(GetHttpRequestMessage(HttpMethod.Post, serviceUrl, payload));
var response = await client.SendAsync(GetHttpRequestMessage(HttpMethod.Post, serviceUrl, payload));
if (response.IsSuccessStatusCode)
{
@ -162,14 +167,15 @@ namespace GameData
using (var jsonTextReader = new JsonTextReader(streamReader))
{
var serializer = new JsonSerializer();
res = serializer.Deserialize<T>(jsonTextReader);
var wrapper = serializer.Deserialize<WrapperSingle<T>>(jsonTextReader);
res = wrapper.Data;
}
}
}
}
else
{
var errorResult = response.Content.ReadAsStringAsync().Result;
var errorResult = await response.Content.ReadAsStringAsync();
_logger.LogError("error posting to service '{service}' with code '{statuscode}' - Result: '{result}', Payload: '{payload}'", serviceUrl, response.StatusCode, errorResult, JsonConvert.SerializeObject(payload));
}
}
@ -227,7 +233,7 @@ namespace GameData
public T[] Get<T>(string serviceUrl, bool suppressExceptions = false)
{
Wrapper<T> res = default;
WrapperArray<T> res = default;
try
{
@ -244,14 +250,14 @@ namespace GameData
if (typeof(T).Equals(typeof(string)))
{
content = streamReader.ReadToEnd();
res = (Wrapper<T>)Convert.ChangeType(content, typeof(T));
res = (WrapperArray<T>)Convert.ChangeType(content, typeof(T));
}
else
{
using (var jsonTextReader = new JsonTextReader(streamReader))
{
var serializer = new JsonSerializer();
res = serializer.Deserialize<Wrapper<T>>(jsonTextReader);
res = serializer.Deserialize<WrapperArray<T>>(jsonTextReader);
}
}
}
@ -275,13 +281,13 @@ namespace GameData
return res.Data;
}
internal void Put<T>(object payload, string serviceUrl, bool suppressExceptions = false)
internal async Task Put<T>(object payload, string serviceUrl, bool suppressExceptions = false)
{
T res = default;
try
{
var response = client.Send(GetHttpRequestMessage(HttpMethod.Post, serviceUrl, payload));
var response = await client.SendAsync(GetHttpRequestMessage(HttpMethod.Post, serviceUrl, payload));
if (response.IsSuccessStatusCode)
{
@ -292,14 +298,15 @@ namespace GameData
using (var jsonTextReader = new JsonTextReader(streamReader))
{
var serializer = new JsonSerializer();
res = serializer.Deserialize<T>(jsonTextReader);
var wrapper = serializer.Deserialize<WrapperSingle<T>>(jsonTextReader);
res = wrapper.Data;
}
}
}
}
else
{
var errorResult = response.Content.ReadAsStringAsync().Result;
var errorResult = await response.Content.ReadAsStringAsync();
_logger.LogError("error posting to service '{service}' with code '{statuscode}' - Result: '{result}', Payload: '{payload}'", serviceUrl, response.StatusCode, errorResult, JsonConvert.SerializeObject(payload));
}
}

View File

@ -19,5 +19,10 @@ namespace GameData.Dummy
{
throw new NotImplementedException();
}
Task IExpenseRepository.Save(MemberExpense data)
{
throw new NotImplementedException();
}
}
}

View File

@ -12,14 +12,25 @@ namespace GameData.Dummy
{
List<GameState> gameStates = new List<GameState>();
public void Save(GameState gameState)
public Task Save(GameState gameState)
{
gameStates.Add(gameState);
return Task.CompletedTask;
}
public GameState Load(Guid gameId)
{
return gameStates.Last();
}
public Task Update(Game game)
{
throw new NotImplementedException();
}
public Task<Game> Create(Game game)
{
throw new NotImplementedException();
}
}
}

View File

@ -23,7 +23,7 @@ namespace GameData.Repository
_log = log;
_client = apiClient;
_log?.LogWarning("TESTWARN");
_log?.LogDebug("creating ExpenseRepository");
}
public IEnumerable<Expense> GetAll()
@ -31,7 +31,7 @@ namespace GameData.Repository
return _client.Get<Expense>(Url);
}
public void Save(MemberExpense memberExpense)
public async Task Save(MemberExpense memberExpense)
{
_memberExpenses.Add(memberExpense);
}

View File

@ -15,7 +15,9 @@ namespace GameData.Repository
readonly ILogger<GameRepository> _log;
private ApiClient _client;
string Url => "items/gamestate";
string UrlGameState => "items/gamestate";
string UrlGame => "items/game";
public GameRepository(ILogger<GameRepository> log, ApiClient apiClient)
{
_log = log;
@ -27,10 +29,20 @@ namespace GameData.Repository
throw new NotImplementedException();
}
public void Save(GameState gameState)
public async Task Save(GameState gameState)
{
var gameStateDo = new GameStateDo(gameState.Id, gameState.GameId, gameState.GameName, gameState);
_client.Post<GameStateDo>(gameStateDo,Url);
var res = await _client.Post<GameStateDo>(gameStateDo,UrlGameState);
}
public async Task Update(Game game)
{
await _client.Put<Game>(game, UrlGame);
}
public async Task<Game> Create(Game game)
{
return await _client.Post<Game>(game, UrlGame);
}
}
}

View File

@ -28,6 +28,7 @@ namespace GameHandler
private ThrowHandler _th;
private ExpenseHandler _eh;
private GameStateHandler _gameStateHandler;
private Game _game;
public GameState GameModel { get => _gameStateHandler.GameState; }
@ -50,12 +51,12 @@ namespace GameHandler
static int[] defaultPlayerIds => new[] {1,2,3,4};
public GameState Start(string gameName = FreeGameHandler.GAMENAME_FREETRAINING)
public async Task<GameState> Start(string gameName = FreeGameHandler.GAMENAME_FREETRAINING)
{
return Start(defaultPlayerIds, new DeathGameSettings(6), gameName);
return await Start(defaultPlayerIds, new DeathGameSettings(6), gameName);
}
public GameState Start(int[] playerIds, IGameSettings gameSettings, string gameName = FreeGameHandler.GAMENAME_FREETRAINING)
public async Task<GameState> Start(int[] playerIds, IGameSettings gameSettings, string gameName = FreeGameHandler.GAMENAME_FREETRAINING)
{
if (_isStarted)
{
@ -64,18 +65,19 @@ namespace GameHandler
_isStarted = true;
InitGameServiceBehaviour(gameName);
var state = InitGameState(playerIds, gameSettings, gameName);
_gameStateHandler.Add(state);
_gameStateHandler.Add(ExpenseModel.Create());
var state = await InitGameState(playerIds, gameSettings, gameName);
await _gameStateHandler.Add(state, _game);
await _gameStateHandler.Add(ExpenseModel.Create());
return state;
}
private GameState InitGameState(int[] playerIds, IGameSettings gameSettings, string gameName)
private async Task<GameState> InitGameState(int[] playerIds, IGameSettings gameSettings, string gameName)
{
var gm = _gh.InitGameModel(playerIds, gameSettings);
var throwState = ThrowState.Create(_gh.ThrowMode(), _gh.ThrowsPerRount());
return GameState.Create(Guid.NewGuid(), gameName, throwState, _gh.GetCurrentPlayerId(gm), gm);
_game = await _gameStateHandler.CreateNewGame();
return GameState.Create(_game.Id, gameName, throwState, _gh.GetCurrentPlayerId(gm), gm);
}
private void InitGameServiceBehaviour(string gameName)
@ -95,7 +97,7 @@ namespace GameHandler
//_lastState = _lastState with { ExpenseModel = expenseModel };
}
public GameState HandleThrow(PinThrow pinThrow)
public async Task<GameState> HandleThrow(PinThrow pinThrow)
{
if (!_isStarted)
{
@ -114,8 +116,8 @@ namespace GameHandler
var newGameState = lastGameState with { ThrowState = throwStateAfterUpdate, GameModel = gameModel, NextPlayerId = _gh.GetCurrentPlayerId(gameModel) };
_gameStateHandler.Add(expenseModel);
_gameStateHandler.Add(newGameState);
await _gameStateHandler.Add(expenseModel);
await _gameStateHandler.Add(newGameState, _game);
return newGameState;
}

View File

@ -64,20 +64,20 @@ namespace GameHandler
}
}
internal void Add(ExpenseModel expenseModel)
internal async Task Add(ExpenseModel expenseModel)
{
if (ExpenseModel != null)
{
if (!expenseModel.Equals(ExpenseModel))
{
expenseModels.Add(new GameStateHandlerItem<ExpenseModel>(_gameStateId, expenseModel, false));
Save();
await Save();
}
}
else
{
expenseModels.Add(new GameStateHandlerItem<ExpenseModel>(_gameStateId, expenseModel, false));
Save();
await Save();
}
@ -87,34 +87,39 @@ namespace GameHandler
}
}
internal void Add(GameState newState)
internal async Task Add(GameState newState, Game game)
{
if (!newState.Equals(GameState))
{
_gameStateId = Guid.NewGuid();
gameStates.Add(new GameStateHandlerItem<GameState>(_gameStateId, newState, false));
Save();
await Save();
}
}
private void Save()
private async Task Save()
{
foreach (var item in gameStates.Where(_ => !_.Saved))
{
_gameRepository.Save(item.Data);
item.Saved = true;
}
await Task.WhenAll(gameStates.Where(_ => !_.Saved)
.Select(_ => _gameRepository.Save(_.Data)))
.ContinueWith(_ => {
gameStates.ForEach(gs => { gs.Saved = true; });
});
foreach (var item in memberExpenses)
{
_expenseRepository.Save(item.Data);
item.Saved = true;
}
await Task.WhenAll(memberExpenses.Where(_ => !_.Saved)
.Select(_ => _expenseRepository.Save(_.Data)))
.ContinueWith(_ => {
memberExpenses.ForEach(me => { me.Saved = true; });
});
}
public void Undo()
{
}
internal async Task<Game> CreateNewGame()
{
return await _gameRepository.Create(null);
}
}
}

View File

@ -18,6 +18,6 @@ namespace GameModel.Contract
};
IEnumerable<Expense> GetAll();
void Save(MemberExpense data);
Task Save(MemberExpense data);
}
}

View File

@ -8,7 +8,9 @@ namespace GameModel.Contracts
{
public interface IGameRepository
{
Task<Game> Create(Game game);
GameState Load(Guid gameId);
void Save(GameState gameState);
Task Save(GameState gameState);
Task Update(Game game);
}
}

16
GameModel/Game.cs Normal file
View File

@ -0,0 +1,16 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace GameModel
{
public record Game(Guid Id)
{
public static Game Create()
{
return new Game(Guid.NewGuid());
}
}
}

View File

@ -62,7 +62,7 @@ Autofac.IContainer Register()
ShowMainMenu();
void ShowMainMenu()
async Task ShowMainMenu()
{
do
{
@ -126,8 +126,8 @@ void NewGameAction()
void StartGameAction(string gameName)
{
_gs = new GameService(container);
var bs = _gs.Start(new[] { 1,2,3,4}, GetGameSettings(gameName), gameName );
var starttask = _gs.Start(new[] { 1, 2, 3, 4 }, GetGameSettings(gameName), gameName);
var bs = starttask.Result;
Show(bs);
@ -159,7 +159,8 @@ void StartGameAction(string gameName)
break;
}
bs = _gs.HandleThrow(PinThrow.Create(throwData.Pindata, throwData.Bell, throwData.Sink, throwData.PlayerId));
var task = _gs.HandleThrow(PinThrow.Create(throwData.Pindata, throwData.Bell, throwData.Sink, throwData.PlayerId));
bs = task.Result;
Show(bs);
} while (true);