Version 3.0.337

This commit is contained in:
Anja Müller-Meißner 2022-08-30 15:42:25 +02:00
parent fd0e63cf10
commit 573fe77e12
2336 changed files with 33688 additions and 86082 deletions

View file

@ -13,7 +13,7 @@ namespace TINK.Model.Connector
/// <summary> Gets the merchant id.</summary>
protected string MerchantId => CopriServer.MerchantId;
/// <summary> Constructs a query base object.</summary>
/// <param name="p_oCopriServer">Server which implements communication.</param>
/// <param name="p_oErrorStack">Object which hold communication objects.</param>

View file

@ -1,12 +1,13 @@
using Serilog;
using System;
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using TINK.Model.Bike;
using Serilog;
using TINK.Model.Bikes;
using TINK.Model.Connector.Updater;
using TINK.Model.Services.CopriApi;
using TINK.Repository;
using TINK.Services.CopriApi;
using BikeInfo = TINK.Model.Bike.BC.BikeInfo;
using BikeInfo = TINK.Model.Bikes.BikeInfoNS.BC.BikeInfo;
namespace TINK.Model.Connector
{
@ -16,14 +17,14 @@ namespace TINK.Model.Connector
private readonly ICachedCopriServer server;
/// <summary>Constructs a copri query object.</summary>
/// <param name="p_oCopriServer">Server which implements communication.</param>
/// <param name="copriServer">Server which implements communication.</param>
public CachedQuery(
ICopriServerBase p_oCopriServer) : base(p_oCopriServer)
ICopriServerBase copriServer) : base(copriServer)
{
server = p_oCopriServer as ICachedCopriServer;
server = copriServer as ICachedCopriServer;
if (server == null)
{
throw new ArgumentException($"Copri server is not of expected typ. Type detected is {p_oCopriServer.GetType()}.");
throw new ArgumentException($"Copri server is not of expected typ. Type detected is {copriServer.GetType()}.");
}
}

View file

@ -1,7 +1,9 @@
using System;
using System.Linq;
using System.Threading.Tasks;
using TINK.Model.Bike;
using Serilog;
using TINK.Model.Bikes;
using TINK.Model.Connector.Updater;
using TINK.Model.Services.CopriApi;
using TINK.Repository;
@ -11,26 +13,26 @@ namespace TINK.Model.Connector
public class CachedQueryLoggedIn : BaseLoggedIn, IQuery
{
/// <summary> Cached copri server. </summary>
private readonly ICachedCopriServer server;
private ICachedCopriServer Server { get; }
/// <summary>Constructs a copri query object.</summary>
/// <param name="p_oCopriServer">Server which implements communication.</param>
public CachedQueryLoggedIn(ICopriServerBase p_oCopriServer,
string p_strSessionCookie,
string p_strMail,
Func<DateTime> p_oDateTimeProvider) : base(p_oCopriServer, p_strSessionCookie, p_strMail, p_oDateTimeProvider)
/// <param name="copriServer">Server which implements communication.</param>
public CachedQueryLoggedIn(ICopriServerBase copriServer,
string sessionCookie,
string mail,
Func<DateTime> dateTimeProvider) : base(copriServer, sessionCookie, mail, dateTimeProvider)
{
server = p_oCopriServer as ICachedCopriServer;
if (server == null)
Server = copriServer as ICachedCopriServer;
if (Server == null)
{
throw new ArgumentException($"Copri server is not of expected typ. Type detected is {p_oCopriServer.GetType()}.");
throw new ArgumentException($"Copri server is not of expected typ. Type detected is {copriServer.GetType()}.");
}
}
/// <summary> Gets all stations including postions.</summary>
public async Task<Result<StationsAndBikesContainer>> GetBikesAndStationsAsync()
{
var stationsResponse = await server.GetStations();
var stationsResponse = await Server.GetStations();
if (stationsResponse.Source == typeof(CopriCallsMonkeyStore)
|| stationsResponse.Exception != null)
@ -41,15 +43,15 @@ namespace TINK.Model.Connector
new StationsAndBikesContainer(
stationsResponse.Response.GetStationsAllMutable(),
UpdaterJSON.GetBikesAll(
(await server.GetBikesAvailable(true)).Response,
(await server.GetBikesOccupied(true)).Response,
(await Server.GetBikesAvailable(true)).Response?.bikes?.Values,
(await Server.GetBikesOccupied(true)).Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider)),
stationsResponse.GeneralData,
stationsResponse.Exception);
}
var bikesAvailableResponse = await server.GetBikesAvailable();
var bikesAvailableResponse = await Server.GetBikesAvailable();
if (bikesAvailableResponse.Source == typeof(CopriCallsMonkeyStore)
|| bikesAvailableResponse.Exception != null)
{
@ -57,16 +59,16 @@ namespace TINK.Model.Connector
return new Result<StationsAndBikesContainer>(
bikesAvailableResponse.Source,
new StationsAndBikesContainer(
(await server.GetStations(true)).Response.GetStationsAllMutable(),
UpdaterJSON.GetBikesAll(bikesAvailableResponse.Response,
(await server.GetBikesOccupied(true)).Response,
(await Server.GetStations(true)).Response.GetStationsAllMutable(),
UpdaterJSON.GetBikesAll(bikesAvailableResponse.Response?.bikes?.Values,
(await Server.GetBikesOccupied(true)).Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider)),
bikesAvailableResponse.GeneralData,
bikesAvailableResponse.Exception);
}
var bikesOccupiedResponse = await server.GetBikesOccupied();
var bikesOccupiedResponse = await Server.GetBikesOccupied();
if (bikesOccupiedResponse.Source == typeof(CopriCallsMonkeyStore)
|| bikesOccupiedResponse.Exception != null)
{
@ -74,10 +76,10 @@ namespace TINK.Model.Connector
return new Result<StationsAndBikesContainer>(
bikesOccupiedResponse.Source,
new StationsAndBikesContainer(
(await server.GetStations(true)).Response.GetStationsAllMutable(),
(await Server.GetStations(true)).Response.GetStationsAllMutable(),
UpdaterJSON.GetBikesAll(
(await server.GetBikesAvailable(true)).Response,
bikesOccupiedResponse.Response,
(await Server.GetBikesAvailable(true)).Response?.bikes?.Values,
bikesOccupiedResponse.Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider)),
bikesOccupiedResponse.GeneralData,
@ -85,16 +87,16 @@ namespace TINK.Model.Connector
}
// Both types bikes could read from copri => update cache
server.AddToCache(stationsResponse);
server.AddToCache(bikesAvailableResponse);
server.AddToCache(bikesOccupiedResponse);
Server.AddToCache(stationsResponse);
Server.AddToCache(bikesAvailableResponse);
Server.AddToCache(bikesOccupiedResponse);
var exceptions = new[] { stationsResponse?.Exception, bikesAvailableResponse?.Exception, bikesOccupiedResponse?.Exception }.Where(x => x != null).ToArray();
var stationsMutable = stationsResponse.Response.GetStationsAllMutable();
var bikesMutable = UpdaterJSON.GetBikesAll(
bikesAvailableResponse.Response,
bikesOccupiedResponse.Response,
bikesAvailableResponse.Response?.bikes?.Values,
bikesOccupiedResponse.Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider);
@ -109,58 +111,108 @@ namespace TINK.Model.Connector
/// <returns>Collection of bikes.</returns>
public async Task<Result<BikeCollection>> GetBikesOccupiedAsync()
{
var result = await server.GetBikesOccupied();
server.AddToCache(result);
return new Result<BikeCollection>(result.Source, result.Response.GetBikesOccupied(Mail, DateTimeProvider), result.GeneralData, result.Exception);
var bikesAvailableResponse = await Server.GetBikesAvailable(false);
if (bikesAvailableResponse.Source == typeof(CopriCallsMonkeyStore)
|| bikesAvailableResponse.Exception != null)
{
// Bikes available were read from cache ==> get bikes occupied from cache as well to avoid inconsistencies.
Log.ForContext<CachedQueryLoggedIn>().Debug("Bikes available read from cache. Reading bikes occupied from cache as well.");
return new Result<BikeCollection>(
bikesAvailableResponse.Source,
UpdaterJSON.GetBikesAll(
bikesAvailableResponse.Response?.bikes?.Values?.Where(bike => bike.GetState() == State.InUseStateEnum.FeedbackPending),
(await Server.GetBikesOccupied(true))?.Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
bikesAvailableResponse.GeneralData,
bikesAvailableResponse.Exception);
}
var bikesOccupiedResponse = await Server.GetBikesOccupied(false);
if (bikesOccupiedResponse.Source == typeof(CopriCallsMonkeyStore)
|| bikesOccupiedResponse.Exception != null)
{
// Bikes occupied were read from cache ==> get bikes available from cache as well to avoid inconsistencies
Log.ForContext<CachedQueryLoggedIn>().Debug("Bikes occupied read from cache. Reread bikes available from cache as well.");
return new Result<BikeCollection>(
bikesOccupiedResponse.Source,
UpdaterJSON.GetBikesAll(
(await Server.GetBikesAvailable(true)).Response?.bikes?.Values?.Where(bike => bike.GetState() == State.InUseStateEnum.FeedbackPending),
bikesOccupiedResponse.Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
bikesOccupiedResponse.GeneralData,
bikesOccupiedResponse.Exception);
}
// Both types bikes could read from copri => update bikes occupied cache.
// // Do not add bikes available to cache because this might lead to conflicts calls GetBikesAsync() and bikes with FeedbackPending state are of no use offline.
Server.AddToCache(bikesOccupiedResponse);
return new Result<BikeCollection>(
bikesOccupiedResponse.Source,
UpdaterJSON.GetBikesAll(
bikesAvailableResponse?.Response.bikes?.Values?.Select(bike => bike)?.Where(bike => bike.GetState() == State.InUseStateEnum.FeedbackPending),
bikesOccupiedResponse?.Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
bikesOccupiedResponse.GeneralData,
bikesOccupiedResponse.Exception);
}
/// <summary> Gets bikes available and bikes occupied. </summary>
/// <returns>Collection of bikes.</returns>
public async Task<Result<BikeCollection>> GetBikesAsync()
{
var l_oBikesAvailableResponse = await server.GetBikesAvailable();
var bikesAvailableResponse = await Server.GetBikesAvailable();
if (l_oBikesAvailableResponse.Source == typeof(CopriCallsMonkeyStore)
|| l_oBikesAvailableResponse.Exception != null)
if (bikesAvailableResponse.Source == typeof(CopriCallsMonkeyStore)
|| bikesAvailableResponse.Exception != null)
{
// Bikes avilable were read from cache ==> get bikes occupied from cache as well to avoid inconsistencies
// Bikes available were read from cache ==> get bikes occupied from cache as well to avoid inconsistencies.
Log.ForContext<CachedQueryLoggedIn>().Debug("Bikes available read from cache. Reading bikes occupied from cache as well.");
return new Result<BikeCollection>(
l_oBikesAvailableResponse.Source,
bikesAvailableResponse.Source,
UpdaterJSON.GetBikesAll(
l_oBikesAvailableResponse.Response,
(await server.GetBikesOccupied(true)).Response,
bikesAvailableResponse.Response?.bikes?.Values,
(await Server.GetBikesOccupied(true)).Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
l_oBikesAvailableResponse.GeneralData,
l_oBikesAvailableResponse.Exception);
bikesAvailableResponse.GeneralData,
bikesAvailableResponse.Exception);
}
var l_oBikesOccupiedResponse = await server.GetBikesOccupied();
if (l_oBikesOccupiedResponse.Source == typeof(CopriCallsMonkeyStore)
|| l_oBikesOccupiedResponse.Exception != null)
var bikesOccupiedResponse = await Server.GetBikesOccupied();
if (bikesOccupiedResponse.Source == typeof(CopriCallsMonkeyStore)
|| bikesOccupiedResponse.Exception != null)
{
// Bikes occupied were read from cache ==> get bikes available from cache as well to avoid inconsistencies
Log.ForContext<CachedQueryLoggedIn>().Debug("Bikes occupied read from cache. Reread bikes available from cache as well.");
return new Result<BikeCollection>(
l_oBikesOccupiedResponse.Source,
bikesOccupiedResponse.Source,
UpdaterJSON.GetBikesAll(
(await server.GetBikesAvailable(true)).Response,
l_oBikesOccupiedResponse.Response,
(await Server.GetBikesAvailable(true)).Response?.bikes?.Values,
bikesOccupiedResponse.Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
l_oBikesOccupiedResponse.GeneralData,
l_oBikesOccupiedResponse.Exception);
bikesOccupiedResponse.GeneralData,
bikesOccupiedResponse.Exception);
}
// Both types bikes could read from copri => update cache
server.AddToCache(l_oBikesAvailableResponse);
server.AddToCache(l_oBikesOccupiedResponse);
Server.AddToCache(bikesAvailableResponse);
Server.AddToCache(bikesOccupiedResponse);
Log.ForContext<CachedQueryLoggedIn>().Debug("Bikes available and occupied read successfully from server.");
return new Result<BikeCollection>(
l_oBikesAvailableResponse.Source,
UpdaterJSON.GetBikesAll(l_oBikesAvailableResponse.Response, l_oBikesOccupiedResponse.Response, Mail, DateTimeProvider),
l_oBikesAvailableResponse.GeneralData,
l_oBikesAvailableResponse.Exception != null || l_oBikesOccupiedResponse.Exception != null ? new AggregateException(new[] { l_oBikesAvailableResponse.Exception, l_oBikesOccupiedResponse.Exception }) : null);
}
bikesAvailableResponse.Source,
UpdaterJSON.GetBikesAll(
bikesAvailableResponse.Response?.bikes?.Values,
bikesOccupiedResponse.Response?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
bikesAvailableResponse.GeneralData,
bikesAvailableResponse.Exception != null || bikesOccupiedResponse.Exception != null ? new AggregateException(new[] { bikesAvailableResponse.Exception, bikesOccupiedResponse.Exception }) : null);
}
}
}

View file

@ -1,5 +1,5 @@
using System.Threading.Tasks;
using TINK.Model.Bike;
using TINK.Model.Bikes;
using TINK.Model.Services.CopriApi;
namespace TINK.Model.Connector

View file

@ -1,12 +1,13 @@
using Serilog;
using System;
using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using TINK.Model.Bike;
using Serilog;
using TINK.Model.Bikes;
using TINK.Model.Connector.Updater;
using TINK.Model.Services.CopriApi;
using TINK.Repository;
using TINK.Services.CopriApi;
using BikeInfo = TINK.Model.Bike.BC.BikeInfo;
using BikeInfo = TINK.Model.Bikes.BikeInfoNS.BC.BikeInfo;
namespace TINK.Model.Connector
{
@ -20,7 +21,7 @@ namespace TINK.Model.Connector
/// <param name="p_oCopriServer">Server which implements communication.</param>
public Query(ICopriServerBase p_oCopriServer) : base(p_oCopriServer)
{
server = p_oCopriServer as ICopriServer;
server = p_oCopriServer as ICopriServer;
if (server == null)
{
throw new ArgumentException($"Copri server is not of expected typ. Type detected is {p_oCopriServer.GetType()}.");
@ -30,11 +31,11 @@ namespace TINK.Model.Connector
/// <summary> Gets all stations including postions.</summary>
public async Task<Result<StationsAndBikesContainer>> GetBikesAndStationsAsync()
{
var stationsAllResponse = await server.GetStationsAsync();
var stationsAllResponse = await server.GetStationsAsync();
var bikesAvailableResponse = await server.GetBikesAvailableAsync();
return new Result<StationsAndBikesContainer>(
typeof(CopriCallsMonkeyStore),
typeof(CopriCallsMonkeyStore),
new StationsAndBikesContainer(stationsAllResponse.GetStationsAllMutable(), bikesAvailableResponse.GetBikesAvailable()),
stationsAllResponse.GetGeneralData());
}

View file

@ -1,6 +1,8 @@
using System;
using System.Linq;
using System.Threading.Tasks;
using TINK.Model.Bike;
using TINK.Model.Bikes;
using TINK.Model.Connector.Updater;
using TINK.Model.Services.CopriApi;
using TINK.Repository;
@ -9,23 +11,23 @@ namespace TINK.Model.Connector
/// <summary> Provides query functionality for a logged in user. </summary>
public class QueryLoggedIn : BaseLoggedIn, IQuery
{
/// <summary> Cached copri server. </summary>
/// <summary> Copri server. </summary>
private readonly ICopriServer server;
/// <summary>Constructs a copri query object.</summary>
/// <param name="p_oCopriServer">Server which implements communication.</param>
public QueryLoggedIn(ICopriServerBase p_oCopriServer,
string p_strSessionCookie,
string p_strMail,
Func<DateTime> p_oDateTimeProvider) : base(p_oCopriServer, p_strSessionCookie, p_strMail, p_oDateTimeProvider)
/// <param name="copriServer">Server which implements communication.</param>
public QueryLoggedIn(ICopriServerBase copriServer,
string sessionCookie,
string mail,
Func<DateTime> dateTimeProvider) : base(copriServer, sessionCookie, mail, dateTimeProvider)
{
server = p_oCopriServer as ICopriServer;
server = copriServer as ICopriServer;
if (server == null)
{
throw new ArgumentException($"Copri server is not of expected typ. Type detected is {p_oCopriServer.GetType()}.");
throw new ArgumentException($"Copri server is not of expected typ. Type detected is {copriServer.GetType()}.");
}
server = p_oCopriServer as ICopriServer;
server = copriServer as ICopriServer;
}
/// <summary> Gets all stations including postions.</summary>
@ -39,30 +41,45 @@ namespace TINK.Model.Connector
typeof(CopriCallsMonkeyStore),
new StationsAndBikesContainer(
stationResponse.GetStationsAllMutable(),
UpdaterJSON.GetBikesAll(bikesAvailableResponse, bikesOccupiedResponse, Mail, DateTimeProvider)),
UpdaterJSON.GetBikesAll(
bikesAvailableResponse?.bikes?.Values,
bikesOccupiedResponse?.bikes_occupied?.Values,
Mail,
DateTimeProvider)),
stationResponse.GetGeneralData());
}
/// <summary> Gets bikes occupied. </summary>
/// <summary> Gets bikes occupied and bikes for which feedback is required. </summary>
/// <returns>Collection of bikes.</returns>
public async Task<Result<BikeCollection>> GetBikesOccupiedAsync()
{
var bikesOccupiedResponse = (await server.GetBikesOccupiedAsync());
var bikesFeedbackRequired = await server.GetBikesAvailableAsync();
var bikesOccupiedResponse = await server.GetBikesOccupiedAsync();
return new Result<BikeCollection>(
typeof(CopriCallsMonkeyStore),
bikesOccupiedResponse.GetBikesOccupied(Mail, DateTimeProvider),
UpdaterJSON.GetBikesAll(
bikesFeedbackRequired.bikes?.Values?.Select(bike => bike)?.Where(bike => bike.GetState() == State.InUseStateEnum.FeedbackPending),
bikesOccupiedResponse?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
bikesOccupiedResponse.GetGeneralData());
}
/// <summary> Gets bikes available and bikes occupied. </summary>
/// <returns>Collection of bikes.</returns>
public async Task<Result<BikeCollection>> GetBikesAsync()
{
var bikesAvailableResponse = await server.GetBikesAvailableAsync();
var bikesOccupiedResponse = await server.GetBikesOccupiedAsync();
return new Result<BikeCollection>(
typeof(CopriCallsMonkeyStore),
UpdaterJSON.GetBikesAll(bikesAvailableResponse, bikesOccupiedResponse, Mail, DateTimeProvider),
typeof(CopriCallsMonkeyStore),
UpdaterJSON.GetBikesAll(
bikesAvailableResponse?.bikes?.Values,
bikesOccupiedResponse?.bikes_occupied?.Values,
Mail,
DateTimeProvider),
bikesAvailableResponse.GetGeneralData());
}
}