changed some code around

feature/haulmkilling
Mark van der Wal 2020-03-25 17:49:00 +01:00
parent d546edaa0d
commit e638370ad4
6 changed files with 154 additions and 160 deletions

View File

@ -1,5 +1,4 @@
using System;
using System.Collections;
using System.IO;
using System.Net.Http;
using System.Net.Mime;
@ -69,6 +68,8 @@ namespace FarmmapsApi.Services
contentStream.ThrowIfNull(nameof(contentStream));
_streamLength = ContentStream.CanSeek ? ContentStream.Length : UnknownSize;
body.ChunkSize = ChunkSize;
Body = body;
Path = "api/v1/file";
HttpClient = httpClient;
@ -93,16 +94,12 @@ namespace FarmmapsApi.Services
/// <summary>Creates a request to initialize a request.</summary>
private HttpRequestMessage CreateInitializeRequest()
{
var baseAddres = HttpClient.BaseAddress;
var uri = new Uri($"{baseAddres.Scheme}://{baseAddres.Host}:{baseAddres.Port}");
var builder = new RequestBuilder()
{
BaseUri = uri,
BaseUri = HttpClient.BaseAddress,
Path = Path,
Method = HttpMethod,
};
SetAllPropertyValues(builder);
HttpRequestMessage request = builder.CreateRequest();
if (ContentType != null)
@ -121,40 +118,5 @@ namespace FarmmapsApi.Services
return request;
}
/// <summary>
/// Reflectively enumerate the properties of this object looking for all properties containing the
/// RequestParameterAttribute and copy their values into the request builder.
/// </summary>
private void SetAllPropertyValues(RequestBuilder requestBuilder)
{
Type myType = this.GetType();
var properties = myType.GetProperties();
foreach (var property in properties)
{
var attribute = property.GetCustomAttribute<RequestParameterAttribute>();
if (attribute != null)
{
string name = attribute.Name ?? property.Name.ToLower();
object value = property.GetValue(this, null);
if (value != null)
{
if (!(value is string) && value is IEnumerable valueAsEnumerable)
{
foreach (var elem in valueAsEnumerable)
{
requestBuilder.AddParameter(attribute.Type, name, Utilities.ConvertToString(elem));
}
}
else
{
// Otherwise just convert it to a string.
requestBuilder.AddParameter(attribute.Type, name, Utilities.ConvertToString(value));
}
}
}
}
}
}
}

View File

@ -0,0 +1,10 @@
namespace FarmmapsApiSamples
{
public static class Constants
{
public const string USERINPUT_ITEMTYPE = "vnd.farmmaps.itemtype.user.input";
public const string GEOTIFF_ITEMTYPE = "vnd.farmmaps.itemtype.geotiff";
public const string CROPFIELD_ITEMTYPE = "vnd.farmmaps.itemtype.cropfield";
public const string VRANBS_TASK = "vnd.farmmaps.task.vranbs";
}
}

View File

@ -1,5 +1,4 @@
using System;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Threading.Tasks;
@ -8,24 +7,22 @@ using FarmmapsApi.Services;
using Google.Apis.Upload;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json.Linq;
using static FarmmapsApi.Extensions;
using static FarmmapsApiSamples.Constants;
namespace FarmmapsApiSamples
{
public class NbsApp : IApp
{
private const string USERINPUT_ITEMTYPE = "vnd.farmmaps.itemtype.user.input";
private const string GEOTIFF_ITEMTYPE = "vnd.farmmaps.itemtype.geotiff";
private const string CROPFIELD_ITEMTYPE = "vnd.farmmaps.itemtype.cropfield";
private const string VRANBS_TASK = "vnd.farmmaps.task.vranbs";
private readonly ILogger<NbsApp> _logger;
private readonly FarmmapsApiService _farmmapsApiService;
private readonly NitrogenService _nitrogenService;
public NbsApp(ILogger<NbsApp> logger, FarmmapsApiService farmmapsApiService)
public NbsApp(ILogger<NbsApp> logger, FarmmapsApiService farmmapsApiService,
NitrogenService nitrogenService)
{
_logger = logger;
_farmmapsApiService = farmmapsApiService;
_nitrogenService = nitrogenService;
farmmapsApiService.EventCallback += OnEvent;
}
@ -40,13 +37,13 @@ namespace FarmmapsApiSamples
try
{
_logger.LogInformation("NBS sample app started");
await _farmmapsApiService.AuthenticateAsync();
_logger.LogInformation("Authenticated client credentials");
var roots = await _farmmapsApiService.GetCurrentUserRootsAsync();
// upload data to Uploaded
var uploadedRoot = roots.SingleOrDefault(r => r.Name == "Uploaded");
if (uploadedRoot != null)
@ -55,21 +52,21 @@ namespace FarmmapsApiSamples
progress =>
{
_logger.LogInformation($"Status: {progress.Status} - BytesSent: {progress.BytesSent}");
if(progress.Status == UploadStatus.Failed)
if (progress.Status == UploadStatus.Failed)
_logger.LogError($"Uploading failed {progress.Exception.Message}");
});
// need to transform shape data to geotiff
var myDriveRoot = roots.SingleOrDefault(r => r.Name == "My drive");
if (myDriveRoot != null)
{
var cropfieldItem = await GetOrCreateCropfieldItem(myDriveRoot.Code);
_logger.LogInformation($"Calculating targetN with targetYield: {60}");
var targetN = await CalculateTargetN(cropfieldItem, 60);
var targetN = await _nitrogenService.CalculateTargetN(cropfieldItem, 60);
_logger.LogInformation($"TargetN: {targetN}");
_logger.LogInformation("Calculating nitrogen map");
// var nitrogenMapItem = CalculateNitrogenMap(cropfieldItem,, targetN);
}
@ -84,9 +81,9 @@ namespace FarmmapsApiSamples
private async Task<Item> GetOrCreateCropfieldItem(string parentItemCode)
{
var cropfieldItems = await
_farmmapsApiService.GetItemChildrenAsync(parentItemCode,CROPFIELD_ITEMTYPE);
_farmmapsApiService.GetItemChildrenAsync(parentItemCode, CROPFIELD_ITEMTYPE);
if (cropfieldItems.Count > 0)
if (cropfieldItems.Count > 0)
return cropfieldItems[0];
var currentYear = new DateTime(DateTime.UtcNow.Year, 1, 1);
@ -105,106 +102,5 @@ namespace FarmmapsApiSamples
return await _farmmapsApiService.CreateItemAsync(cropfieldItemRequest);
}
/// <summary>
/// Calculates TargetN, makes the assumption the cropfield and user.input(targetn) item have the same parent
/// </summary>
/// <param name="cropfieldItem">The cropfield to base the calculations on</param>
/// <param name="targetYield">The target yield input for the TargetN calculation</param>
/// <returns>The TargetN</returns>
private async Task<double> CalculateTargetN(Item cropfieldItem, int targetYield)
{
var targetNItems = await
_farmmapsApiService.GetItemChildrenAsync(cropfieldItem.ParentCode, USERINPUT_ITEMTYPE);
Item targetNItem;
if (targetNItems.Count == 0)
{
_logger.LogInformation("Creating targetN item");
var itemRequest = CreateTargetNItemRequest(cropfieldItem.ParentCode);
targetNItem = await _farmmapsApiService.CreateItemAsync(itemRequest);
}
else
{
targetNItem = targetNItems[0];
}
var nbsTargetNRequest = new TaskRequest {TaskType = VRANBS_TASK};
nbsTargetNRequest.attributes["operation"] = "targetn";
nbsTargetNRequest.attributes["inputCode"] = targetNItem.Code;
nbsTargetNRequest.attributes["inputType"] = "irmi";
nbsTargetNRequest.attributes["purposeType"] = "consumption";
nbsTargetNRequest.attributes["targetYield"] = targetYield.ToString();
string itemTaskCode = await _farmmapsApiService.QueueTaskAsync(cropfieldItem.Code, nbsTargetNRequest);
await PollTask(TimeSpan.FromSeconds(3), async (tokenSource) =>
{
var itemTaskStatus = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if (itemTaskStatus.State != ItemTaskState.Processing && itemTaskStatus.State != ItemTaskState.Scheduled)
tokenSource.Cancel();
});
var itemTask = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if(itemTask.State == ItemTaskState.Error)
{
_logger.LogError($"Something went wrong with task execution: {itemTask.Message}");
return 0;
}
var item = await _farmmapsApiService.GetItemAsync(targetNItem.Code);
if (item.Data.ContainsKey("TargetN"))
return item.Data["TargetN"].Value<double>();
return 0;
}
private async Task<Item> CalculateNitrogenMap(Item cropfieldItem, Item inputItem, double targetN)
{
var nbsNitrogenRequest = new TaskRequest {TaskType = VRANBS_TASK};
nbsNitrogenRequest.attributes["operation"] = "nitrogen";
nbsNitrogenRequest.attributes["inputCode"] = inputItem.Code;
nbsNitrogenRequest.attributes["inputType"] = "irmi";
nbsNitrogenRequest.attributes["targetN"] = targetN.ToString(CultureInfo.InvariantCulture);
string itemTaskCode = await _farmmapsApiService.QueueTaskAsync(cropfieldItem.Code, nbsNitrogenRequest);
await PollTask(TimeSpan.FromSeconds(5), async (tokenSource) =>
{
var itemTaskStatus = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if (itemTaskStatus.State != ItemTaskState.Processing && itemTaskStatus.State != ItemTaskState.Scheduled)
tokenSource.Cancel();
});
var itemTask = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if(itemTask.State == ItemTaskState.Error)
{
_logger.LogError($"Something went wrong with task execution: {itemTask.Message}");
return null;
}
var geotiffItems = await
_farmmapsApiService.GetItemChildrenAsync(cropfieldItem.Code, GEOTIFF_ITEMTYPE);
// how to uniquely know which item is really created!?
var nitrogenItem = geotiffItems.SingleOrDefault(i => i.Name.Contains("nitrogen"));
if (nitrogenItem == null)
{
_logger.LogError("Could not find the nitrogen geotiff child item under cropfield");
return null;
}
return nitrogenItem;
}
private ItemRequest CreateTargetNItemRequest(string parentItemCode)
{
return new ItemRequest()
{
ParentCode = parentItemCode,
ItemType = USERINPUT_ITEMTYPE,
Name = "TargetN",
DataDate = DateTime.UtcNow
};
}
}
}

View File

@ -0,0 +1,125 @@
using System;
using System.Globalization;
using System.Linq;
using System.Threading.Tasks;
using FarmmapsApi.Models;
using FarmmapsApi.Services;
using Microsoft.Extensions.Logging;
using static FarmmapsApi.Extensions;
using static FarmmapsApiSamples.Constants;
namespace FarmmapsApiSamples
{
public class NitrogenService
{
private readonly ILogger<NitrogenService> _logger;
private readonly FarmmapsApiService _farmmapsApiService;
public NitrogenService(ILogger<NitrogenService> logger, FarmmapsApiService farmmapsApiService)
{
_logger = logger;
_farmmapsApiService = farmmapsApiService;
}
/// <summary>
/// Calculates TargetN, makes the assumption the cropfield and user.input(targetn) item have the same parent
/// </summary>
/// <param name="cropfieldItem">The cropfield to base the calculations on</param>
/// <param name="targetYield">The target yield input for the TargetN calculation</param>
/// <returns>The TargetN</returns>
public async Task<double> CalculateTargetN(Item cropfieldItem, int targetYield)
{
var targetNItems = await
_farmmapsApiService.GetItemChildrenAsync(cropfieldItem.ParentCode, USERINPUT_ITEMTYPE);
Item targetNItem;
if (targetNItems.Count == 0)
{
_logger.LogInformation("Creating targetN item");
var itemRequest = CreateTargetNItemRequest(cropfieldItem.ParentCode);
targetNItem = await _farmmapsApiService.CreateItemAsync(itemRequest);
}
else
{
targetNItem = targetNItems[0];
}
var nbsTargetNRequest = new TaskRequest {TaskType = VRANBS_TASK};
nbsTargetNRequest.attributes["operation"] = "targetn";
nbsTargetNRequest.attributes["inputCode"] = targetNItem.Code;
nbsTargetNRequest.attributes["inputType"] = "irmi";
nbsTargetNRequest.attributes["purposeType"] = "consumption";
nbsTargetNRequest.attributes["targetYield"] = targetYield.ToString();
string itemTaskCode = await _farmmapsApiService.QueueTaskAsync(cropfieldItem.Code, nbsTargetNRequest);
await PollTask(TimeSpan.FromSeconds(3), async (tokenSource) =>
{
var itemTaskStatus = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if (itemTaskStatus.State != ItemTaskState.Processing && itemTaskStatus.State != ItemTaskState.Scheduled)
tokenSource.Cancel();
});
var itemTask = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if(itemTask.State == ItemTaskState.Error)
{
_logger.LogError($"Something went wrong with task execution: {itemTask.Message}");
return 0;
}
var item = await _farmmapsApiService.GetItemAsync(targetNItem.Code);
if (item.Data.ContainsKey("TargetN"))
return item.Data.Value<double>("TargetN");
return 0;
}
public async Task<Item> CalculateNitrogenMap(Item cropfieldItem, Item inputItem, double targetN)
{
var nbsNitrogenRequest = new TaskRequest {TaskType = VRANBS_TASK};
nbsNitrogenRequest.attributes["operation"] = "nitrogen";
nbsNitrogenRequest.attributes["inputCode"] = inputItem.Code;
nbsNitrogenRequest.attributes["inputType"] = "irmi";
nbsNitrogenRequest.attributes["targetN"] = targetN.ToString(CultureInfo.InvariantCulture);
string itemTaskCode = await _farmmapsApiService.QueueTaskAsync(cropfieldItem.Code, nbsNitrogenRequest);
await PollTask(TimeSpan.FromSeconds(5), async (tokenSource) =>
{
var itemTaskStatus = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if (itemTaskStatus.State != ItemTaskState.Processing && itemTaskStatus.State != ItemTaskState.Scheduled)
tokenSource.Cancel();
});
var itemTask = await _farmmapsApiService.GetTaskStatusAsync(cropfieldItem.Code, itemTaskCode);
if(itemTask.State == ItemTaskState.Error)
{
_logger.LogError($"Something went wrong with task execution: {itemTask.Message}");
return null;
}
var geotiffItems = await
_farmmapsApiService.GetItemChildrenAsync(cropfieldItem.Code, GEOTIFF_ITEMTYPE);
// how to uniquely know which item is really created!?
var nitrogenItem = geotiffItems.SingleOrDefault(i => i.Name.Contains("nitrogen"));
if (nitrogenItem == null)
{
_logger.LogError("Could not find the nitrogen geotiff child item under cropfield");
return null;
}
return nitrogenItem;
}
private ItemRequest CreateTargetNItemRequest(string parentItemCode)
{
return new ItemRequest()
{
ParentCode = parentItemCode,
ItemType = USERINPUT_ITEMTYPE,
Name = "TargetN",
DataDate = DateTime.UtcNow
};
}
}
}

View File

@ -27,6 +27,7 @@ namespace FarmmapsApiSamples
})
.AddFilter("System.Net.Http", LogLevel.Warning))
.AddFarmmapsServices(configuration)
.AddTransient<NitrogenService>()
.AddSingleton<IApp, NbsApp>()
.BuildServiceProvider();

View File

@ -1,6 +1,6 @@
{
"Authority": "https://accounts.farmmaps.awtest.nl/",
"Endpoint": "http://localhost:8083",
"Endpoint": "https://farmmaps.awtest.nl/",
"BasePath": "api/v1",
"DiscoveryEndpointUrl": "https://accounts.farmmaps.awtest.nl/.well-known/openid-configuration",
"RedirectUri": "http://example.nl/api",