public void PostTrackPoint() { var trackPoints = new List<TrackPoint>(); //Create the test TrackPoints with random numbers as properties for (int i = 0; i < 10; i++) { var random = new Random(); var trackPoint = new TrackPoint { Id = Guid.NewGuid(), //CompassDirection = random.Next(0, 359), Latitude = random.Next(-90, 90), Longitude = random.Next(-180, 180), //LastTimeStamp = DateTime.Now.AddSeconds(10 * i), Speed = random.Next(20, 60), }; trackPoints.Add(trackPoint); } var fakeRouteId = Guid.NewGuid(); var request = new HttpRequestMessage(HttpMethod.Get, "http://localhost"); var controller = new TrackPointsController { Request = request }; //var response = controller.PostEmployeeTrackPoint(trackPoints.ToArray()); //Assert.AreEqual(HttpStatusCode.Created, response.StatusCode); //var postedTrackPoint = response.Content.ReadAsync().Result; }
/// <summary> /// Takes a ModelTrackPoint and pushed it to the AzureTables /// </summary> /// <param name="currentBusinessAccount">The current BusinessAccount</param> /// <param name="trackPoint">The Model TrackPoint to be pushed to AzureTables</param> /// <param name="employee">The employee</param> /// <param name="routeId">The Id of the Route that the vehicle or employee are currently on</param> private void PushTrackPointToAzure(Core.Models.CoreEntities.BusinessAccount currentBusinessAccount, TrackPoint trackPoint, Core.Models.CoreEntities.Employee employee, Guid routeId) { //Get the storage account information from Azure var storageAccount = CloudStorageAccount.Parse(AzureServerHelpers.StorageConnectionString); //Create the Service Context for the TrackPointsHistory Tables var serviceContext = new TrackPointsHistoryContext(storageAccount.TableEndpoint.ToString(), storageAccount.Credentials); var tableName = CheckCreateTrackPointTable(storageAccount, currentBusinessAccount); //Create the object to be stored in the Azure table var newTrackPoint = new TrackPointsHistoryTableDataModel(Guid.NewGuid().ToString(), Guid.NewGuid().ToString()) { EmployeeId = employee.Id, VehicleId = new Guid(), RouteId = routeId, Latitude = (double?)trackPoint.Latitude, Longitude = (double?)trackPoint.Longitude, CollectedTimeStamp = trackPoint.CollectedTimeStamp, Accuracy = trackPoint.Accuracy }; //Push to Azure Table serviceContext.AddObject(tableName, newTrackPoint); //Saves the Tables serviceContext.SaveChangesWithRetries(); }
public static TrackPoint ConvertToModel(TrackPointsHistoryTableDataModel modelTrackPoint) { var trackPointId = modelTrackPoint.EmployeeId ?? modelTrackPoint.VehicleId; if (trackPointId == null) return null; var trackPoint = new TrackPoint { Heading = null, Id = (Guid)trackPointId, CollectedTimeStamp = modelTrackPoint.CollectedTimeStamp, Latitude = (decimal?)modelTrackPoint.Latitude, Longitude = (decimal?)modelTrackPoint.Longitude, Speed = null, Source = null, RouteId = modelTrackPoint.RouteId, Accuracy = modelTrackPoint.Accuracy }; return trackPoint; }
/// <summary> /// Stores employee trackpoints. /// Used by the mobile phone application. /// NOTE: TrackPoints CollectedTimeStamp should be in UTC. /// </summary> /// <param name="roleId">Current roleId </param> /// <param name="trackPoints">The list of TrackPoints being passed from an Employee's device</param> /// <returns>An Http response to the device signaling that the TrackPoint was successfully created</returns> public void Post(Guid roleId, TrackPoint[] trackPoints) { if (!trackPoints.Any() || !trackPoints.First().RouteId.HasValue) throw Request.BadRequest(); var routeId = trackPoints.First().RouteId.Value; var currentUserAccount = CoreEntitiesContainer.CurrentUserAccount(); var currentBusinessAccount = CoreEntitiesContainer.Owner(roleId, new[] { RoleType.Administrator, RoleType.Regular, RoleType.Mobile }).FirstOrDefault(); //Return an Unauthorized Status Code if //a) there is no UserAccount //b) the user does not have access to the route (currentBusinessAccount == null) if (currentUserAccount == null || currentBusinessAccount == null) throw Request.NotAuthorized(); var employee = CoreEntitiesContainer.Employees.FirstOrDefault(e => e.LinkedUserAccount.Id == currentUserAccount.Id && e.EmployerId == currentBusinessAccount.Id); if (employee == null) throw Request.NotFound("Employee"); //order the new track points by their TimeStamps //remove inaccurate trackpoints var orderedModelTrackPoints = trackPoints.Where(tp => tp.Accuracy < 50).OrderBy(tp => tp.CollectedTimeStamp).ToArray(); var latestTrackPoint = orderedModelTrackPoints.LastOrDefault(); //if there was a previous point today, check the latest point is not erroneous if (employee.LastTimeStamp.HasValue && DateTime.UtcNow.Subtract(employee.LastTimeStamp.Value) < TimeSpan.FromDays(1)) { var previous = new GeoLocation(employee.LastLatitude.Value, employee.LastLongitude.Value); latestTrackPoint = orderedModelTrackPoints.LastOrDefault(t => !Erroneous(t, previous, t.CollectedTimeStamp.Subtract(employee.LastTimeStamp.Value))); //set the heading based on the previous point if (latestTrackPoint != null) latestTrackPoint.Heading = (int)GeoLocationTools.Bearing(previous, latestTrackPoint); } if (latestTrackPoint != null) { //Save the latest (most current) TrackPoint to the database employee.LastCompassDirection = latestTrackPoint.Heading; employee.LastLatitude = (double?)latestTrackPoint.Latitude; employee.LastLongitude = (double?)latestTrackPoint.Longitude; employee.LastSource = latestTrackPoint.Source; employee.LastSpeed = (double?)latestTrackPoint.Speed; employee.LastTimeStamp = latestTrackPoint.CollectedTimeStamp; employee.LastAccuracy = latestTrackPoint.Accuracy; } //Push TrackPoints to Azure as long as either //the LastPushToAzureTimeStamp is null //the LastPushToAzureTimeStamp difference from the TrackPoint is > TimeBetweenPushesToAzure var lastPushToAzureTimeStamp = employee.LastPushToAzureTimeStamp; //send the TrackPoints to azure, that are seperated by TimeBetweenPushesToAzure (in seconds) foreach (var trackPoint in orderedModelTrackPoints) { if (lastPushToAzureTimeStamp.HasValue && (trackPoint.CollectedTimeStamp - lastPushToAzureTimeStamp) < TimeSpan.FromSeconds(UpdateConstants.SecondsBetweenHistoricalTrackPoints)) continue; if (trackPoint.Id == Guid.Empty) trackPoint.Id = Guid.NewGuid(); PushTrackPointToAzure(currentBusinessAccount, trackPoint, employee, routeId); lastPushToAzureTimeStamp = trackPoint.CollectedTimeStamp; } employee.LastPushToAzureTimeStamp = lastPushToAzureTimeStamp; //Save all the changes that have been made in the Database SaveWithRetry(); }