OpenrouteServiceAPI implementiert, Längengrad bei Addresse
This commit is contained in:
@@ -1,7 +1,9 @@
|
||||
using BS.Shared;
|
||||
using System.Diagnostics;
|
||||
|
||||
namespace BeWo.Data.Entities
|
||||
{
|
||||
[DebuggerDisplay("{Oid}: {Street}, {Town}")]
|
||||
public class Address : BeWoEntityBase
|
||||
{
|
||||
public static string PropertyName_AddressLine1 = "AddressLine1";
|
||||
@@ -30,6 +32,12 @@ namespace BeWo.Data.Entities
|
||||
|
||||
private string _Town;
|
||||
|
||||
private decimal? _Latitude;
|
||||
|
||||
private decimal? _Longitude;
|
||||
|
||||
private long? _L_Version;
|
||||
|
||||
public Address()
|
||||
{
|
||||
this._Tid = TableID.Address;
|
||||
@@ -147,6 +155,54 @@ namespace BeWo.Data.Entities
|
||||
}
|
||||
}
|
||||
|
||||
public virtual decimal? Latitude
|
||||
{
|
||||
get
|
||||
{
|
||||
return this._Latitude;
|
||||
}
|
||||
|
||||
set
|
||||
{
|
||||
if (this.AreDifferent(this._Latitude, value))
|
||||
{
|
||||
this._Latitude = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual decimal? Longitude
|
||||
{
|
||||
get
|
||||
{
|
||||
return this._Longitude;
|
||||
}
|
||||
|
||||
set
|
||||
{
|
||||
if (this.AreDifferent(this._Longitude, value))
|
||||
{
|
||||
this._Longitude = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual long? L_Version
|
||||
{
|
||||
get
|
||||
{
|
||||
return this._L_Version;
|
||||
}
|
||||
|
||||
set
|
||||
{
|
||||
if (this.AreDifferent(this._L_Version, value))
|
||||
{
|
||||
this._L_Version = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual Address CopyToNew()
|
||||
{
|
||||
return new Address
|
||||
@@ -161,5 +217,13 @@ namespace BeWo.Data.Entities
|
||||
Town = this.Town
|
||||
};
|
||||
}
|
||||
|
||||
public override int GetHashCode()
|
||||
{
|
||||
if (this is null)
|
||||
return 0;
|
||||
|
||||
return Oid.Value.GetHashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,18 +1,20 @@
|
||||
using BS.Shared;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace BeWo.Data.Entities
|
||||
{
|
||||
[DebuggerDisplay("{Oid}({Origin.Oid},{Destination.Oid}): {Distance_in_meter}m, {Time_in_seconds}s")]
|
||||
public class AddressRoute : BeWoEntityBase
|
||||
{
|
||||
private long address1_oid;
|
||||
private long address1_version;
|
||||
private long address2_oid;
|
||||
private long address2_version;
|
||||
private Address _Origin;
|
||||
private long _Origin_Version;
|
||||
private Address _Destination;
|
||||
private long _Destination_Version;
|
||||
|
||||
private int distance_in_meter;
|
||||
private string distance_in_meter_txt;
|
||||
@@ -24,62 +26,62 @@ namespace BeWo.Data.Entities
|
||||
_Tid = TableID.AddressRoute;
|
||||
}
|
||||
|
||||
public virtual long Address1_Oid
|
||||
public virtual Address Origin
|
||||
{
|
||||
get
|
||||
{
|
||||
return address1_oid;
|
||||
return _Origin;
|
||||
}
|
||||
set
|
||||
{
|
||||
if (AreDifferent(address1_oid, value))
|
||||
if (AreDifferent(_Origin, value))
|
||||
{
|
||||
address1_oid = value;
|
||||
_Origin = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual long Address1_Version
|
||||
public virtual long Origin_Version
|
||||
{
|
||||
get
|
||||
{
|
||||
return address1_version;
|
||||
return _Origin_Version;
|
||||
}
|
||||
set
|
||||
{
|
||||
if (AreDifferent(address1_version, value))
|
||||
if (AreDifferent(_Origin_Version, value))
|
||||
{
|
||||
address1_version = value;
|
||||
_Origin_Version = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual long Address2_Oid
|
||||
public virtual Address Destination
|
||||
{
|
||||
get
|
||||
{
|
||||
return address2_oid;
|
||||
return _Destination;
|
||||
}
|
||||
set
|
||||
{
|
||||
if (AreDifferent(address2_oid, value))
|
||||
if (AreDifferent(_Destination, value))
|
||||
{
|
||||
address2_oid = value;
|
||||
_Destination = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public virtual long Address2_Version
|
||||
public virtual long Destination_Version
|
||||
{
|
||||
get
|
||||
{
|
||||
return address2_version;
|
||||
return _Destination_Version;
|
||||
}
|
||||
set
|
||||
{
|
||||
if (AreDifferent(address2_version, value))
|
||||
if (AreDifferent(_Destination_Version, value))
|
||||
{
|
||||
address2_version = value;
|
||||
_Destination_Version = value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,19 +6,22 @@
|
||||
<generator class="identity" />
|
||||
</id>
|
||||
<version type="Int64" column="Version" name="Version" />
|
||||
<property column="Tid" type="BS.Shared.TableID, BS.Shared" name="_Tid" access="field" />
|
||||
<property column="Tid" type="BS.Shared.TableID, BS.Shared" name="_Tid" access="field" />
|
||||
<property column="AddressLine1" type="String" name="AddressLine1" length="64" />
|
||||
<property column="AddressLine2" type="String" name="AddressLine2" length="64" />
|
||||
<property column="Street" type="String" name="Street" length="256" />
|
||||
<property column="PostalCode" type="String" name="PostalCode" length="128" />
|
||||
<property column="Town" type="String" name="Town" length="256" />
|
||||
<property column="State" type="String" name="State" length="256" />
|
||||
<property column="Country" type="String" name="Country" length="256" />
|
||||
<property column="Notice" type="String" name="Notice" length="1024" />
|
||||
<property column="InsTs" type="DateTime" name="InsTs" />
|
||||
<property column="InsUser" type="String" name="InsUser" length="256" />
|
||||
<property column="UdpUser" type="String" name="UdpUser" length="256" />
|
||||
<property column="IsActive" type="BS.Shared.ActivationTypeId, BS.Shared" name="IsActive" />
|
||||
<property column="SystemEntryID" type="BS.Shared.SystemEntryID, BS.Shared" name="SystemEntryID" />
|
||||
<property column="Street" type="String" name="Street" length="256" />
|
||||
<property column="PostalCode" type="String" name="PostalCode" length="128" />
|
||||
<property column="Town" type="String" name="Town" length="256" />
|
||||
<property column="State" type="String" name="State" length="256" />
|
||||
<property column="Country" type="String" name="Country" length="256" />
|
||||
<property column="Notice" type="String" name="Notice" length="1024" />
|
||||
<property column="InsTs" type="DateTime" name="InsTs" />
|
||||
<property column="InsUser" type="String" name="InsUser" length="256" />
|
||||
<property column="UdpUser" type="String" name="UdpUser" length="256" />
|
||||
<property column="IsActive" type="BS.Shared.ActivationTypeId, BS.Shared" name="IsActive" />
|
||||
<property column="SystemEntryID" type="BS.Shared.SystemEntryID, BS.Shared" name="SystemEntryID" />
|
||||
<property column="Latitude" type="Decimal" name="Latitude" />
|
||||
<property column="Longitude" type="Decimal" name="Longitude" />
|
||||
<property column="L_Version" type="Int64" name="L_Version" />
|
||||
</class>
|
||||
</hibernate-mapping>
|
||||
@@ -15,11 +15,12 @@
|
||||
<property column="UdpUser" type="String" name="UdpUser" length="256" />
|
||||
<property column="SystemEntryID" type="BS.Shared.SystemEntryID, BS.Shared" name="SystemEntryID" />
|
||||
|
||||
<property column="Address1Oid" type="Int64" name="Address1_Oid" />
|
||||
<property column="Address1Version" type="Int64" name="Address1_Version" />
|
||||
<property column="Address2Oid" type="Int64" name="Address2_Oid" />
|
||||
<property column="Address2Version" type="Int64" name="Address2_Version" />
|
||||
<property column="Address1Version" type="Int64" name="Origin_Version" />
|
||||
<property column="Address2Version" type="Int64" name="Destination_Version" />
|
||||
<property column="DistanceMeter" type="Int32" name="Distance_in_meter" />
|
||||
<property column="TimeSec" type="Int32" name="Time_in_seconds" />
|
||||
|
||||
<many-to-one name="Origin" column="Address1Oid" class="BeWo.Data.Entities.Address, BeWo.Data" cascade="all" fetch="join"/>
|
||||
<many-to-one name="Destination" column="Address2Oid" class="BeWo.Data.Entities.Address, BeWo.Data" cascade="all" fetch="join"/>
|
||||
</class>
|
||||
</hibernate-mapping>
|
||||
@@ -104,6 +104,9 @@
|
||||
<add key="DownloadVersionFilePath" value="D:\Rene\ServerBeWoDataExample2\version\update.config" />
|
||||
<add key="GoogleDistanceMatrixApiUrl" value="https://maps.googleapis.com/maps/api/distancematrix/json" />
|
||||
<add key="GoogleDistanceMatrixApiKey" value="AIzaSyDZ_tfNwm_YWC9JiCLQtHsd9X2OUUKuL0c" />
|
||||
<add key="OpenrouteServiceApiUrl" value="https://api.openrouteservice.org/v2/matrix/driving-car" />
|
||||
<add key="OpenrouteServiceApiUrlGeocode" value="https://api.openrouteservice.org/geocode/search" />
|
||||
<add key="OpenrouteServiceApiKey" value="5b3ce3597851110001cf62484b0917529e9a4008acda819dc06e47e8" />
|
||||
</appSettings>
|
||||
<runtime>
|
||||
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
|
||||
|
||||
4
Model/Changes_2023_03_20_Address_Längengrad.txt
Normal file
4
Model/Changes_2023_03_20_Address_Längengrad.txt
Normal file
@@ -0,0 +1,4 @@
|
||||
ALTER TABLE `bewodemo`.`address`
|
||||
ADD COLUMN `Latitude` DECIMAL(8,6) NULL DEFAULT NULL AFTER `AddressLine2`,
|
||||
ADD COLUMN `Longitude` DECIMAL(9,6) NULL DEFAULT NULL AFTER `Latitude`,
|
||||
ADD COLUMN `L_Version` BIGINT(19) NULL DEFAULT NULL AFTER `Longitude`;
|
||||
@@ -21,10 +21,10 @@ namespace BeWo.Service.DCEntityMapper
|
||||
pDataContract.UdpUser = pEntity.UdpUser;
|
||||
pDataContract.SystemEntryID = pEntity.SystemEntryID;
|
||||
|
||||
pDataContract.Address1_Oid = pEntity.Address1_Oid;
|
||||
pDataContract.Address1_Version = pEntity.Address1_Version;
|
||||
pDataContract.Address2_Oid = pEntity.Address2_Oid;
|
||||
pDataContract.Address2_Version = pEntity.Address2_Version;
|
||||
pDataContract.Origin_Address_Oid = pEntity.Origin.Oid.Value;
|
||||
pDataContract.Origin_Address_Version = pEntity.Origin_Version;
|
||||
pDataContract.Destination_Address_Oid = pEntity.Destination.Oid.Value;
|
||||
pDataContract.Destination_Address_Version = pEntity.Destination_Version;
|
||||
|
||||
pDataContract.Distance_in_meter = pEntity.Distance_in_meter;
|
||||
pDataContract.Distance_in_meter_txt = pEntity.Distance_in_meter_txt;
|
||||
@@ -36,21 +36,23 @@ namespace BeWo.Service.DCEntityMapper
|
||||
|
||||
public override AddressRoute MergeWithEntity(AddressRouteDC pDataContract, AddressRoute pEntity)
|
||||
{
|
||||
this.ConcurrencyCheck(pDataContract.Version, pEntity);
|
||||
throw new NotImplementedException("#84971983047130984");
|
||||
|
||||
pEntity.Oid = pDataContract.Oid;
|
||||
pEntity.Notice = pDataContract.Notice;
|
||||
pEntity.SystemEntryID = pDataContract.SystemEntryID;
|
||||
//this.ConcurrencyCheck(pDataContract.Version, pEntity);
|
||||
|
||||
pEntity.Address1_Oid = pDataContract.Address1_Oid;
|
||||
pEntity.Address1_Version = pDataContract.Address1_Version;
|
||||
pEntity.Address2_Oid = pDataContract.Address2_Oid;
|
||||
pEntity.Address2_Version = pDataContract.Address2_Version;
|
||||
//pEntity.Oid = pDataContract.Oid;
|
||||
//pEntity.Notice = pDataContract.Notice;
|
||||
//pEntity.SystemEntryID = pDataContract.SystemEntryID;
|
||||
|
||||
pEntity.Distance_in_meter = pDataContract.Distance_in_meter;
|
||||
pEntity.Distance_in_meter_txt = pDataContract.Distance_in_meter_txt;
|
||||
pEntity.Time_in_seconds = pDataContract.Time_in_sec;
|
||||
pEntity.Time_in_seconds_txt = pDataContract.Time_in_sec_txt;
|
||||
//pEntity.Origin = pDataContract.Origin_Address_Oid;
|
||||
//pEntity.Address1_Version = pDataContract.Origin_Address_Version;
|
||||
//pEntity.Address2_Oid = pDataContract.Destination_Address_Oid;
|
||||
//pEntity.Address2_Version = pDataContract.Destination_Address_Version;
|
||||
|
||||
//pEntity.Distance_in_meter = pDataContract.Distance_in_meter;
|
||||
//pEntity.Distance_in_meter_txt = pDataContract.Distance_in_meter_txt;
|
||||
//pEntity.Time_in_seconds = pDataContract.Time_in_sec;
|
||||
//pEntity.Time_in_seconds_txt = pDataContract.Time_in_sec_txt;
|
||||
|
||||
return pEntity;
|
||||
}
|
||||
|
||||
@@ -484,8 +484,10 @@
|
||||
<Compile Include="ServiceProxy\ServiceFacade.cs" />
|
||||
<Compile Include="ServiceProxy\ServiceGenerated.cs" />
|
||||
<Compile Include="ServiceUtils\DistanceCalculator\AddressRouteManager.cs" />
|
||||
<Compile Include="ServiceUtils\DistanceCalculator\AddressRouteMatrix.cs" />
|
||||
<Compile Include="ServiceUtils\DistanceCalculator\GoogleDistanceMatrixAPI.cs" />
|
||||
<Compile Include="ServiceUtils\DistanceCalculator\IDistanceAPI.cs" />
|
||||
<Compile Include="ServiceUtils\DistanceCalculator\OpenrouteServiceAPI.cs" />
|
||||
<Compile Include="ServiceUtils\Paths\ServerFilePaths.cs" />
|
||||
<Compile Include="ServiceUtils\Update\UpdateFileLimiter.cs" />
|
||||
<Compile Include="ServiceUtils\Update\UpdateServerSession.cs" />
|
||||
|
||||
@@ -42,19 +42,28 @@ namespace BeWo.Service.ServiceImplementations
|
||||
|
||||
public object CallMeForTesting(string token, object input)
|
||||
{
|
||||
if (token != "dafslihjkriouuorgha3431342..")
|
||||
return "Nö";
|
||||
try
|
||||
{
|
||||
if (token != "dafslihjkriouuorgha3431342..")
|
||||
return "Nö";
|
||||
|
||||
var address1 = DAOFactory.GenericDAO.LoadByID<Address>(3000);
|
||||
var address2 = DAOFactory.GenericDAO.LoadByID<Address>(3001);
|
||||
var address3 = DAOFactory.GenericDAO.LoadByID<Address>(3002);
|
||||
var address4 = DAOFactory.GenericDAO.LoadByID<Address>(3003);
|
||||
var address5 = DAOFactory.GenericDAO.LoadByID<Address>(3004);
|
||||
return null;
|
||||
|
||||
var add1 = new Address[] { address1, address2, address5 };
|
||||
var add2 = new Address[] { address3, address4 };
|
||||
var address1 = DAOFactory.GenericDAO.LoadByID<Address>(3000);
|
||||
var address2 = DAOFactory.GenericDAO.LoadByID<Address>(3001);
|
||||
var address3 = DAOFactory.GenericDAO.LoadByID<Address>(3002);
|
||||
var address4 = DAOFactory.GenericDAO.LoadByID<Address>(3003);
|
||||
var address5 = DAOFactory.GenericDAO.LoadByID<Address>(3004);
|
||||
|
||||
AddressRouteManager.GetAddressRoute(add1, add2);
|
||||
var add1 = new Address[] { address1, address2, address5 };
|
||||
var add2 = new Address[] { address3, address4 };
|
||||
|
||||
AddressRouteManager.GetMatrix(add1, add2);
|
||||
}
|
||||
catch(Exception e)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
@@ -1500,7 +1500,7 @@ namespace BeWo.Service.ServiceImplementations
|
||||
}
|
||||
}
|
||||
|
||||
private List<CompactVertreterEmployeeDC> GetDistanceForVertreterEmployees(long customerOid, ref List<CompactVertreterEmployeeDC> list, List<Employee> employees)
|
||||
private void GetDistanceForVertreterEmployees(long customerOid, ref List<CompactVertreterEmployeeDC> list, List<Employee> employees)
|
||||
{
|
||||
var customer = DAOFactory.GenericDAO.LoadByID<Customer>(customerOid);
|
||||
var school = customer.Customer2OrganisationList.FirstOrDefault(f => f.ValueList.Any(b => b.Entry.Type == ValueListEntryType.EnvironmentOrganisationType && b.Entry.Value.Equals("Schule")));
|
||||
@@ -1508,14 +1508,15 @@ namespace BeWo.Service.ServiceImplementations
|
||||
var origin = new Address[] { school.Person.Address };
|
||||
var destinations = employees.Select(x => x.Person.Address).ToArray();
|
||||
|
||||
var routes = AddressRouteManager.GetAddressRoute(origin, destinations);
|
||||
var matrix = AddressRouteManager.GetMatrix(origin, destinations);
|
||||
|
||||
for (int i = 0; i < destinations.Length; i++)
|
||||
Employee empl; AddressRoute route;
|
||||
foreach (var employee in list)
|
||||
{
|
||||
list[i].AddressRoute = MapperFactory.AddressRouteDC_AddressRoute.MapToNewDC(routes[0, i]);
|
||||
empl = employees.FirstOrDefault(e => e.Person.Oid.Value == employee.PersonOid);
|
||||
route = matrix.GetRoute(school.Person.Address, empl.Person.Address);
|
||||
employee.AddressRoute = MapperFactory.AddressRouteDC_AddressRoute.MapToNewDC(route);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public List<EmployeeTokenRelationDC> LoadEmployeeTokenRelationsByOid(IEnumerable<long> pOids)
|
||||
|
||||
@@ -12,196 +12,83 @@ namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
|
||||
static AddressRouteManager()
|
||||
{
|
||||
DistanceAPI = new GoogleDistanceMatrixApi();
|
||||
DistanceAPI =
|
||||
new GoogleDistanceMatrixApi();
|
||||
//new OpenrouteServiceAPI();
|
||||
}
|
||||
|
||||
public static AddressRoute[,] GetAddressRoute(Address[] origins, Address[] destinations)
|
||||
public static AddressRouteMatrix GetMatrix(Address[] origins, Address[] destinations)
|
||||
{
|
||||
var routes = DAOFactory.GenericDAO.GetAll<AddressRoute>();
|
||||
var res = new AddressRoute[origins.Length, destinations.Length];
|
||||
var matrix = new AddressRouteMatrix(origins, destinations);
|
||||
|
||||
//var toRequest = new List<Tuple<int, Address, int, Address, bool>>();
|
||||
var toRequest = new Dictionary<Tuple<int, int>, Tuple<Address, Address, bool, AddressRoute>>();
|
||||
LoadExistingData(ref matrix, routes, out var needUpdate);
|
||||
|
||||
Address origin, destination;
|
||||
for (int i = 0; i < origins.Length; i++)
|
||||
var requests = needUpdate.Union(matrix.GetUnkownRoutes()).ToList();
|
||||
|
||||
// Alles aktuell
|
||||
if (!requests.Any())
|
||||
return matrix;
|
||||
|
||||
var ori2req = requests.Select(x => x.Origin).ToHashSet();
|
||||
var des2req = requests.Select(x => x.Destination).ToHashSet();
|
||||
|
||||
DistanceAPI.RequestMissingData(ref matrix, ori2req, des2req);
|
||||
|
||||
foreach (var req in requests)
|
||||
{
|
||||
origin = origins[i];
|
||||
var route = matrix.GetRoute(req.Origin, req.Destination);
|
||||
|
||||
for (int j = 0; j < destinations.Length; j++)
|
||||
if (route is null)
|
||||
throw new NotImplementedException("Unerwartetes Verhalten #4314513094871");
|
||||
|
||||
route.Origin_Version = route.Origin.Version.Value;
|
||||
route.Destination_Version = route.Destination.Version.Value;
|
||||
|
||||
if (!route.Version.HasValue)
|
||||
{
|
||||
destination = destinations[j];
|
||||
|
||||
var search = routes.FirstOrDefault(route => route.Address1_Oid == origin.Oid && route.Address2_Oid == destination.Oid);
|
||||
|
||||
if (search is AddressRoute)
|
||||
{
|
||||
if (search.Address1_Version == origin.Version && search.Address2_Version == destination.Version)
|
||||
{
|
||||
// Gefunden
|
||||
res[i, j] = search;
|
||||
}
|
||||
else
|
||||
{
|
||||
toRequest.Add(new Tuple<int, int>(i, j), new Tuple<Address, Address, bool, AddressRoute>(origin, destination, false, search));
|
||||
// Braucht Update
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
toRequest.Add(new Tuple<int, int>(i, j), new Tuple<Address, Address, bool, AddressRoute>(origin, destination, true, null));
|
||||
// Neu laden
|
||||
}
|
||||
// Neu
|
||||
DAOFactory.GenericDAO.Insert(req);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Update
|
||||
DAOFactory.GenericDAO.Update(req);
|
||||
}
|
||||
}
|
||||
|
||||
// Falls keine Update benötigt werden
|
||||
if (!toRequest.Any())
|
||||
return res;
|
||||
|
||||
var origins2req = toRequest.Select(keyvalue => keyvalue.Value.Item1).ToHashSet().ToArray();
|
||||
var destinations2req = toRequest.Select(keyvalue => keyvalue.Value.Item2).ToHashSet().ToArray();
|
||||
|
||||
var newRoutes = DistanceAPI.GetAddressRoutes(origins2req, destinations2req);
|
||||
|
||||
for (int i = 0; i < origins.Length; i++)
|
||||
{
|
||||
origin = origins[i];
|
||||
|
||||
for (int j = 0; j < destinations.Length; j++)
|
||||
{
|
||||
destination = destinations[j];
|
||||
|
||||
// bereits gefunden
|
||||
if (res[i, j] is AddressRoute)
|
||||
continue;
|
||||
|
||||
var req = toRequest[new Tuple<int, int>(i, j)];
|
||||
|
||||
var newRoute = FindRoute(newRoutes, req.Item1, req.Item2);
|
||||
|
||||
if (req.Item3)
|
||||
{
|
||||
// Neu
|
||||
DAOFactory.GenericDAO.Insert(newRoute);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Alt
|
||||
var oldRoute = req.Item4;
|
||||
|
||||
oldRoute.Address1_Version = newRoute.Address1_Version;
|
||||
oldRoute.Address2_Version = newRoute.Address2_Version;
|
||||
|
||||
oldRoute.Distance_in_meter = newRoute.Distance_in_meter;
|
||||
oldRoute.Distance_in_meter_txt = newRoute.Distance_in_meter_txt;
|
||||
oldRoute.Time_in_seconds = newRoute.Time_in_seconds;
|
||||
oldRoute.Time_in_seconds_txt = newRoute.Time_in_seconds_txt;
|
||||
|
||||
DAOFactory.GenericDAO.Update(oldRoute);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return res;
|
||||
return matrix;
|
||||
}
|
||||
|
||||
public static AddressRoute FindRoute(AddressRoute[,] routes, Address origin, Address destination)
|
||||
public static void LoadExistingData(ref AddressRouteMatrix matrix, IList<AddressRoute> routes, out List<AddressRoute> needUpdate)
|
||||
{
|
||||
for (int i = 0; i < routes.GetLength(0); i++)
|
||||
{
|
||||
for (int j = 0; j < routes.GetLength(1); j++)
|
||||
{
|
||||
var route = routes[i, j];
|
||||
needUpdate = new List<AddressRoute>();
|
||||
|
||||
if (origin.Oid == route.Address1_Oid && destination.Oid == route.Address2_Oid)
|
||||
return route;
|
||||
foreach (var route in routes)
|
||||
{
|
||||
var origin = route.Origin;
|
||||
var destination = route.Destination;
|
||||
|
||||
if (!matrix.CanUseRoute(origin, destination))
|
||||
continue;
|
||||
|
||||
if (origin.Version == route.Origin_Version && destination.Version == route.Destination_Version)
|
||||
{
|
||||
// Ist aktuell
|
||||
matrix.SetRoute(origin, destination, route);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Braucht Update
|
||||
matrix.SetRoute(origin, destination, route);
|
||||
needUpdate.Add(route);
|
||||
}
|
||||
}
|
||||
|
||||
throw new NotImplementedException("#974289");
|
||||
}
|
||||
|
||||
//public static AddressRoute GetAddressRoute(Address address1, Address address2)
|
||||
//{
|
||||
// var routes = DAOFactory.GenericDAO.GetAll<AddressRoute>();
|
||||
|
||||
// foreach (var route in routes)
|
||||
// {
|
||||
// if (route.Address1_Oid == address1.Oid && route.Address2_Oid == address2.Oid)
|
||||
// {
|
||||
// if (route.Address1_Version == address1.Version && route.Address2_Version == address2.Version)
|
||||
// {
|
||||
// // Route korrekt vorhanden
|
||||
// return route;
|
||||
// }
|
||||
// else
|
||||
// {
|
||||
// // Route vorhanden, aber Addresse hat update
|
||||
// return UpdateAddressRoute(route, address1, address2);
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
// // Route nicht vorhanden
|
||||
// return InsertNewAddressRoute(address1, address2);
|
||||
//}
|
||||
|
||||
//public static void DeleteAddressRoute(long oid) => DeleteAddressRoute(DAOFactory.GenericDAO.LoadByID<AddressRoute>(oid));
|
||||
|
||||
//public static void DeleteAddressRoute(AddressRoute route)
|
||||
//{
|
||||
// if (route is object)
|
||||
// DAOFactory.GenericDAO.Delete(route);
|
||||
//}
|
||||
|
||||
//public static AddressRoute InsertNewAddressRoute(Address address1, Address address2)
|
||||
//{
|
||||
// var newRoute = new AddressRoute
|
||||
// {
|
||||
// Address1_Oid = address1.Oid.Value,
|
||||
// Address2_Oid = address2.Oid.Value
|
||||
// };
|
||||
|
||||
// RequestAddressRoute(ref newRoute, address1, address2);
|
||||
|
||||
// DAOFactory.GenericDAO.Insert(newRoute);
|
||||
|
||||
// return newRoute;
|
||||
//}
|
||||
|
||||
//public static AddressRoute UpdateAddressRoute(AddressRoute route, Address address1, Address address2)
|
||||
//{
|
||||
// RequestAddressRoute(ref route, address1, address2);
|
||||
|
||||
// DAOFactory.GenericDAO.Update(route);
|
||||
|
||||
// return route;
|
||||
//}
|
||||
|
||||
//public static AddressRoute RequestAddressRoute(ref AddressRoute route, Address address1, Address address2)
|
||||
//{
|
||||
// route.Address1_Version = address1.Version.Value;
|
||||
// route.Address2_Version = address2.Version.Value;
|
||||
|
||||
// // Calculate Distance
|
||||
|
||||
// var api = new GoogleDistanceMatrixApi(address1, address2);
|
||||
// var task = api.GetResponse();
|
||||
|
||||
// task.Wait();
|
||||
|
||||
// if (task.Exception is object)
|
||||
// {
|
||||
// throw task.Exception;
|
||||
// }
|
||||
|
||||
// route.Distance_in_meter = task.Result.Rows[0].Elements[0].Distance.Value;
|
||||
// route.Distance_in_meter_txt = task.Result.Rows[0].Elements[0].Distance.Text;
|
||||
// route.Time_in_seconds = task.Result.Rows[0].Elements[0].Duration.Value;
|
||||
// route.Time_in_seconds_txt = task.Result.Rows[0].Elements[0].Duration.Text;
|
||||
|
||||
// return route;
|
||||
//}
|
||||
public static string AddressToString(Address address)
|
||||
{
|
||||
return $"{address.Street}, {address.PostalCode}, {address.Town}, {address.State}, {address.Country}";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
using BeWo.Data.Entities;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
{
|
||||
public class AddressRouteMatrix
|
||||
{
|
||||
public int OriginsLength { get; set; }
|
||||
public int DestinationsLength { get; set; }
|
||||
|
||||
public Address[] OriginAddresses { get; set; }
|
||||
public Address[] DestinationAddresses { get; set; }
|
||||
public Dictionary<Address, int> Origins { get; set; }
|
||||
public Dictionary<Address, int> Destinations { get; set; }
|
||||
public AddressRoute[,] Routes { get; set; }
|
||||
|
||||
public AddressRouteMatrix(Address[] originAddresses, Address[] destinationAddresses)
|
||||
{
|
||||
OriginAddresses = originAddresses;
|
||||
Origins = new Dictionary<Address, int>();
|
||||
OriginsLength = originAddresses.Length;
|
||||
|
||||
DestinationAddresses = destinationAddresses;
|
||||
Destinations = new Dictionary<Address, int>();
|
||||
DestinationsLength = destinationAddresses.Length;
|
||||
|
||||
int i;
|
||||
for (i = 0; i < OriginsLength; i++)
|
||||
{
|
||||
Origins.Add(originAddresses[i], i);
|
||||
}
|
||||
|
||||
for (i = 0; i < DestinationsLength; i++)
|
||||
{
|
||||
Destinations.Add(destinationAddresses[i], i);
|
||||
}
|
||||
|
||||
Routes = new AddressRoute[OriginsLength, DestinationsLength];
|
||||
}
|
||||
|
||||
public void SetRoute(Address origin, Address destination, AddressRoute value) => Routes[Origins[origin], Destinations[destination]] = value;
|
||||
public AddressRoute GetRoute(Address origin, Address destination)
|
||||
{
|
||||
return Routes[Origins[origin], Destinations[destination]];
|
||||
}
|
||||
|
||||
public IEnumerable<AddressRoute> GetUnkownRoutes()
|
||||
{
|
||||
for (int i = 0; i < OriginsLength; i++)
|
||||
{
|
||||
for (int j = 0; j < DestinationsLength; j++)
|
||||
{
|
||||
var route = Routes[i, j];
|
||||
|
||||
if (route is null)
|
||||
{
|
||||
route = new AddressRoute
|
||||
{
|
||||
Origin = OriginAddresses[i],
|
||||
Destination = DestinationAddresses[j]
|
||||
};
|
||||
|
||||
Routes[i, j] = route;
|
||||
|
||||
yield return route;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public bool CanUseRoute(Address origin, Address destination)
|
||||
{
|
||||
if (!Origins.ContainsKey(origin))
|
||||
return false;
|
||||
if (!Destinations.ContainsKey(destination))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -48,6 +48,8 @@ namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
private string Key { get; set; }
|
||||
private string Url { get; set; }
|
||||
|
||||
private AddressRouteMatrix Matrix { get; set; }
|
||||
|
||||
private Address[] OriginAddresses { get; set; }
|
||||
private Address[] DestinationAddresses { get; set; }
|
||||
|
||||
@@ -68,12 +70,13 @@ namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
Key = appSettings["GoogleDistanceMatrixApiKey"];
|
||||
}
|
||||
|
||||
public AddressRoute[,] GetAddressRoutes(Address[] originAddresses, Address[] destinationAddresses)
|
||||
public void RequestMissingData(ref AddressRouteMatrix matrix, IEnumerable<Address> origins, IEnumerable<Address> destinations)
|
||||
{
|
||||
OriginAddresses = originAddresses;
|
||||
DestinationAddresses = destinationAddresses;
|
||||
Matrix = matrix;
|
||||
OriginAddresses = origins.ToArray();
|
||||
DestinationAddresses = destinations.ToArray();
|
||||
|
||||
var task = GetResponse();
|
||||
var task = GetMatrix();
|
||||
|
||||
task.Wait();
|
||||
|
||||
@@ -81,11 +84,9 @@ namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
{
|
||||
throw task.Exception;
|
||||
}
|
||||
|
||||
return task.Result;
|
||||
}
|
||||
|
||||
public async Task<AddressRoute[,]> GetResponse()
|
||||
public async Task<AddressRouteMatrix> GetMatrix()
|
||||
{
|
||||
using (var client = new HttpClient())
|
||||
{
|
||||
@@ -100,33 +101,33 @@ namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
{
|
||||
var content = await response.Content.ReadAsStringAsync();
|
||||
|
||||
return ToAddressRouteArray(JsonConvert.DeserializeObject<Response>(content));
|
||||
return FillMatrix(JsonConvert.DeserializeObject<Response>(content));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public AddressRoute[,] ToAddressRouteArray(Response response)
|
||||
public AddressRouteMatrix FillMatrix(Response response)
|
||||
{
|
||||
var res = new AddressRoute[OriginAddresses.Length, DestinationAddresses.Length];
|
||||
|
||||
for (int i = 0; i < response.Rows.Length; i++)
|
||||
{
|
||||
var row = response.Rows[i];
|
||||
var origin = OriginAddresses[i];
|
||||
|
||||
for (int j = 0; j < row.Elements.Length; j++)
|
||||
{
|
||||
var element = row.Elements[j];
|
||||
var destination = DestinationAddresses[j];
|
||||
|
||||
res[i, j] = ToAddressRoute(element);
|
||||
var route = Matrix.GetRoute(origin, destination);
|
||||
|
||||
res[i, j].Address1_Oid = OriginAddresses[i].Oid.Value;
|
||||
res[i, j].Address1_Version = OriginAddresses[i].Version.Value;
|
||||
res[i, j].Address2_Oid = DestinationAddresses[j].Oid.Value;
|
||||
res[i, j].Address2_Version = DestinationAddresses[j].Version.Value;
|
||||
route.Distance_in_meter = element.Distance.Value;
|
||||
route.Distance_in_meter_txt = element.Distance.Text;
|
||||
route.Time_in_seconds = element.Duration.Value;
|
||||
route.Time_in_seconds_txt = element.Duration.Text;
|
||||
}
|
||||
}
|
||||
|
||||
return res;
|
||||
return Matrix;
|
||||
}
|
||||
|
||||
public AddressRoute ToAddressRoute(Response.Element element)
|
||||
@@ -143,16 +144,11 @@ namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
|
||||
private string GetRequestUrl()
|
||||
{
|
||||
var originAddresses = OriginAddresses.Select(str => ToGoogle(str)).Select(HttpUtility.UrlEncode).ToArray();
|
||||
var originAddresses = OriginAddresses.Select(str => AddressRouteManager.AddressToString(str)).Select(HttpUtility.UrlEncode).ToArray();
|
||||
var origins = string.Join("|", originAddresses);
|
||||
var destinationAddresses = DestinationAddresses.Select(str => ToGoogle(str)).Select(HttpUtility.UrlEncode).ToArray();
|
||||
var destinationAddresses = DestinationAddresses.Select(str => AddressRouteManager.AddressToString(str)).Select(HttpUtility.UrlEncode).ToArray();
|
||||
var destinations = string.Join("|", destinationAddresses);
|
||||
return $"{Url}?origins={origins}&destinations={destinations}&key={Key}";
|
||||
}
|
||||
|
||||
public static string ToGoogle(Address add)
|
||||
{
|
||||
return $"{add.Street}, {add.PostalCode}, {add.Town}, {add.State}, {add.Country}";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -10,6 +10,10 @@ namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
{
|
||||
public interface IDistanceAPI
|
||||
{
|
||||
AddressRoute[,] GetAddressRoutes(Address[] originAddresses, Address[] destinationAddresses);
|
||||
//AddressRoute[,] GetAddressRoutes(Address[] originAddresses, Address[] destinationAddresses);
|
||||
|
||||
//AddressRouteMatrix GetAddressRouteMatrix(Address[] originAddresses, Address[] destinationAddresses);
|
||||
|
||||
void RequestMissingData(ref AddressRouteMatrix matrix, IEnumerable<Address> origins, IEnumerable<Address> destinations);
|
||||
}
|
||||
}
|
||||
|
||||
259
Service/ServiceUtils/DistanceCalculator/OpenrouteServiceAPI.cs
Normal file
259
Service/ServiceUtils/DistanceCalculator/OpenrouteServiceAPI.cs
Normal file
@@ -0,0 +1,259 @@
|
||||
using BeWo.Data.Access;
|
||||
using BeWo.Data.Entities;
|
||||
using Newtonsoft.Json;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Configuration;
|
||||
using System.Globalization;
|
||||
using System.Linq;
|
||||
using System.Net.Http;
|
||||
using System.Net.Http.Headers;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using System.Web;
|
||||
using Task = System.Threading.Tasks.Task;
|
||||
|
||||
namespace BeWo.Service.ServiceUtils.DistanceCalculator
|
||||
{
|
||||
public class OpenrouteServiceAPI : IDistanceAPI
|
||||
{
|
||||
public class ResponseGeo
|
||||
{
|
||||
public Feature[] Features { get; set; }
|
||||
|
||||
public class Feature
|
||||
{
|
||||
public string Type { get; set; }
|
||||
public Geometry Geometry { get; set; }
|
||||
}
|
||||
|
||||
public class Geometry
|
||||
{
|
||||
public string Type { get; set; }
|
||||
public decimal[] Coordinates { get; set; }
|
||||
}
|
||||
}
|
||||
|
||||
public class ResponseMatrix
|
||||
{
|
||||
public decimal[,] Durations { get; set; }
|
||||
public decimal[,] Distances { get; set; }
|
||||
}
|
||||
|
||||
private string Key { get; set; }
|
||||
private string GeoKey { get; set; }
|
||||
private string Url { get; set; }
|
||||
|
||||
private AddressRouteMatrix Matrix { get; set; }
|
||||
|
||||
private Address[] OriginAddresses { get; set; }
|
||||
private Address[] DestinationAddresses { get; set; }
|
||||
|
||||
public OpenrouteServiceAPI()
|
||||
{
|
||||
var appSettings = ConfigurationManager.AppSettings;
|
||||
|
||||
if (string.IsNullOrEmpty(appSettings["OpenrouteServiceApiUrl"]))
|
||||
{
|
||||
throw new Exception("OpenrouteServiceApiUrl is not set in AppSettings.");
|
||||
}
|
||||
Url = appSettings["OpenrouteServiceApiUrl"];
|
||||
|
||||
if (string.IsNullOrEmpty(appSettings["OpenrouteServiceApiKey"]))
|
||||
{
|
||||
throw new Exception("OpenrouteServiceApiKey is not set in AppSettings.");
|
||||
}
|
||||
Key = appSettings["OpenrouteServiceApiKey"];
|
||||
|
||||
if (string.IsNullOrEmpty(appSettings["OpenrouteServiceApiUrlGeocode"]))
|
||||
{
|
||||
throw new Exception("OpenrouteServiceApiUrlGeocode is not set in AppSettings.");
|
||||
}
|
||||
GeoKey = appSettings["OpenrouteServiceApiUrlGeocode"];
|
||||
}
|
||||
|
||||
public void RequestMissingData(ref AddressRouteMatrix matrix, IEnumerable<Address> origins, IEnumerable<Address> destinations)
|
||||
{
|
||||
Matrix = matrix;
|
||||
OriginAddresses = origins.ToArray();
|
||||
DestinationAddresses = destinations.ToArray();
|
||||
|
||||
if (!(origins.Any() && destinations.Any()))
|
||||
throw new NotImplementedException("Keine Addresse angefragt");
|
||||
|
||||
LoadCoordinates().Wait();
|
||||
|
||||
var task = GetMatrix();
|
||||
|
||||
task.Wait();
|
||||
|
||||
if (task.Exception is object)
|
||||
{
|
||||
throw task.Exception;
|
||||
}
|
||||
}
|
||||
|
||||
public async Task LoadCoordinates()
|
||||
{
|
||||
// Update Koordinaten
|
||||
var items = OriginAddresses.Union(DestinationAddresses).ToHashSet();
|
||||
foreach (var item in items)
|
||||
{
|
||||
if (item.L_Version is object && item.L_Version == item.Version)
|
||||
continue;
|
||||
|
||||
await LoadCoordinate(item);
|
||||
|
||||
DAOFactory.GenericDAO.Update(item);
|
||||
}
|
||||
}
|
||||
|
||||
public async Task LoadCoordinate(Address address)
|
||||
{
|
||||
using (var client = new HttpClient())
|
||||
{
|
||||
var uri = new Uri(GetGeocodeUrl(address));
|
||||
|
||||
client.DefaultRequestHeaders.Clear();
|
||||
client.DefaultRequestHeaders.TryAddWithoutValidation("accept", "application/json; charset=utf-8");
|
||||
client.DefaultRequestHeaders.TryAddWithoutValidation("Content-Type", "application/json; charset=utf-8");
|
||||
|
||||
using (var response = await client.GetAsync(uri))
|
||||
{
|
||||
string responseData = await response.Content.ReadAsStringAsync();
|
||||
|
||||
if (response.IsSuccessStatusCode)
|
||||
{
|
||||
try
|
||||
{
|
||||
var data = JsonConvert.DeserializeObject<ResponseGeo>(responseData);
|
||||
|
||||
address.Longitude = data.Features[0].Geometry.Coordinates[0];
|
||||
address.Latitude = data.Features[0].Geometry.Coordinates[1];
|
||||
address.L_Version = address.Version.Value + 1;
|
||||
|
||||
return;
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw e;
|
||||
}
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("OpenrouteServiceAPI failed with status code: " + response.StatusCode + " |||Data: " + responseData);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public async Task<AddressRouteMatrix> GetMatrix()
|
||||
{
|
||||
using (var client = new HttpClient())
|
||||
{
|
||||
var uri = new Uri(Url);
|
||||
|
||||
client.DefaultRequestHeaders.Clear();
|
||||
client.DefaultRequestHeaders.TryAddWithoutValidation("accept", "application/json; charset=utf-8");
|
||||
client.DefaultRequestHeaders.TryAddWithoutValidation("Content-Type", "application/json; charset=utf-8");
|
||||
client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", Key);
|
||||
|
||||
using (var content = new StringContent(GetMatrixBodyContentString()))
|
||||
//using (var content = new StringContent("{\"locations\":[[48.477473,9.70093],[49.153868,9.207916]]}"))
|
||||
{
|
||||
content.Headers.ContentType = new MediaTypeHeaderValue("application/json");
|
||||
using (var response = await client.PostAsync(uri, content))
|
||||
{
|
||||
string responseData = await response.Content.ReadAsStringAsync();
|
||||
|
||||
if (response.IsSuccessStatusCode)
|
||||
{
|
||||
var data = JsonConvert.DeserializeObject<ResponseMatrix>(responseData);
|
||||
|
||||
return FillMatrix(data);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception("OpenrouteServiceAPI failed with status code: " + response.StatusCode + " |||Data: " + responseData);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public AddressRouteMatrix FillMatrix(ResponseMatrix response)
|
||||
{
|
||||
for (int i = 0; i < response.Durations.GetLength(0); i++)
|
||||
{
|
||||
for (int j = 0; j < response.Durations.GetLength(1); j++)
|
||||
{
|
||||
var distance = response.Distances[i, j];
|
||||
var duration = response.Durations[i, j];
|
||||
|
||||
var origin = OriginAddresses[i];
|
||||
var destination = DestinationAddresses[j];
|
||||
|
||||
var route = Matrix.GetRoute(origin, destination);
|
||||
|
||||
route.Distance_in_meter = (int) (distance * 1000);
|
||||
route.Time_in_seconds = (int) duration;
|
||||
}
|
||||
}
|
||||
|
||||
return Matrix;
|
||||
}
|
||||
|
||||
private string GetGeocodeUrl(Address address)
|
||||
{
|
||||
var html = HttpUtility.UrlEncode(AddressRouteManager.AddressToString(address));
|
||||
return $"{GeoKey}?api_key={Key}&text={html}&sources=openstreetmap&size=1";
|
||||
}
|
||||
|
||||
private string GetMatrixBodyContentString()
|
||||
{
|
||||
var sb = new StringBuilder();
|
||||
|
||||
var origins = OriginAddresses.Select(GetCoordinates);
|
||||
var olen = OriginAddresses.Count();
|
||||
var destination = DestinationAddresses.Select(GetCoordinates);
|
||||
var dlen = DestinationAddresses.Count();
|
||||
|
||||
sb.Append("{\"locations\":");
|
||||
sb.Append("[");
|
||||
sb.Append(string.Join(",", origins.Union(destination)));
|
||||
sb.Append("]");
|
||||
|
||||
sb.Append(",\"metrics\":[\"distance\",\"duration\"]");
|
||||
sb.Append(",\"units\":\"km\"");
|
||||
|
||||
sb.Append(",\"sources\":");
|
||||
sb.Append(GetList(0, olen - 1));
|
||||
|
||||
sb.Append(",\"destinations\":");
|
||||
sb.Append(GetList(olen, olen + dlen - 1));
|
||||
|
||||
sb.Append("}");
|
||||
|
||||
return sb.ToString();
|
||||
}
|
||||
|
||||
private string GetCoordinates(Address add) => $"[{add.Longitude.Value.ToString(new CultureInfo("en-US"))},{add.Latitude.Value.ToString(new CultureInfo("en-US"))}]";
|
||||
|
||||
private string GetList(int x, int y)
|
||||
{
|
||||
if (y < x)
|
||||
throw new ArgumentException($"y({y}) darf nicht kleiner als x({x}) sein");
|
||||
|
||||
var diff = y - x;
|
||||
var list = new int[diff + 1];
|
||||
|
||||
for (int i = 0; i <= diff; i++)
|
||||
{
|
||||
list[i] = x + i;
|
||||
}
|
||||
|
||||
return "[" + string.Join(",", list) + "]";
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -34,16 +34,16 @@ namespace BS.Shared.DataContracts
|
||||
public SystemEntryID? SystemEntryID { get; set; }
|
||||
|
||||
[DataMember]
|
||||
public long Address1_Oid { get; set; }
|
||||
public long Origin_Address_Oid { get; set; }
|
||||
|
||||
[DataMember]
|
||||
public long Address1_Version { get; set; }
|
||||
public long Origin_Address_Version { get; set; }
|
||||
|
||||
[DataMember]
|
||||
public long Address2_Oid { get; set; }
|
||||
public long Destination_Address_Oid { get; set; }
|
||||
|
||||
[DataMember]
|
||||
public long Address2_Version { get; set; }
|
||||
public long Destination_Address_Version { get; set; }
|
||||
|
||||
[DataMember]
|
||||
public int Distance_in_meter { get; set; }
|
||||
|
||||
Reference in New Issue
Block a user