Simulation input validation (#140)
This commit is contained in:
Родитель
9e88ab3e69
Коммит
4d8168da33
|
@ -4,7 +4,6 @@ using System.Threading.Tasks;
|
|||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.Services;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.Services.Diagnostics;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.Services.Models;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Exceptions;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Filters;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Models;
|
||||
|
@ -43,6 +42,8 @@ namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Controller
|
|||
[FromBody] SimulationApiModel simulation,
|
||||
[FromQuery(Name = "template")] string template = "")
|
||||
{
|
||||
simulation?.ValidateInputRequest(this.log);
|
||||
|
||||
if (simulation == null)
|
||||
{
|
||||
if (string.IsNullOrEmpty(template))
|
||||
|
@ -55,7 +56,7 @@ namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Controller
|
|||
}
|
||||
|
||||
return SimulationApiModel.FromServiceModel(
|
||||
await this.simulationsService.InsertAsync(this.GetServiceModel(simulation), template));
|
||||
await this.simulationsService.InsertAsync(simulation.ToServiceModel(), template));
|
||||
}
|
||||
|
||||
[HttpPut("{id}")]
|
||||
|
@ -63,6 +64,8 @@ namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Controller
|
|||
[FromBody] SimulationApiModel simulation,
|
||||
string id = "")
|
||||
{
|
||||
simulation?.ValidateInputRequest(this.log);
|
||||
|
||||
if (simulation == null)
|
||||
{
|
||||
this.log.Warn("No data or invalid data provided", () => new { simulation });
|
||||
|
@ -70,7 +73,7 @@ namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Controller
|
|||
}
|
||||
|
||||
return SimulationApiModel.FromServiceModel(
|
||||
await this.simulationsService.UpsertAsync(this.GetServiceModel(simulation, id)));
|
||||
await this.simulationsService.UpsertAsync(simulation.ToServiceModel(id)));
|
||||
}
|
||||
|
||||
[HttpPatch("{id}")]
|
||||
|
@ -93,23 +96,5 @@ namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Controller
|
|||
{
|
||||
await this.simulationsService.DeleteAsync(id);
|
||||
}
|
||||
|
||||
private Simulation GetServiceModel(SimulationApiModel simulation, string id = "")
|
||||
{
|
||||
try
|
||||
{
|
||||
return simulation.ToServiceModel(id);
|
||||
}
|
||||
catch (InvalidSimulationSchedulingException e)
|
||||
{
|
||||
this.log.Error("Invalid simulation start/end time", () => new { simulation, e });
|
||||
throw new BadRequestException("Invalid start/end time", e);
|
||||
}
|
||||
catch (InvalidDateFormatException e)
|
||||
{
|
||||
this.log.Error("Invalid date format", () => new { simulation, e });
|
||||
throw new BadRequestException("Invalid date format", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,25 +0,0 @@
|
|||
// Copyright (c) Microsoft. All rights reserved.
|
||||
|
||||
using System;
|
||||
|
||||
namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Exceptions
|
||||
{
|
||||
public class InvalidSimulationSchedulingException : Exception
|
||||
{
|
||||
/// <summary>
|
||||
/// This exception is thrown by a controller when a client is trying to set
|
||||
/// a simulation start and end time using and invalid period, e.g. start > end.
|
||||
/// </summary>
|
||||
public InvalidSimulationSchedulingException() : base()
|
||||
{
|
||||
}
|
||||
|
||||
public InvalidSimulationSchedulingException(string message) : base(message)
|
||||
{
|
||||
}
|
||||
|
||||
public InvalidSimulationSchedulingException(string message, Exception innerException) : base(message, innerException)
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
|
@ -3,6 +3,7 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.Services.Diagnostics;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.Services.Models;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Exceptions;
|
||||
using Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Models.Helpers;
|
||||
|
@ -81,12 +82,6 @@ namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Models.Sim
|
|||
DeviceModels = this.DeviceModels?.Select(x => x.ToServiceModel()).ToList()
|
||||
};
|
||||
|
||||
if (result.StartTime.HasValue && result.EndTime.HasValue
|
||||
&& result.StartTime.Value.Ticks >= result.EndTime.Value.Ticks)
|
||||
{
|
||||
throw new InvalidSimulationSchedulingException("The simulation End Time must be after the Start Time");
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
@ -122,5 +117,54 @@ namespace Microsoft.Azure.IoTSolutions.DeviceSimulation.WebService.v1.Models.Sim
|
|||
|
||||
return result;
|
||||
}
|
||||
|
||||
public void ValidateInputRequest(ILogger log)
|
||||
{
|
||||
const string NO_DEVICE_MODEL = "The simulation doesn't contain any device model";
|
||||
const string ZERO_DEVICES = "The simulation has zero devices";
|
||||
const string END_TIME_BEFORE_START_TIME = "The simulation End Time must be after the Start Time";
|
||||
const string INVALID_DATE = "Invalid date format";
|
||||
const string CANNOT_RUN_IN_THE_PAST = "The simulation end date is in the past";
|
||||
|
||||
// A simulation must contain at least one device model
|
||||
if (this.DeviceModels.Count < 1)
|
||||
{
|
||||
log.Error(NO_DEVICE_MODEL, () => new { simulation = this });
|
||||
throw new BadRequestException(NO_DEVICE_MODEL);
|
||||
}
|
||||
|
||||
// A simulation must use at least one device
|
||||
if (this.DeviceModels.Sum(x => x.Count) < 1)
|
||||
{
|
||||
log.Error(ZERO_DEVICES, () => new { simulation = this });
|
||||
throw new BadRequestException(ZERO_DEVICES);
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
var now = DateTimeOffset.UtcNow;
|
||||
var startTime = DateHelper.ParseDateExpression(this.StartTime, now);
|
||||
var endTime = DateHelper.ParseDateExpression(this.EndTime, now);
|
||||
|
||||
// The start time must be before the end time
|
||||
if (startTime.HasValue && endTime.HasValue && startTime.Value.Ticks >= endTime.Value.Ticks)
|
||||
{
|
||||
log.Error(END_TIME_BEFORE_START_TIME, () => new { simulation = this });
|
||||
throw new BadRequestException(END_TIME_BEFORE_START_TIME);
|
||||
}
|
||||
|
||||
// The end time cannot be in the past
|
||||
if (endTime.HasValue && endTime.Value.Ticks <= now.Ticks)
|
||||
{
|
||||
log.Error(CANNOT_RUN_IN_THE_PAST, () => new { simulation = this });
|
||||
throw new BadRequestException(CANNOT_RUN_IN_THE_PAST);
|
||||
}
|
||||
}
|
||||
catch (InvalidDateFormatException e)
|
||||
{
|
||||
log.Error(INVALID_DATE, () => new { simulation = this });
|
||||
throw new BadRequestException(INVALID_DATE, e);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -33,7 +33,7 @@ install_precommit_hook() {
|
|||
uninstall_precommit_hook() {
|
||||
echo "Removing pre-commit hook..."
|
||||
|
||||
cd $APP_HOME/.git || failed
|
||||
cd $APP_HOME/.git/hooks || failed
|
||||
set +e
|
||||
rm -f ./pre-commit
|
||||
set -e
|
||||
|
|
Загрузка…
Ссылка в новой задаче