first commit -push
This commit is contained in:
130
RobotNet.MapManager/Controllers/ActionsController.cs
Normal file
130
RobotNet.MapManager/Controllers/ActionsController.cs
Normal file
@@ -0,0 +1,130 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.Shares;
|
||||
using System.Text.Json;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class ActionsController(MapEditorDbContext MapDb, LoggerController<ActionsController> Logger) : ControllerBase
|
||||
{
|
||||
[HttpPost]
|
||||
public async Task<MessageResult<ActionDto>> CreateAction([FromBody] ActionCreateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(model.MapId);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {model.MapId}");
|
||||
|
||||
if (MapDb.Actions.Any(action => action.Name == model.Name && action.MapId == model.MapId)) return new(false, $"Tên Action {model.Name} đã tồn tại");
|
||||
|
||||
var entity = await MapDb.Actions.AddAsync(new()
|
||||
{
|
||||
MapId = model.MapId,
|
||||
Name = model.Name,
|
||||
Content = model.Content,
|
||||
});
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = entity.Entity.Id,
|
||||
MapId = entity.Entity.MapId,
|
||||
Name = entity.Entity.Name,
|
||||
Content = entity.Entity.Content,
|
||||
}
|
||||
};
|
||||
}
|
||||
catch(Exception ex)
|
||||
{
|
||||
Logger.Warning($"CreateAction: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"CreateAction: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("{id}")]
|
||||
public async Task<IEnumerable<ActionDto>> GetActions(Guid id)
|
||||
{
|
||||
return await MapDb.Actions.Where(action => action.MapId == id).Select(action => new ActionDto()
|
||||
{
|
||||
Id = action.Id,
|
||||
MapId = action.MapId,
|
||||
Name = action.Name,
|
||||
Content = action.Content,
|
||||
}).ToListAsync();
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
public async Task<MessageResult> UpdateAction([FromBody] ActionDto model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var action = await MapDb.Actions.FindAsync(model.Id);
|
||||
if (action is not null)
|
||||
{
|
||||
action.Name = model.Name;
|
||||
action.Content = model.Content;
|
||||
MapDb.Actions.Update(action);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true);
|
||||
}
|
||||
return new(false, $"Hệ thống không tìm thấy Action {model.Name} này");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"UpdateAction: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"UpdateAction: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpDelete]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult> DeleteAction(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var action = await MapDb.Actions.FindAsync(id);
|
||||
if (action is not null)
|
||||
{
|
||||
foreach (var node in MapDb.Nodes)
|
||||
{
|
||||
var actionIds = JsonSerializer.Deserialize<Guid[]>(node.Actions);
|
||||
if (actionIds is not null && actionIds.Any(a => a == action.Id))
|
||||
{
|
||||
var acitonIdsAfter = actionIds.ToList();
|
||||
acitonIdsAfter.Remove(action.Id);
|
||||
node.Actions = JsonSerializer.Serialize(acitonIdsAfter.Count > 0 ? acitonIdsAfter : []);
|
||||
}
|
||||
}
|
||||
foreach (var edge in MapDb.Edges)
|
||||
{
|
||||
var actionIds = JsonSerializer.Deserialize<Guid[]>(edge.Actions);
|
||||
if (actionIds is not null && actionIds.Any(a => a == action.Id))
|
||||
{
|
||||
var acitonIdsAfter = actionIds.ToList();
|
||||
acitonIdsAfter.Remove(action.Id);
|
||||
edge.Actions = JsonSerializer.Serialize(acitonIdsAfter.Count > 0 ? acitonIdsAfter : []);
|
||||
}
|
||||
}
|
||||
MapDb.Actions.Remove(action);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true) ;
|
||||
}
|
||||
return new(false, $"Hệ thống không tìm thấy Action {id} này");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"DeleteAction {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"DeleteAction {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
}
|
||||
269
RobotNet.MapManager/Controllers/EdgesController.cs
Normal file
269
RobotNet.MapManager/Controllers/EdgesController.cs
Normal file
@@ -0,0 +1,269 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.MapShares.Enums;
|
||||
using RobotNet.Shares;
|
||||
using System.Text.Json;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class EdgesController(MapEditorDbContext MapDb, LoggerController<EdgesController> Logger) : ControllerBase
|
||||
{
|
||||
[HttpPost]
|
||||
[Route("")]
|
||||
public async Task<MessageResult<EdgeCreateDto>> CreateEdge([FromBody] EdgeCreateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(model.MapId);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {model.MapId}");
|
||||
|
||||
if (Math.Sqrt(Math.Pow(model.X1 - model.X2, 2) + Math.Pow(model.Y1 - model.Y2, 2)) < map.EdgeMinLengthDefault) return new(false, "Độ dài edge quá nhỏ");
|
||||
|
||||
var nodes = await MapDb.Nodes.Where(n => n.MapId == model.MapId).ToListAsync();
|
||||
var edges = await MapDb.Edges.Where(e => e.MapId == model.MapId && e.TrajectoryDegree == TrajectoryDegree.One).ToListAsync();
|
||||
|
||||
var closesStartNode = MapEditorHelper.GetClosesNode(model.X1, model.Y1, [.. nodes.Select(node => new NodeDto()
|
||||
{
|
||||
MapId = node.MapId,
|
||||
X = node.X,
|
||||
Y = node.Y,
|
||||
Theta = node.Theta,
|
||||
Actions = node.Actions,
|
||||
Id = node.Id,
|
||||
Name = node.Name,
|
||||
AllowedDeviationTheta = node.AllowedDeviationTheta,
|
||||
AllowedDeviationXy = node.AllowedDeviationXy
|
||||
})]);
|
||||
|
||||
var closesEndNode = MapEditorHelper.GetClosesNode(model.X2, model.Y2, [.. nodes.Select(node => new NodeDto()
|
||||
{
|
||||
MapId = node.MapId,
|
||||
X = node.X,
|
||||
Y = node.Y,
|
||||
Theta = node.Theta,
|
||||
Actions = node.Actions,
|
||||
Id = node.Id,
|
||||
Name = node.Name,
|
||||
AllowedDeviationTheta = node.AllowedDeviationTheta,
|
||||
AllowedDeviationXy = node.AllowedDeviationXy
|
||||
})]);
|
||||
|
||||
Node? startNode = await MapDb.Nodes.FindAsync(closesStartNode?.Id);
|
||||
Node? endNode = await MapDb.Nodes.FindAsync(closesEndNode?.Id);
|
||||
List<Guid> RemoveEdge = [];
|
||||
List<EdgeDto> AddEdgeDto = [];
|
||||
|
||||
if (startNode is null)
|
||||
{
|
||||
startNode = ServerHelper.CreateNode(map, model.X1, model.Y1);
|
||||
await MapDb.Nodes.AddAsync(startNode);
|
||||
var closesEdge = ServerHelper.GetClosesEdge(model.X1, model.Y1, nodes, edges, 0.1);
|
||||
if (closesEdge is not null)
|
||||
{
|
||||
var closesEdgeStartNode = await MapDb.Nodes.FirstOrDefaultAsync(n => n.Id == closesEdge.StartNodeId);
|
||||
var closesEdgeEndNode = await MapDb.Nodes.FirstOrDefaultAsync(n => n.Id == closesEdge.EndNodeId);
|
||||
if (closesEdgeStartNode is not null && closesEdgeEndNode is not null)
|
||||
{
|
||||
var startEdge = ServerHelper.CreateEdge(map, closesEdgeStartNode.Id, startNode.Id, TrajectoryDegree.One);
|
||||
var endEdge = ServerHelper.CreateEdge(map, startNode.Id, closesEdgeEndNode.Id, TrajectoryDegree.One);
|
||||
await MapDb.Edges.AddAsync(startEdge);
|
||||
await MapDb.Edges.AddAsync(endEdge);
|
||||
|
||||
MapDb.Edges.Remove(closesEdge);
|
||||
edges.Remove(closesEdge);
|
||||
RemoveEdge.Add(closesEdge.Id);
|
||||
|
||||
edges.Add(startEdge);
|
||||
edges.Add(endEdge);
|
||||
nodes.Add(startNode);
|
||||
AddEdgeDto.Add(ServerHelper.CreateEdgeDto(startEdge, closesEdgeStartNode, startNode));
|
||||
AddEdgeDto.Add(ServerHelper.CreateEdgeDto(endEdge, startNode, closesEdgeEndNode));
|
||||
}
|
||||
}
|
||||
}
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
if (endNode is null)
|
||||
{
|
||||
endNode = ServerHelper.CreateNode(map, model.X2, model.Y2);
|
||||
await MapDb.Nodes.AddAsync(endNode);
|
||||
|
||||
var closesEdge = ServerHelper.GetClosesEdge(model.X2, model.Y2, nodes, edges, 0.1);
|
||||
if (closesEdge is not null)
|
||||
{
|
||||
var closesEdgeStartNode = await MapDb.Nodes.FirstOrDefaultAsync(n => n.Id == closesEdge.StartNodeId);
|
||||
var closesEdgeEndNode = await MapDb.Nodes.FirstOrDefaultAsync(n => n.Id == closesEdge.EndNodeId);
|
||||
if (closesEdgeStartNode is not null && closesEdgeEndNode is not null)
|
||||
{
|
||||
var startEdge = ServerHelper.CreateEdge(map, closesEdgeStartNode.Id, endNode.Id, TrajectoryDegree.One);
|
||||
var endEdge = ServerHelper.CreateEdge(map, endNode.Id, closesEdgeEndNode.Id, TrajectoryDegree.One);
|
||||
await MapDb.Edges.AddAsync(startEdge);
|
||||
await MapDb.Edges.AddAsync(endEdge);
|
||||
|
||||
MapDb.Edges.Remove(closesEdge);
|
||||
RemoveEdge.Add(closesEdge.Id);
|
||||
AddEdgeDto.Add(ServerHelper.CreateEdgeDto(startEdge, closesEdgeStartNode, endNode));
|
||||
AddEdgeDto.Add(ServerHelper.CreateEdgeDto(endEdge, endNode, closesEdgeEndNode));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var edge = ServerHelper.CreateEdge(map, startNode.Id, endNode.Id, model.TrajectoryDegree, model.ControlPoint1X, model.ControlPoint1Y, model.ControlPoint2X, model.ControlPoint2Y);
|
||||
await MapDb.Edges.AddAsync(edge);
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
AddEdgeDto.Add(ServerHelper.CreateEdgeDto(edge, startNode, endNode));
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new EdgeCreateDto()
|
||||
{
|
||||
EdgesDto = AddEdgeDto,
|
||||
RemoveEdge = RemoveEdge,
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"CreateEdge: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"CreateEdge: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpDelete]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult> DeleteEdge(Guid id)
|
||||
{
|
||||
using var transaction = await MapDb.Database.BeginTransactionAsync();
|
||||
try
|
||||
{
|
||||
var edge = await MapDb.Edges.FindAsync(id);
|
||||
if (edge == null) return new(false, $"Không tồn tại edge id = {id}");
|
||||
|
||||
MapDb.Edges.Remove(edge);
|
||||
|
||||
if (!MapDb.Edges.Any(e => (e.StartNodeId == edge.StartNodeId || e.EndNodeId == edge.StartNodeId) && e.Id != edge.Id))
|
||||
{
|
||||
var node = await MapDb.Nodes.FindAsync(edge.StartNodeId);
|
||||
if (node != null)
|
||||
{
|
||||
var element = await MapDb.Elements.FirstOrDefaultAsync(e => e.NodeId == node.Id);
|
||||
if (element is not null) MapDb.Elements.Remove(element);
|
||||
MapDb.Nodes.Remove(node);
|
||||
}
|
||||
}
|
||||
|
||||
if (!MapDb.Edges.Any(e => (e.StartNodeId == edge.EndNodeId || e.EndNodeId == edge.EndNodeId) && e.Id != edge.Id))
|
||||
{
|
||||
var node = await MapDb.Nodes.FindAsync(edge.EndNodeId);
|
||||
if (node != null)
|
||||
{
|
||||
var element = await MapDb.Elements.FirstOrDefaultAsync(e => e.NodeId == node.Id);
|
||||
if (element is not null) MapDb.Elements.Remove(element);
|
||||
MapDb.Nodes.Remove(node);
|
||||
}
|
||||
}
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
await transaction.CommitAsync();
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
await transaction.RollbackAsync();
|
||||
Logger.Warning($"DeleteEdge {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"DeleteEdge {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpDelete]
|
||||
[Route("")]
|
||||
public async Task<MessageResult> DeleteEdges([FromBody] IEnumerable<Guid> DeleteEdgesId)
|
||||
{
|
||||
try
|
||||
{
|
||||
List<Edge> deleteEdges = [];
|
||||
List<Node> deleteNodes = [];
|
||||
foreach (var edgeId in DeleteEdgesId)
|
||||
{
|
||||
var edge = await MapDb.Edges.FindAsync(edgeId);
|
||||
if (edge == null) continue;
|
||||
|
||||
MapDb.Edges.Remove(edge);
|
||||
|
||||
if (!MapDb.Edges.Any(e => (e.StartNodeId == edge.StartNodeId || e.EndNodeId == edge.StartNodeId) && e.Id != edge.Id))
|
||||
{
|
||||
var node = await MapDb.Nodes.FindAsync(edge.StartNodeId);
|
||||
if (node != null)
|
||||
{
|
||||
var element = await MapDb.Elements.FirstOrDefaultAsync(e => e.NodeId == node.Id);
|
||||
if (element is not null) MapDb.Elements.Remove(element);
|
||||
MapDb.Nodes.Remove(node);
|
||||
}
|
||||
}
|
||||
|
||||
if (!MapDb.Edges.Any(e => (e.StartNodeId == edge.EndNodeId || e.EndNodeId == edge.EndNodeId) && e.Id != edge.Id))
|
||||
{
|
||||
var node = await MapDb.Nodes.FindAsync(edge.EndNodeId);
|
||||
if (node != null)
|
||||
{
|
||||
var element = await MapDb.Elements.FirstOrDefaultAsync(e => e.NodeId == node.Id);
|
||||
if (element is not null) MapDb.Elements.Remove(element);
|
||||
MapDb.Nodes.Remove(node);
|
||||
}
|
||||
}
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
}
|
||||
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"DeleteEdges: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"DeleteEdges: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("")]
|
||||
public async Task<MessageResult> UpdateEdge([FromBody] EdgeUpdateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var edge = await MapDb.Edges.FindAsync(model.Id);
|
||||
if (edge == null) return new(false, $"Không tồn tại edge id = {model.Id}");
|
||||
|
||||
edge.MaxSpeed = model.MaxSpeed;
|
||||
edge.MaxHeight = model.MaxHeight;
|
||||
edge.MinHeight = model.MinHeight;
|
||||
edge.ControlPoint1X = model.ControlPoint1X;
|
||||
edge.ControlPoint1Y = model.ControlPoint1Y;
|
||||
edge.ControlPoint2X = model.ControlPoint2X;
|
||||
edge.ControlPoint2Y = model.ControlPoint2Y;
|
||||
edge.DirectionAllowed = model.DirectionAllowed;
|
||||
edge.RotationAllowed = model.RotationAllowed;
|
||||
edge.MaxRotationSpeed = model.MaxRotationSpeed;
|
||||
edge.Actions = JsonSerializer.Serialize(model.Actions ?? []);
|
||||
edge.AllowedDeviationXy = model.AllowedDeviationXy;
|
||||
edge.AllowedDeviationTheta = model.AllowedDeviationTheta;
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"UpdateEdge: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"UpdateEdge: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
}
|
||||
258
RobotNet.MapManager/Controllers/ElementModelsController.cs
Normal file
258
RobotNet.MapManager/Controllers/ElementModelsController.cs
Normal file
@@ -0,0 +1,258 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.Shares;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class ElementModelsController(MapEditorDbContext MapDb, MapEditorStorageRepository MapStorage, LoggerController<ElementModelsController> Logger) : ControllerBase
|
||||
{
|
||||
[HttpGet]
|
||||
[Route("map/{mapId}")]
|
||||
public async Task<MessageResult<IEnumerable<ElementModelDto>>> Gets(Guid mapId)
|
||||
{
|
||||
try
|
||||
{
|
||||
return new(true)
|
||||
{
|
||||
Data = await (from elm in MapDb.ElementModels
|
||||
where !string.IsNullOrEmpty(elm.Name) && elm.MapId == mapId
|
||||
select new ElementModelDto()
|
||||
{
|
||||
Id = elm.Id,
|
||||
MapId = elm.MapId,
|
||||
Name = elm.Name,
|
||||
Height = elm.Height,
|
||||
Width = elm.Width,
|
||||
Image1Height = elm.Image1Height,
|
||||
Image2Height = elm.Image2Height,
|
||||
Image1Width = elm.Image1Width,
|
||||
Image2Width = elm.Image2Width,
|
||||
Content = elm.Content,
|
||||
}).ToListAsync()
|
||||
};
|
||||
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Gets: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Gets: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult<ElementModelDto>> Get(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var elmodel = await MapDb.ElementModels.FindAsync(id);
|
||||
if (elmodel is null) return new(false, $"Element Model {id} không tồn tại");
|
||||
return new(true)
|
||||
{
|
||||
Data = new ElementModelDto()
|
||||
{
|
||||
Id = elmodel.Id,
|
||||
Name = elmodel.Name,
|
||||
MapId = elmodel.MapId,
|
||||
Height = elmodel.Height,
|
||||
Width = elmodel.Width,
|
||||
Content = elmodel.Content,
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Get {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Get {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
public async Task<MessageResult<ElementModelDto>> CreateElementModel([FromForm] ElementModelCreateModel model, [FromForm(Name = "imageOpen")] IFormFile imageOpen, [FromForm(Name = "imageClose")] IFormFile imageClose)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (model == null || imageOpen == null || imageClose == null) return new(false, "Dữ liệu đầu vào không hợp lệ");
|
||||
var map = await MapDb.Maps.FindAsync(model.MapId);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {model.MapId}");
|
||||
if (MapDb.ElementModels.Any(elm => elm.Name == model.Name && elm.MapId == model.MapId)) return new(false, $"Tên Model {model.Name} đã tồn tại");
|
||||
|
||||
var image1 = SixLabors.ImageSharp.Image.Load(imageOpen.OpenReadStream());
|
||||
var image2 = SixLabors.ImageSharp.Image.Load(imageClose.OpenReadStream());
|
||||
var entity = MapDb.ElementModels.Add(new()
|
||||
{
|
||||
Name = model.Name,
|
||||
MapId = model.MapId,
|
||||
Width = model.Width,
|
||||
Height = model.Height,
|
||||
Image1Height = (ushort)image1.Height,
|
||||
Image1Width = (ushort)image1.Width,
|
||||
Image2Height = (ushort)image2.Height,
|
||||
Image2Width = (ushort)image2.Width,
|
||||
Content = "",
|
||||
});
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
var (isSuccess, message) = await MapStorage.UploadAsync("ElementOpenModels", $"{entity.Entity.Id}", imageOpen.OpenReadStream(), imageOpen.Length, imageOpen.ContentType, CancellationToken.None);
|
||||
if (!isSuccess)
|
||||
{
|
||||
MapDb.ElementModels.Remove(entity.Entity);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(false, message);
|
||||
}
|
||||
(isSuccess, message) = await MapStorage.UploadAsync("ElementCloseModels", $"{entity.Entity.Id}", imageClose.OpenReadStream(), imageClose.Length, imageClose.ContentType, CancellationToken.None);
|
||||
if (!isSuccess)
|
||||
{
|
||||
MapDb.ElementModels.Remove(entity.Entity);
|
||||
await MapDb.SaveChangesAsync();
|
||||
await MapStorage.DeleteAsync("ElementOpenModels", $"{entity.Entity.Id}", CancellationToken.None);
|
||||
return new(false, message);
|
||||
}
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = entity.Entity.Id,
|
||||
Name = entity.Entity.Name,
|
||||
MapId = entity.Entity.MapId,
|
||||
Width = entity.Entity.Width,
|
||||
Height = entity.Entity.Height,
|
||||
Image1Height = entity.Entity.Image1Height,
|
||||
Image1Width = entity.Entity.Image1Width,
|
||||
Image2Height = entity.Entity.Image2Height,
|
||||
Image2Width = entity.Entity.Image2Width,
|
||||
Content = entity.Entity.Content
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"CreateElementModel: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"CreateElementModel: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
public async Task<MessageResult<ElementModelDto>> Update([FromBody] ElementModelUpdateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var elModel = await MapDb.ElementModels.FindAsync(model.Id);
|
||||
if (elModel is null) return new(false, $"Model {model.Id} không tồn tại");
|
||||
if (MapDb.ElementModels.Any(elm => elm.Name == model.Name && elm.MapId == elModel.MapId && model.Id != elModel.Id)) return new(false, $"Tên Model {model.Name} đã tồn tại");
|
||||
|
||||
elModel.Name = model.Name;
|
||||
elModel.Width = model.Width;
|
||||
elModel.Height = model.Height;
|
||||
elModel.Content = model.Content;
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = elModel.Id,
|
||||
Name = elModel.Name,
|
||||
MapId = elModel.MapId,
|
||||
Width = elModel.Width,
|
||||
Height = elModel.Height,
|
||||
Image1Height = elModel.Image1Height,
|
||||
Image1Width = elModel.Image1Width,
|
||||
Image2Height = elModel.Image2Height,
|
||||
Image2Width = elModel.Image2Width,
|
||||
Content = elModel.Content
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpDelete]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult> Delete(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var elModel = await MapDb.ElementModels.FindAsync(id);
|
||||
if (elModel is null) return new(false, $"Model {id} không tồn tại");
|
||||
|
||||
await MapStorage.DeleteAsync("ElementOpenModels", id.ToString(), CancellationToken.None);
|
||||
await MapStorage.DeleteAsync("ElementCloseModels", id.ToString(), CancellationToken.None);
|
||||
MapDb.Elements.RemoveRange(MapDb.Elements.Where(e => e.ModelId == id));
|
||||
MapDb.ElementModels.Remove(elModel);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Delete {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Delete {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("openimage/{id}")]
|
||||
public async Task<MessageResult> UpdateOpenImage(Guid id, [FromForm(Name = "image")] IFormFile image)
|
||||
{
|
||||
try
|
||||
{
|
||||
var elModel = await MapDb.ElementModels.FindAsync(id);
|
||||
if (elModel is null) return new(false, $"Model {id} không tồn tại");
|
||||
|
||||
var imageStream = image.OpenReadStream();
|
||||
var (isSuccess, message) = await MapStorage.UploadAsync("ElementOpenModels", $"{elModel.Id}", imageStream, image.Length, image.ContentType, CancellationToken.None);
|
||||
if (!isSuccess) return new(false, message);
|
||||
|
||||
var imageUpdate = SixLabors.ImageSharp.Image.Load(image.OpenReadStream());
|
||||
elModel.Image1Width = (ushort)imageUpdate.Width;
|
||||
elModel.Image1Height = (ushort)imageUpdate.Height;
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"UpdateOpenImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"UpdateOpenImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("closeimage/{id}")]
|
||||
public async Task<MessageResult> UpdateCloseImage(Guid id, [FromForm(Name = "image")] IFormFile image)
|
||||
{
|
||||
try
|
||||
{
|
||||
var elModel = await MapDb.ElementModels.FindAsync(id);
|
||||
if (elModel is null) return new(false, $"Model {id} không tồn tại");
|
||||
|
||||
var imageStream = image.OpenReadStream();
|
||||
var (isSuccess, message) = await MapStorage.UploadAsync("ElementCloseModels", $"{elModel.Id}", imageStream, image.Length, image.ContentType, CancellationToken.None);
|
||||
if (!isSuccess) return new(false, message);
|
||||
|
||||
var imageUpdate = SixLabors.ImageSharp.Image.Load(image.OpenReadStream());
|
||||
elModel.Image2Width = (ushort)imageUpdate.Width;
|
||||
elModel.Image2Height = (ushort)imageUpdate.Height;
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"UpdateCloseImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"UpdateCloseImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
}
|
||||
211
RobotNet.MapManager/Controllers/ElementsController.cs
Normal file
211
RobotNet.MapManager/Controllers/ElementsController.cs
Normal file
@@ -0,0 +1,211 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.Shares;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class ElementsController(MapEditorDbContext MapDb, LoggerController<ElementsController> Logger) : ControllerBase
|
||||
{
|
||||
|
||||
[HttpGet]
|
||||
public async Task<MessageResult<ElementDto>> GetElement([FromQuery] string mapName, [FromQuery] string elementName)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Name == mapName);
|
||||
if (map is null) return new(false, $"Không tồn tại map tên = {mapName}");
|
||||
|
||||
var el = await MapDb.Elements.FirstOrDefaultAsync(e => e.MapId == map.Id && e.Name == elementName);
|
||||
if (el is null) return new(false, $"Không tồn tại element name = {elementName}");
|
||||
|
||||
var elNode = await MapDb.Nodes.FindAsync(el.NodeId);
|
||||
if (elNode is null) return new(false, $"Không tồn tại node id = {el.NodeId}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = el.Id,
|
||||
Name = el.Name,
|
||||
MapId = el.MapId,
|
||||
IsOpen = el.IsOpen,
|
||||
NodeId = el.NodeId,
|
||||
OffsetX = el.OffsetX,
|
||||
OffsetY = el.OffsetY,
|
||||
ModelId = el.ModelId,
|
||||
Content = el.Content,
|
||||
NodeName = elNode.Name,
|
||||
X = elNode.X,
|
||||
Y = elNode.Y,
|
||||
Theta = elNode.Theta
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetElement: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"GetElement: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("{modelId}")]
|
||||
public async Task<MessageResult<IEnumerable<ElementDto>>> GetElementsByModelId([FromRoute] Guid modelId)
|
||||
{
|
||||
try
|
||||
{
|
||||
var elModel = await MapDb.ElementModels.FindAsync(modelId);
|
||||
if (elModel is null) return new(false, $"Không tồn tại model id = {modelId}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = await (from el in MapDb.Elements
|
||||
where el.ModelId == modelId
|
||||
select new ElementDto()
|
||||
{
|
||||
Id = el.Id,
|
||||
MapId = el.MapId,
|
||||
Name = el.Name,
|
||||
ModelId = el.ModelId,
|
||||
ModelName = elModel.Name,
|
||||
IsOpen = el.IsOpen,
|
||||
NodeId = el.NodeId,
|
||||
OffsetX = el.OffsetX,
|
||||
OffsetY = el.OffsetY,
|
||||
Content = el.Content,
|
||||
}).ToListAsync()
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetElementsByModelId: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"GetElementsByModelId: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
public async Task<MessageResult<ElementDto>> Create([FromBody] ElementCreateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (model == null || string.IsNullOrEmpty(model.Name)) return new(false, "Dữ liệu không hợp lệ");
|
||||
var map = await MapDb.Maps.FindAsync(model.MapId);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {model.MapId}");
|
||||
|
||||
var node = await MapDb.Nodes.FindAsync(model.NodeId);
|
||||
if (node == null) return new(false, $"Không tồn tại node id = {model.NodeId}");
|
||||
|
||||
var elModel = await MapDb.ElementModels.FindAsync(model.ModelId);
|
||||
if (elModel is null) return new(false, $"Không tồn tại element model id = {model.ModelId}");
|
||||
|
||||
if (MapDb.Elements.Any(el => el.Name == model.Name && el.MapId == model.MapId)) return new(false, $"Tên Element đã tồn tại");
|
||||
|
||||
if (MapDb.Elements.Any(el => el.NodeId == model.NodeId)) return new(false, $"Node này đã có Element");
|
||||
|
||||
var entity = await MapDb.Elements.AddAsync(new()
|
||||
{
|
||||
Name = model.Name,
|
||||
MapId = model.MapId,
|
||||
NodeId = model.NodeId,
|
||||
ModelId = model.ModelId,
|
||||
OffsetX = model.OffsetX,
|
||||
OffsetY = model.OffsetY,
|
||||
Content = elModel.Content,
|
||||
});
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = entity.Entity.Id,
|
||||
MapId = entity.Entity.MapId,
|
||||
NodeId = entity.Entity.NodeId,
|
||||
ModelName = elModel.Name,
|
||||
Name = entity.Entity.Name,
|
||||
ModelId = entity.Entity.ModelId,
|
||||
OffsetX = entity.Entity.OffsetX,
|
||||
OffsetY = entity.Entity.OffsetY,
|
||||
Content = entity.Entity.Content,
|
||||
IsOpen = entity.Entity.IsOpen,
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Create: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Create: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
public async Task<MessageResult<ElementDto>> Update([FromBody] ElementUpdateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var element = await MapDb.Elements.FindAsync(model.Id);
|
||||
if (element == null) return new(false, $"Không tồn tại element id = {model.Id}");
|
||||
|
||||
var map = await MapDb.Maps.FindAsync(element.MapId);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {element.MapId}");
|
||||
|
||||
if (MapDb.Elements.Any(el => el.Name == model.Name && el.MapId == element.MapId && el.Id != model.Id)) return new(false, $"Tên Element đã tồn tại");
|
||||
|
||||
element.Name = model.Name;
|
||||
element.OffsetX = model.OffsetX;
|
||||
element.OffsetY = model.OffsetY;
|
||||
element.Content = model.Content;
|
||||
element.IsOpen = model.IsOpen;
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = element.Id,
|
||||
MapId = element.MapId,
|
||||
NodeId = element.NodeId,
|
||||
Name = element.Name,
|
||||
ModelId = element.ModelId,
|
||||
OffsetX = element.OffsetX,
|
||||
OffsetY = element.OffsetY,
|
||||
Content = element.Content,
|
||||
IsOpen = element.IsOpen,
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpDelete]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult> Delete(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var element = await MapDb.Elements.FindAsync(id);
|
||||
if (element == null) return new(false, $"Không tồn tại element id = {id}");
|
||||
|
||||
MapDb.Elements.Remove(element);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Delete {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Delete {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
}
|
||||
66
RobotNet.MapManager/Controllers/ImagesController.cs
Normal file
66
RobotNet.MapManager/Controllers/ImagesController.cs
Normal file
@@ -0,0 +1,66 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using RobotNet.MapManager.Services;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[AllowAnonymous]
|
||||
public class ImagesController(MapEditorStorageRepository StorageRepo, IHttpClientFactory HttpClientFactory, LoggerController<ImagesController> Logger) : ControllerBase
|
||||
{
|
||||
[HttpGet]
|
||||
[Route("map/{id}")]
|
||||
public async Task<IActionResult> GetMapImage(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var (usingLocal, url) = StorageRepo.GetUrl("MapImages", $"{id}");
|
||||
if (!usingLocal)
|
||||
{
|
||||
var http = HttpClientFactory.CreateClient();
|
||||
var imageBytes = await http.GetByteArrayAsync(url);
|
||||
if (imageBytes != null && imageBytes.Length > 0) return File(imageBytes, "image/png");
|
||||
else return NotFound("Không thể lấy được ảnh map.");
|
||||
}
|
||||
if (System.IO.File.Exists(url)) return File(System.IO.File.ReadAllBytes(url), "image/png");
|
||||
else return NotFound();
|
||||
}
|
||||
catch(Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetMapImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return NotFound();
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("elementModel/{id}")]
|
||||
public async Task<IActionResult> GetElementModelImage(Guid id, [FromQuery] bool IsOpen)
|
||||
{
|
||||
try
|
||||
{
|
||||
var (usingLocal, url) = StorageRepo.GetUrl(IsOpen ? "ElementOpenModels" : "ElementCloseModels", id.ToString());
|
||||
if (!usingLocal)
|
||||
{
|
||||
var http = HttpClientFactory.CreateClient();
|
||||
var imageBytes = await http.GetByteArrayAsync(url);
|
||||
if (imageBytes != null && imageBytes.Length > 0)
|
||||
{
|
||||
return File(imageBytes, "image/png");
|
||||
}
|
||||
else
|
||||
{
|
||||
return NotFound("Không thể lấy được ảnh element model.");
|
||||
}
|
||||
}
|
||||
if (System.IO.File.Exists(url)) return File(System.IO.File.ReadAllBytes(url), "image/png");
|
||||
else return NotFound();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetElementModelImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return NotFound();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using RobotNet.MapManager.Services;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[AllowAnonymous]
|
||||
public class MapDesignerLoggerController(LoggerController<MapDesignerLoggerController> Logger) : ControllerBase
|
||||
{
|
||||
private readonly string LoggerDirectory = "mapManagerlogs";
|
||||
|
||||
[HttpGet]
|
||||
public async Task<IEnumerable<string>> GetLogs([FromQuery(Name = "date")] DateTime date)
|
||||
{
|
||||
string temp = "";
|
||||
try
|
||||
{
|
||||
string fileName = $"{date:yyyy-MM-dd}.log";
|
||||
string path = Path.Combine(LoggerDirectory, fileName);
|
||||
if (!Path.GetFullPath(path).StartsWith(Path.GetFullPath(LoggerDirectory)))
|
||||
{
|
||||
Logger.Warning($"GetLogs: phát hiện đường dẫn không hợp lệ.");
|
||||
return [];
|
||||
}
|
||||
|
||||
if (!System.IO.File.Exists(path))
|
||||
{
|
||||
Logger.Warning($"GetLogs: không tìm thấy file log của ngày {date.ToShortDateString()} - {path}.");
|
||||
return [];
|
||||
}
|
||||
|
||||
temp = Path.Combine(LoggerDirectory, $"{Guid.NewGuid()}.log");
|
||||
System.IO.File.Copy(path, temp);
|
||||
return await System.IO.File.ReadAllLinesAsync(temp);
|
||||
}
|
||||
catch(Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetLogs: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return [];
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (System.IO.File.Exists(temp)) System.IO.File.Delete(temp);
|
||||
}
|
||||
}
|
||||
}
|
||||
249
RobotNet.MapManager/Controllers/MapExportController.cs
Normal file
249
RobotNet.MapManager/Controllers/MapExportController.cs
Normal file
@@ -0,0 +1,249 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.Shares;
|
||||
using System.Security.Cryptography;
|
||||
using System.Text;
|
||||
using System.Text.Json;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class MapExportController(MapEditorDbContext MapDb, MapEditorStorageRepository StorageRepo, IHttpClientFactory HttpClientFactory, LoggerController<MapExportController> Logger) : ControllerBase
|
||||
{
|
||||
private readonly byte[] Key = Encoding.UTF8.GetBytes("2512199802031998");
|
||||
private readonly byte[] IV = Encoding.UTF8.GetBytes("2512199802031998");
|
||||
|
||||
[HttpGet]
|
||||
[Route("encrypt/{Id}")]
|
||||
public async Task<IActionResult> EncryptMap(Guid Id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Id == Id);
|
||||
if (map is null) return NotFound($"Map {Id} không tồn tại");
|
||||
|
||||
var (usingLocal, url) = StorageRepo.GetUrl("MapImages", $"{Id}");
|
||||
byte[] imageData = await GetImageDataAsync(usingLocal, url);
|
||||
|
||||
var elementModels = MapDb.ElementModels.Where(n => n.MapId == Id);
|
||||
List<ElementModelExportDto> ElementModelExport = [];
|
||||
foreach (var elementModel in elementModels)
|
||||
{
|
||||
var getImageOpen = StorageRepo.GetUrl("ElementOpenModels", elementModel.Id.ToString());
|
||||
byte[] imageElementModelOpenData = await GetImageDataAsync(getImageOpen.usingLocal, getImageOpen.url);
|
||||
|
||||
var getImageClose = StorageRepo.GetUrl("ElementCloseModels", elementModel.Id.ToString());
|
||||
byte[] imageElementModelCloseData = await GetImageDataAsync(getImageClose.usingLocal, getImageClose.url);
|
||||
|
||||
ElementModelExport.Add(new ElementModelExportDto()
|
||||
{
|
||||
Id = elementModel.Id,
|
||||
Height = elementModel.Height,
|
||||
Width = elementModel.Width,
|
||||
Image1Height = elementModel.Image1Height,
|
||||
Image2Height = elementModel.Image2Height,
|
||||
Image1Width = elementModel.Image1Width,
|
||||
Image2Width = elementModel.Image2Width,
|
||||
Name = elementModel.Name,
|
||||
Content = elementModel.Content,
|
||||
ImageOpenData = imageElementModelOpenData,
|
||||
ImageCloseData = imageElementModelCloseData,
|
||||
});
|
||||
}
|
||||
var nodes = MapDb.Nodes.Where(n => n.MapId == Id);
|
||||
var edges = MapDb.Edges.Where(n => n.MapId == Id);
|
||||
var zones = MapDb.Zones.Where(n => n.MapId == Id);
|
||||
var actions = MapDb.Actions.Where(n => n.MapId == Id);
|
||||
var elements = MapDb.Elements.Where(n => n.MapId == Id);
|
||||
|
||||
var mapDto = new MapExportDto()
|
||||
{
|
||||
Id = Id,
|
||||
Name = map.Name,
|
||||
Description = map.Description,
|
||||
Info = new()
|
||||
{
|
||||
OriginX = map.OriginX,
|
||||
OriginY = map.OriginY,
|
||||
Resolution = map.Resolution,
|
||||
ViewX = map.ViewX,
|
||||
ViewY = map.ViewY,
|
||||
ViewWidth = map.ViewWidth,
|
||||
ViewHeight = map.ViewHeight,
|
||||
VDA5050 = map.VDA5050,
|
||||
},
|
||||
Setting = new()
|
||||
{
|
||||
NodeNameAutoGenerate = map.NodeNameAutoGenerate,
|
||||
NodeNameTemplate = map.NodeNameTemplateDefault,
|
||||
NodeAllowedDeviationXy = map.EdgeAllowedDeviationXyDefault,
|
||||
NodeAllowedDeviationTheta = map.EdgeAllowedDeviationThetaDefault,
|
||||
|
||||
EdgeStraightMaxSpeed = map.EdgeStraightMaxSpeedDefault,
|
||||
EdgeCurveMaxSpeed = map.EdgeCurveMaxSpeedDefault,
|
||||
EdgeMaxRotationSpeed = map.EdgeMaxRotationSpeedDefault,
|
||||
EdgeMinLength = map.EdgeMinLengthDefault,
|
||||
EdgeMaxHeight = map.EdgeMaxHeightDefault,
|
||||
EdgeMinHeight = map.EdgeMinHeightDefault,
|
||||
EdgeRotationAllowed = map.EdgeRotationAllowedDefault,
|
||||
EdgeDirectionAllowed = map.EdgeDirectionAllowedDefault,
|
||||
EdgeAllowedDeviationTheta = map.EdgeAllowedDeviationThetaDefault,
|
||||
EdgeAllowedDeviationXy = map.EdgeAllowedDeviationXyDefault,
|
||||
|
||||
ZoneMinSquare = map.ZoneMinSquareDefault,
|
||||
},
|
||||
Data = new()
|
||||
{
|
||||
NodeCount = map.NodeCount,
|
||||
Nodes = [.. nodes.Select(n => new NodeDto()
|
||||
{
|
||||
Id = n.Id,
|
||||
Name = n.Name,
|
||||
X = n.X,
|
||||
Y = n.Y,
|
||||
Theta = n.Theta,
|
||||
AllowedDeviationXy = n.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = n.AllowedDeviationTheta,
|
||||
Actions = n.Actions,
|
||||
})],
|
||||
Edges = [.. edges.Select(e => new EdgeDto()
|
||||
{
|
||||
ControlPoint1X = e.ControlPoint1X,
|
||||
ControlPoint1Y = e.ControlPoint1Y,
|
||||
ControlPoint2X = e.ControlPoint2X,
|
||||
ControlPoint2Y = e.ControlPoint2Y,
|
||||
TrajectoryDegree = e.TrajectoryDegree,
|
||||
EndNodeId = e.EndNodeId,
|
||||
StartNodeId = e.StartNodeId,
|
||||
DirectionAllowed = e.DirectionAllowed,
|
||||
RotationAllowed = e.RotationAllowed,
|
||||
AllowedDeviationTheta = e.AllowedDeviationTheta,
|
||||
AllowedDeviationXy = e.AllowedDeviationXy,
|
||||
MaxHeight = e.MaxHeight,
|
||||
MinHeight = e.MinHeight,
|
||||
MaxSpeed = e.MaxSpeed,
|
||||
MaxRotationSpeed = e.MaxRotationSpeed,
|
||||
Actions = e.Actions,
|
||||
})],
|
||||
Zones = [.. zones.Select(z => new ZoneDto()
|
||||
{
|
||||
Type = z.Type,
|
||||
X1 = z.X1,
|
||||
Y1 = z.Y1,
|
||||
X2 = z.X2,
|
||||
Y2 = z.Y2,
|
||||
X3 = z.X3,
|
||||
Y3 = z.Y3,
|
||||
X4 = z.X4,
|
||||
Y4 = z.Y4,
|
||||
})],
|
||||
Actions = [.. actions.Select(a => new ActionDto()
|
||||
{
|
||||
Id = a.Id,
|
||||
Name = a.Name,
|
||||
Content = a.Content,
|
||||
})],
|
||||
ElementModels = [.. ElementModelExport],
|
||||
Elements = [.. elements.Select(e => new ElementDto()
|
||||
{
|
||||
Name = e.Name,
|
||||
IsOpen = e.IsOpen,
|
||||
ModelId = e.ModelId,
|
||||
NodeId = e.NodeId,
|
||||
OffsetX = e.OffsetX,
|
||||
OffsetY = e.OffsetY,
|
||||
Content = e.Content,
|
||||
})],
|
||||
ImageData = imageData,
|
||||
}
|
||||
};
|
||||
|
||||
var jsonData = JsonSerializer.Serialize(mapDto, JsonOptionExtends.Write);
|
||||
var data = EncryptDataAES(jsonData, Key, IV);
|
||||
return File(data, "application/octet-stream", $"{map.Name}.map");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"EncryptMap: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return NotFound("Hệ thống có lỗi xảy ra");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
[Route("decrypt")]
|
||||
public async Task<MessageResult<MapExportDto>> DecryptMap([FromForm(Name = "importmap")] IFormFile file)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (file == null || file.Length == 0) return new(false, "File không hợp lệ");
|
||||
if (!file.FileName.EndsWith(".map", StringComparison.OrdinalIgnoreCase)) return new(false, "Định dạng file không hợp lệ, yêu cầu file .map");
|
||||
using var memoryStream = new MemoryStream();
|
||||
await file.CopyToAsync(memoryStream);
|
||||
byte[] fileBytes = memoryStream.ToArray();
|
||||
|
||||
var jsonData = DecryptDataAES(fileBytes, Key, IV);
|
||||
var mapData = JsonSerializer.Deserialize<MapExportDto>(jsonData, JsonOptionExtends.Read);
|
||||
if (mapData is null) return new(false, "Dữ liệu không hợp lệ");
|
||||
else return new(true) { Data = mapData };
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"EncryptMap: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"EncryptMap: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
private static byte[] EncryptDataAES(string data, byte[] key, byte[] iv)
|
||||
{
|
||||
using Aes aesAlg = Aes.Create();
|
||||
aesAlg.Key = key;
|
||||
aesAlg.IV = iv;
|
||||
|
||||
ICryptoTransform encryptor = aesAlg.CreateEncryptor(aesAlg.Key, aesAlg.IV);
|
||||
|
||||
using MemoryStream msEncrypt = new();
|
||||
using CryptoStream csEncrypt = new(msEncrypt, encryptor, CryptoStreamMode.Write);
|
||||
using (StreamWriter swEncrypt = new(csEncrypt))
|
||||
{
|
||||
swEncrypt.Write(data);
|
||||
}
|
||||
return msEncrypt.ToArray();
|
||||
}
|
||||
|
||||
private static string DecryptDataAES(byte[] data, byte[] key, byte[] iv)
|
||||
{
|
||||
using Aes aesAlg = Aes.Create();
|
||||
aesAlg.Key = key;
|
||||
aesAlg.IV = iv;
|
||||
|
||||
ICryptoTransform decryptor = aesAlg.CreateDecryptor(aesAlg.Key, aesAlg.IV);
|
||||
|
||||
using MemoryStream msDecrypt = new(data);
|
||||
using CryptoStream csDecrypt = new(msDecrypt, decryptor, CryptoStreamMode.Read);
|
||||
using StreamReader srDecrypt = new(csDecrypt);
|
||||
return srDecrypt.ReadToEnd();
|
||||
}
|
||||
|
||||
public async Task<byte[]> GetImageDataAsync(bool usingLocal, string url)
|
||||
{
|
||||
if (!usingLocal)
|
||||
{
|
||||
var http = HttpClientFactory.CreateClient();
|
||||
var response = await http.GetAsync(url, HttpCompletionOption.ResponseHeadersRead);
|
||||
if (!response.IsSuccessStatusCode) return [];
|
||||
return await response.Content.ReadAsByteArrayAsync();
|
||||
}
|
||||
else
|
||||
{
|
||||
if (System.IO.File.Exists(url)) return System.IO.File.ReadAllBytes(url);
|
||||
return [];
|
||||
}
|
||||
}
|
||||
}
|
||||
381
RobotNet.MapManager/Controllers/MapsDataController.cs
Normal file
381
RobotNet.MapManager/Controllers/MapsDataController.cs
Normal file
@@ -0,0 +1,381 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.MapShares.Models;
|
||||
using RobotNet.Shares;
|
||||
using System.Text.Json;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class MapsDataController(MapEditorDbContext MapDb, LoggerController<MapsDataController> Logger) : ControllerBase
|
||||
{
|
||||
[HttpGet]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult<MapDataDto>> GetMapData(Guid id)
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(id);
|
||||
if (map is null) return new(false, $"Không tìm thấy bản đồ: {id}");
|
||||
|
||||
var result = new MessageResult<MapDataDto>(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = map.Id,
|
||||
Name = map.Name,
|
||||
OriginX = map.OriginX,
|
||||
OriginY = map.OriginY,
|
||||
Resolution = map.Resolution,
|
||||
ImageHeight = map.ImageHeight,
|
||||
ImageWidth = map.ImageWidth,
|
||||
Active = map.Active,
|
||||
Nodes = [.. MapDb.Nodes.Where(node => node.MapId == id).Select(node => new NodeDto()
|
||||
{
|
||||
Id = node.Id,
|
||||
MapId = node.MapId,
|
||||
Name = node.Name,
|
||||
Theta = node.Theta,
|
||||
X = node.X,
|
||||
Y = node.Y,
|
||||
AllowedDeviationXy = node.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = node.AllowedDeviationTheta,
|
||||
Actions = node.Actions,
|
||||
})],
|
||||
Edges = [.. MapDb.Edges.Where(edge => edge.MapId == id).Select(edge => new EdgeDto()
|
||||
{
|
||||
Id = edge.Id,
|
||||
MapId = edge.MapId,
|
||||
StartNodeId = edge.StartNodeId,
|
||||
EndNodeId = edge.EndNodeId,
|
||||
|
||||
MaxSpeed = edge.MaxSpeed,
|
||||
MaxHeight = edge.MaxHeight,
|
||||
MinHeight = edge.MinHeight,
|
||||
DirectionAllowed = edge.DirectionAllowed,
|
||||
RotationAllowed = edge.RotationAllowed,
|
||||
TrajectoryDegree = edge.TrajectoryDegree,
|
||||
ControlPoint1X = edge.ControlPoint1X,
|
||||
ControlPoint1Y = edge.ControlPoint1Y,
|
||||
ControlPoint2X = edge.ControlPoint2X,
|
||||
ControlPoint2Y = edge.ControlPoint2Y,
|
||||
MaxRotationSpeed = edge.MaxRotationSpeed,
|
||||
Actions = edge.Actions,
|
||||
AllowedDeviationXy = edge.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = edge.AllowedDeviationTheta,
|
||||
})],
|
||||
Zones = [.. MapDb.Zones.Where(zone => zone.MapId == id).Select(zone => new ZoneDto()
|
||||
{
|
||||
Id = zone.Id,
|
||||
MapId = zone.MapId,
|
||||
Type = zone.Type,
|
||||
Name = zone.Name,
|
||||
X1 = zone.X1,
|
||||
X2 = zone.X2,
|
||||
Y1 = zone.Y1,
|
||||
Y2 = zone.Y2,
|
||||
X3 = zone.X3,
|
||||
Y3 = zone.Y3,
|
||||
X4 = zone.X4,
|
||||
Y4 = zone.Y4,
|
||||
}).OrderBy(z => z.Type)],
|
||||
Elements = [.. MapDb.Elements.Where(el => el.MapId == id).Select(element => new ElementDto()
|
||||
{
|
||||
Id = element.Id,
|
||||
MapId = element.MapId,
|
||||
ModelId = element.ModelId,
|
||||
Name = element.Name,
|
||||
NodeId = element.NodeId,
|
||||
OffsetX = element.OffsetX,
|
||||
OffsetY = element.OffsetY,
|
||||
IsOpen = element.IsOpen,
|
||||
Content = element.Content,
|
||||
})],
|
||||
Actions = [.. MapDb.Actions.Where(a => a.MapId == id).Select(action => new ActionDto()
|
||||
{
|
||||
Id = action.Id,
|
||||
MapId = action.MapId,
|
||||
Name = action.Name,
|
||||
Content = action.Content,
|
||||
})]
|
||||
}
|
||||
};
|
||||
return result;
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("{id}/updates")]
|
||||
public async Task<MessageResult<IEnumerable<EdgeDto>>> Updates(Guid id, MapEditorBackupModel model)
|
||||
{
|
||||
if (model == null || model.Steps == null) return new(false, "Dữ liệu đầu vào không hợp lệ");
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(id);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {id}");
|
||||
|
||||
List<EdgeDto> EdgeDtos = [];
|
||||
foreach (var step in model.Steps)
|
||||
{
|
||||
switch (step.Type)
|
||||
{
|
||||
case MapEditorBackupType.Node:
|
||||
PositionBackup? nodeUpdate = JsonSerializer.Deserialize<PositionBackup>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (nodeUpdate is not null)
|
||||
{
|
||||
var nodeDb = await MapDb.Nodes.FindAsync(step.Id);
|
||||
if (nodeDb is not null)
|
||||
{
|
||||
nodeDb.X = nodeUpdate.X;
|
||||
nodeDb.Y = nodeUpdate.Y;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case MapEditorBackupType.ControlPoint1Edge:
|
||||
PositionBackup? controlPoint1 = JsonSerializer.Deserialize<PositionBackup>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (controlPoint1 is not null)
|
||||
{
|
||||
var edgeDb = await MapDb.Edges.FindAsync(step.Id);
|
||||
if (edgeDb is not null)
|
||||
{
|
||||
edgeDb.ControlPoint1X = controlPoint1.X;
|
||||
edgeDb.ControlPoint1Y = controlPoint1.Y;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case MapEditorBackupType.ControlPoint2Edge:
|
||||
PositionBackup? controlPoint2 = JsonSerializer.Deserialize<PositionBackup>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (controlPoint2 is not null)
|
||||
{
|
||||
var edgeDb = await MapDb.Edges.FindAsync(step.Id);
|
||||
if (edgeDb is not null)
|
||||
{
|
||||
edgeDb.ControlPoint2X = controlPoint2.X;
|
||||
edgeDb.ControlPoint2Y = controlPoint2.Y;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case MapEditorBackupType.Zone:
|
||||
ZoneShapeBackup? zoneUpdate = JsonSerializer.Deserialize<ZoneShapeBackup>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (zoneUpdate is not null)
|
||||
{
|
||||
var zoneDb = await MapDb.Zones.FindAsync(step.Id);
|
||||
if (zoneDb is not null)
|
||||
{
|
||||
zoneDb.X1 = zoneUpdate.X1;
|
||||
zoneDb.Y1 = zoneUpdate.Y1;
|
||||
zoneDb.X2 = zoneUpdate.X2;
|
||||
zoneDb.Y2 = zoneUpdate.Y2;
|
||||
zoneDb.X3 = zoneUpdate.X3;
|
||||
zoneDb.Y3 = zoneUpdate.Y3;
|
||||
zoneDb.X4 = zoneUpdate.X4;
|
||||
zoneDb.Y4 = zoneUpdate.Y4;
|
||||
}
|
||||
}
|
||||
break;
|
||||
case MapEditorBackupType.MoveEdge:
|
||||
List<EdgeBackup>? edgesUpdate = JsonSerializer.Deserialize<List<EdgeBackup>>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (edgesUpdate is not null && edgesUpdate.Count > 0)
|
||||
{
|
||||
foreach (var edgeUpate in edgesUpdate)
|
||||
{
|
||||
var edgeDb = await MapDb.Edges.FindAsync(edgeUpate.Id);
|
||||
if (edgeDb is not null)
|
||||
{
|
||||
var startNode = await MapDb.Nodes.FindAsync(edgeDb.StartNodeId);
|
||||
var endNode = await MapDb.Nodes.FindAsync(edgeDb.EndNodeId);
|
||||
if (startNode is not null && endNode is not null)
|
||||
{
|
||||
startNode.X = edgeUpate.StartX;
|
||||
startNode.Y = edgeUpate.StartY;
|
||||
endNode.X = edgeUpate.EndX;
|
||||
endNode.Y = edgeUpate.EndY;
|
||||
}
|
||||
edgeDb.ControlPoint1X = edgeUpate.ControlPoint1X;
|
||||
edgeDb.ControlPoint1Y = edgeUpate.ControlPoint1Y;
|
||||
edgeDb.ControlPoint2X = edgeUpate.ControlPoint2X;
|
||||
edgeDb.ControlPoint2Y = edgeUpate.ControlPoint2Y;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case MapEditorBackupType.Copy:
|
||||
List<EdgeMapCopyModel>? edgesCopy = JsonSerializer.Deserialize<List<EdgeMapCopyModel>>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (edgesCopy is not null && edgesCopy.Count > 0)
|
||||
{
|
||||
Dictionary<Guid, Node> CreateNewNode = [];
|
||||
foreach (var edgeCopy in edgesCopy)
|
||||
{
|
||||
if (!CreateNewNode.TryGetValue(edgeCopy.StartNodeId, out _))
|
||||
{
|
||||
var startNode = await MapDb.Nodes.FindAsync(edgeCopy.StartNodeId);
|
||||
var newStartNode = await MapDb.Nodes.AddAsync(new Node()
|
||||
{
|
||||
MapId = edgeCopy.MapId,
|
||||
Name = map.NodeNameAutoGenerate ? $"{map.NodeNameTemplateDefault}{++map.NodeCount}" : string.Empty,
|
||||
X = edgeCopy.X1,
|
||||
Y = edgeCopy.Y1,
|
||||
Theta = startNode is not null ? startNode.Theta : 0,
|
||||
Actions = startNode is not null ? startNode.Actions : "",
|
||||
AllowedDeviationXy = startNode is not null ? startNode.AllowedDeviationXy : map.NodeAllowedDeviationXyDefault,
|
||||
AllowedDeviationTheta = startNode is not null ? startNode.AllowedDeviationTheta : map.NodeAllowedDeviationThetaDefault,
|
||||
});
|
||||
CreateNewNode.Add(edgeCopy.StartNodeId, newStartNode.Entity);
|
||||
}
|
||||
if (!CreateNewNode.TryGetValue(edgeCopy.EndNodeId, out _))
|
||||
{
|
||||
var endNode = await MapDb.Nodes.FindAsync(edgeCopy.EndNodeId);
|
||||
var newEndNode = await MapDb.Nodes.AddAsync(new Node()
|
||||
{
|
||||
MapId = edgeCopy.MapId,
|
||||
Name = map.NodeNameAutoGenerate ? $"{map.NodeNameTemplateDefault}{++map.NodeCount}" : string.Empty,
|
||||
X = edgeCopy.X2,
|
||||
Y = edgeCopy.Y2,
|
||||
Theta = endNode is not null ? endNode.Theta : 0,
|
||||
Actions = endNode is not null ? endNode.Actions : "",
|
||||
AllowedDeviationXy = endNode is not null ? endNode.AllowedDeviationXy : map.NodeAllowedDeviationXyDefault,
|
||||
AllowedDeviationTheta = endNode is not null ? endNode.AllowedDeviationTheta : map.NodeAllowedDeviationThetaDefault,
|
||||
});
|
||||
CreateNewNode.Add(edgeCopy.EndNodeId, newEndNode.Entity);
|
||||
}
|
||||
|
||||
var newEdge = await MapDb.Edges.AddAsync(new Edge()
|
||||
{
|
||||
MapId = edgeCopy.MapId,
|
||||
StartNodeId = CreateNewNode[edgeCopy.StartNodeId] is null ? Guid.Empty : CreateNewNode[edgeCopy.StartNodeId].Id,
|
||||
EndNodeId = CreateNewNode[edgeCopy.EndNodeId] is null ? Guid.Empty : CreateNewNode[edgeCopy.EndNodeId].Id,
|
||||
TrajectoryDegree = edgeCopy.TrajectoryDegree,
|
||||
ControlPoint1X = edgeCopy.ControlPoint1X,
|
||||
ControlPoint1Y = edgeCopy.ControlPoint1Y,
|
||||
ControlPoint2X = edgeCopy.ControlPoint2X,
|
||||
ControlPoint2Y = edgeCopy.ControlPoint2Y,
|
||||
DirectionAllowed = edgeCopy.DirectionAllowed,
|
||||
RotationAllowed = edgeCopy.RotationAllowed,
|
||||
MaxSpeed = edgeCopy.MaxSpeed,
|
||||
MaxRotationSpeed = edgeCopy.MaxRotationSpeed,
|
||||
MaxHeight = edgeCopy.MaxHeight,
|
||||
MinHeight = edgeCopy.MinHeight,
|
||||
Actions = edgeCopy.Actions,
|
||||
AllowedDeviationTheta = edgeCopy.AllowedDeviationTheta,
|
||||
AllowedDeviationXy = edgeCopy.AllowedDeviationXy,
|
||||
});
|
||||
EdgeDtos.Add(new()
|
||||
{
|
||||
|
||||
Id = newEdge.Entity.Id,
|
||||
MapId = newEdge.Entity.MapId,
|
||||
StartNodeId = newEdge.Entity.StartNodeId,
|
||||
EndNodeId = newEdge.Entity.EndNodeId,
|
||||
TrajectoryDegree = newEdge.Entity.TrajectoryDegree,
|
||||
ControlPoint1X = newEdge.Entity.ControlPoint1X,
|
||||
ControlPoint1Y = newEdge.Entity.ControlPoint1Y,
|
||||
ControlPoint2X = newEdge.Entity.ControlPoint2X,
|
||||
ControlPoint2Y = newEdge.Entity.ControlPoint2Y,
|
||||
DirectionAllowed = newEdge.Entity.DirectionAllowed,
|
||||
RotationAllowed = newEdge.Entity.RotationAllowed,
|
||||
MaxSpeed = newEdge.Entity.MaxSpeed,
|
||||
MaxRotationSpeed = newEdge.Entity.MaxRotationSpeed,
|
||||
MaxHeight = newEdge.Entity.MaxHeight,
|
||||
MinHeight = newEdge.Entity.MinHeight,
|
||||
Actions = newEdge.Entity.Actions,
|
||||
AllowedDeviationXy = newEdge.Entity.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = newEdge.Entity.AllowedDeviationTheta,
|
||||
StartNode = new NodeDto()
|
||||
{
|
||||
Id = CreateNewNode[edgeCopy.StartNodeId].Id,
|
||||
Name = CreateNewNode[edgeCopy.StartNodeId].Name,
|
||||
MapId = CreateNewNode[edgeCopy.StartNodeId].MapId,
|
||||
Theta = CreateNewNode[edgeCopy.StartNodeId].Theta,
|
||||
X = CreateNewNode[edgeCopy.StartNodeId].X,
|
||||
Y = CreateNewNode[edgeCopy.StartNodeId].Y,
|
||||
AllowedDeviationXy = CreateNewNode[edgeCopy.StartNodeId].AllowedDeviationXy,
|
||||
AllowedDeviationTheta = CreateNewNode[edgeCopy.StartNodeId].AllowedDeviationTheta,
|
||||
Actions = CreateNewNode[edgeCopy.StartNodeId].Actions,
|
||||
},
|
||||
EndNode = new NodeDto()
|
||||
{
|
||||
Id = CreateNewNode[edgeCopy.EndNodeId].Id,
|
||||
Name = CreateNewNode[edgeCopy.EndNodeId].Name,
|
||||
MapId = CreateNewNode[edgeCopy.EndNodeId].MapId,
|
||||
Theta = CreateNewNode[edgeCopy.EndNodeId].Theta,
|
||||
X = CreateNewNode[edgeCopy.EndNodeId].X,
|
||||
Y = CreateNewNode[edgeCopy.EndNodeId].Y,
|
||||
AllowedDeviationXy = CreateNewNode[edgeCopy.EndNodeId].AllowedDeviationXy,
|
||||
AllowedDeviationTheta = CreateNewNode[edgeCopy.EndNodeId].AllowedDeviationTheta,
|
||||
Actions = CreateNewNode[edgeCopy.EndNodeId].Actions,
|
||||
},
|
||||
});
|
||||
}
|
||||
}
|
||||
break;
|
||||
case MapEditorBackupType.SplitNode:
|
||||
var nodeSplit = await MapDb.Nodes.FindAsync(step.Id);
|
||||
if (nodeSplit is not null)
|
||||
{
|
||||
SplitNodeBackup? SplitNodeUpdate = JsonSerializer.Deserialize<SplitNodeBackup>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (SplitNodeUpdate is not null)
|
||||
{
|
||||
foreach (var data in SplitNodeUpdate.EdgeSplit)
|
||||
{
|
||||
var edge = await MapDb.Edges.FindAsync(data.Key);
|
||||
if (edge is not null)
|
||||
{
|
||||
var newNode = new Node()
|
||||
{
|
||||
Id = data.Value.Id,
|
||||
Name = data.Value.Name,
|
||||
X = data.Value.X,
|
||||
Y = data.Value.Y,
|
||||
Theta = data.Value.Theta,
|
||||
MapId = data.Value.MapId,
|
||||
AllowedDeviationXy = data.Value.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = data.Value.AllowedDeviationTheta,
|
||||
Actions = data.Value.Actions,
|
||||
};
|
||||
if (edge.StartNodeId == nodeSplit.Id) edge.StartNodeId = newNode.Id;
|
||||
else if (edge.EndNodeId == nodeSplit.Id) edge.EndNodeId = newNode.Id;
|
||||
else continue;
|
||||
await MapDb.Nodes.AddAsync(newNode);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
case MapEditorBackupType.MergeNode:
|
||||
var nodemerge = await MapDb.Nodes.FindAsync(step.Id);
|
||||
if (nodemerge is not null)
|
||||
{
|
||||
MergeNodeUpdate? MergeNodeUpdate = JsonSerializer.Deserialize<MergeNodeUpdate>(step.Obj.ToString() ?? "", JsonOptionExtends.Read);
|
||||
if (MergeNodeUpdate is not null)
|
||||
{
|
||||
foreach (var data in MergeNodeUpdate.EdgesMerge)
|
||||
{
|
||||
var edge = await MapDb.Edges.FindAsync(data.Key);
|
||||
if (edge is not null)
|
||||
{
|
||||
var rmNode = await MapDb.Nodes.FindAsync(data.Value);
|
||||
if (edge.StartNodeId == data.Value) edge.StartNodeId = nodemerge.Id;
|
||||
else if (edge.EndNodeId == data.Value) edge.EndNodeId = nodemerge.Id;
|
||||
if (rmNode is not null) MapDb.Nodes.Remove(rmNode);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
Logger.Info($"User {HttpContext.User.Identity?.Name} đã cập nhật dữ liệu cho bản đồ: {map.Name} - {map.Id}");
|
||||
return new(true) { Data = EdgeDtos };
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Updates: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, "Hệ thống có lỗi xảy ra");
|
||||
}
|
||||
}
|
||||
}
|
||||
571
RobotNet.MapManager/Controllers/MapsManagerController.cs
Normal file
571
RobotNet.MapManager/Controllers/MapsManagerController.cs
Normal file
@@ -0,0 +1,571 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.AspNetCore.SignalR;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Hubs;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.MapShares.Enums;
|
||||
using RobotNet.Shares;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class MapsManagerController(MapEditorDbContext MapDb, MapEditorStorageRepository StorageRepo, IHubContext<MapHub> MapHub, LoggerController<MapsManagerController> Logger) : ControllerBase
|
||||
{
|
||||
[HttpGet]
|
||||
public async Task<IEnumerable<MapInfoDto>> GetMapInfos([FromQuery(Name = "txtSearch")] string? txtSearch)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(txtSearch))
|
||||
{
|
||||
return await (from map in MapDb.Maps
|
||||
select new MapInfoDto()
|
||||
{
|
||||
Id = map.Id,
|
||||
VersionId = map.VersionId,
|
||||
Name = map.Name,
|
||||
Description = map.Description,
|
||||
Active = map.Active,
|
||||
OriginX = map.OriginX,
|
||||
OriginY = map.OriginY,
|
||||
Width = Math.Round(map.ImageWidth * map.Resolution, 2),
|
||||
Height = Math.Round(map.ImageHeight * map.Resolution, 2),
|
||||
Resolution = map.Resolution,
|
||||
VDA5050 = map.VDA5050,
|
||||
}).ToListAsync();
|
||||
}
|
||||
else
|
||||
{
|
||||
return await (from map in MapDb.Maps
|
||||
where !string.IsNullOrEmpty(map.Name) && map.Name.Contains(txtSearch)
|
||||
select new MapInfoDto()
|
||||
{
|
||||
Id = map.Id,
|
||||
VersionId = map.VersionId,
|
||||
Name = map.Name,
|
||||
Description = map.Description,
|
||||
Active = map.Active,
|
||||
OriginX = map.OriginX,
|
||||
OriginY = map.OriginY,
|
||||
Width = Math.Round(map.ImageWidth * map.Resolution, 2),
|
||||
Height = Math.Round(map.ImageHeight * map.Resolution, 2),
|
||||
Resolution = map.Resolution,
|
||||
VDA5050 = map.VDA5050,
|
||||
}).ToListAsync();
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetMapInfos: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult<MapInfoDto>> GetMapInfoId(Guid id)
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Id == id);
|
||||
if (map == null) return new MessageResult<MapInfoDto>(false, $"Không tìm thấy map {id}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new MapInfoDto()
|
||||
{
|
||||
Id = map.Id,
|
||||
Name = map.Name,
|
||||
Active = map.Active,
|
||||
OriginX = map.OriginX,
|
||||
OriginY = map.OriginY,
|
||||
Width = Math.Round(map.ImageWidth * map.Resolution, 2),
|
||||
Height = Math.Round(map.ImageHeight * map.Resolution, 2),
|
||||
Resolution = map.Resolution,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("info")]
|
||||
public async Task<MessageResult<MapInfoDto>> GetMapInfoName([FromQuery(Name = "name")] string name)
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Name == name);
|
||||
if (map == null) return new MessageResult<MapInfoDto>(false, $"Không tìm thấy map {name}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new MapInfoDto()
|
||||
{
|
||||
Id = map.Id,
|
||||
Name = map.Name,
|
||||
Active = map.Active,
|
||||
OriginX = map.OriginX,
|
||||
OriginY = map.OriginY,
|
||||
Width = Math.Round(map.ImageWidth * map.Resolution, 2),
|
||||
Height = Math.Round(map.ImageHeight * map.Resolution, 2),
|
||||
Resolution = map.Resolution,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
[Route("")]
|
||||
public async Task<MessageResult<MapInfoDto>> CreateMap([FromForm] MapCreateModel model, [FromForm(Name = "Image")] IFormFile imageUpload)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (imageUpload is null) return new(false, "Dữ liệu không hợp lệ");
|
||||
if (imageUpload.ContentType != "image/png") return new(false, "Ảnh map chỉ hỗ trợ định dạng image/png");
|
||||
if (await MapDb.Maps.AnyAsync(map => map.Name == model.Name)) return new(false, "Tên của map đã tồn tại. Hãy đặt tên khác!");
|
||||
|
||||
var image = SixLabors.ImageSharp.Image.Load(imageUpload.OpenReadStream());
|
||||
|
||||
var entityMap = await MapDb.Maps.AddAsync(new Map()
|
||||
{
|
||||
Name = model.Name,
|
||||
OriginX = model.OriginX,
|
||||
OriginY = model.OriginY,
|
||||
Resolution = model.Resolution,
|
||||
ImageHeight = (ushort)image.Height,
|
||||
ImageWidth = (ushort)image.Width,
|
||||
Active = false,
|
||||
|
||||
NodeCount = 0,
|
||||
NodeNameAutoGenerate = true,
|
||||
NodeNameTemplateDefault = "Node",
|
||||
NodeAllowedDeviationXyDefault = 0.1,
|
||||
NodeAllowedDeviationThetaDefault = 0,
|
||||
|
||||
EdgeMinLengthDefault = 1,
|
||||
EdgeMaxHeightDefault = 1,
|
||||
EdgeMinHeightDefault = 0.1,
|
||||
EdgeStraightMaxSpeedDefault = 1,
|
||||
EdgeCurveMaxSpeedDefault = 0.3,
|
||||
EdgeMaxRotationSpeedDefault = 0.5,
|
||||
EdgeAllowedDeviationXyDefault = 0.1,
|
||||
EdgeAllowedDeviationThetaDefault = 0,
|
||||
EdgeRotationAllowedDefault = true,
|
||||
EdgeDirectionAllowedDefault = DirectionAllowed.Both,
|
||||
|
||||
ZoneMinSquareDefault = 0.25,
|
||||
});
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
var (isSuccess, message) = await StorageRepo.UploadAsync("MapImages", $"{entityMap.Entity.Id}", imageUpload.OpenReadStream(), imageUpload.Length, imageUpload.ContentType, CancellationToken.None);
|
||||
if (!isSuccess)
|
||||
{
|
||||
MapDb.Maps.Remove(entityMap.Entity);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(false, message);
|
||||
}
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
Logger.Info($"User {HttpContext.User.Identity?.Name} đã tạo bản đồ mới với tên: {model.Name}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new MapInfoDto()
|
||||
{
|
||||
Id = entityMap.Entity.Id,
|
||||
Name = entityMap.Entity.Name,
|
||||
Active = entityMap.Entity.Active,
|
||||
OriginX = entityMap.Entity.OriginX,
|
||||
OriginY = entityMap.Entity.OriginY,
|
||||
Width = entityMap.Entity.ImageWidth * entityMap.Entity.Resolution,
|
||||
Height = entityMap.Entity.ImageHeight * entityMap.Entity.Resolution,
|
||||
Resolution = entityMap.Entity.Resolution,
|
||||
},
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"CreateMap: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"CreateMap: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult<MapInfoDto>> UpdateMap(Guid id, [FromBody] MapUpdateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (id != model.Id) return new(false, "Dữ liệu gửi không chính xác");
|
||||
|
||||
var map = await MapDb.Maps.FindAsync(id);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {id}");
|
||||
|
||||
if (map.Name != model.Name && await MapDb.Maps.AnyAsync(m => m.Name == model.Name))
|
||||
{
|
||||
return new(false, "Tên của map đã tồn tại, Hãy đặt tên khác!");
|
||||
}
|
||||
|
||||
if (model.Resolution <= 0)
|
||||
{
|
||||
return new(false, "Độ phân giải của bản đồ phải lớn hơn 0");
|
||||
}
|
||||
|
||||
map.Name = model.Name;
|
||||
bool originChange = map.OriginX != model.OriginX || map.OriginY != model.OriginY;
|
||||
if (originChange)
|
||||
{
|
||||
map.OriginX = model.OriginX;
|
||||
map.OriginY = model.OriginY;
|
||||
}
|
||||
if (map.Resolution != model.Resolution)
|
||||
{
|
||||
var scale = model.Resolution / map.Resolution;
|
||||
map.Resolution = model.Resolution;
|
||||
if (originChange)
|
||||
{
|
||||
map.OriginX *= scale;
|
||||
map.OriginY *= scale;
|
||||
}
|
||||
|
||||
var nodes = await MapDb.Nodes.Where(n => n.MapId == map.Id).ToListAsync();
|
||||
foreach (var node in nodes)
|
||||
{
|
||||
node.X *= scale;
|
||||
node.Y *= scale;
|
||||
}
|
||||
|
||||
var edges = await MapDb.Edges.Where(e => e.MapId == map.Id).ToListAsync();
|
||||
foreach (var edge in edges)
|
||||
{
|
||||
edge.ControlPoint1X *= scale;
|
||||
edge.ControlPoint1Y *= scale;
|
||||
edge.ControlPoint2X *= scale;
|
||||
edge.ControlPoint2Y *= scale;
|
||||
}
|
||||
}
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
Logger.Info($"User {HttpContext.User.Identity?.Name} đã cập nhật thông tin bản đồ : {model.Id} - {map.Name}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = id,
|
||||
Name = map.Name,
|
||||
OriginX = map.OriginX,
|
||||
OriginY = map.OriginY,
|
||||
Resolution = model.Resolution,
|
||||
Width = Math.Round(map.ImageWidth * map.Resolution, 2),
|
||||
Height = Math.Round(map.ImageHeight * map.Resolution, 2),
|
||||
},
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"UpdateMap {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"UpdateMap {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpDelete]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult> DeleteMap(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(id);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {id}");
|
||||
|
||||
MapDb.Elements.RemoveRange(MapDb.Elements.Where(e => e.MapId == map.Id));
|
||||
MapDb.ElementModels.RemoveRange(MapDb.ElementModels.Where(em => em.MapId == map.Id));
|
||||
MapDb.Edges.RemoveRange(MapDb.Edges.Where(edge => edge.MapId == map.Id));
|
||||
MapDb.Nodes.RemoveRange(MapDb.Nodes.Where(node => node.MapId == map.Id));
|
||||
MapDb.Zones.RemoveRange(MapDb.Zones.Where(zone => zone.MapId == map.Id));
|
||||
MapDb.Actions.RemoveRange(MapDb.Actions.Where(action => action.MapId == map.Id));
|
||||
MapDb.Maps.Remove(map);
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
await StorageRepo.DeleteAsync("MapImages", $"{id}", CancellationToken.None);
|
||||
|
||||
Logger.Info($"User {HttpContext.User.Identity?.Name} đã xóa bản đồ {map.Name}");
|
||||
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"DeleteMap {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"DeleteMap {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("active")]
|
||||
public async Task<MessageResult> ActiveToggle([FromBody] MapActiveModel model)
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(model.Id);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {model.Id}");
|
||||
|
||||
map.Active = model.Active;
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
await MapHub.Clients.All.SendAsync("MapUpdated", model.Id);
|
||||
|
||||
Logger.Info($"User {HttpContext.User.Identity?.Name} đã thay đổi trạng thái active bản đồ {map.Name}: {model.Active}");
|
||||
|
||||
return new(true);
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("image/{id}")]
|
||||
public async Task<MessageResult> UpdateImage(Guid id, [FromForm(Name = "image")] IFormFile image)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(id);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {id}");
|
||||
|
||||
var imageStream = image.OpenReadStream();
|
||||
var imageUpdate = SixLabors.ImageSharp.Image.Load(imageStream);
|
||||
map.ImageWidth = (ushort)imageUpdate.Width;
|
||||
map.ImageHeight = (ushort)imageUpdate.Height;
|
||||
await MapDb.SaveChangesAsync();
|
||||
var (isSuccess, message) = await StorageRepo.UploadAsync("MapImages", $"{id}", image.OpenReadStream(), image.Length, image.ContentType, CancellationToken.None);
|
||||
|
||||
Logger.Info($"User {HttpContext.User.Identity?.Name} đã thay đổi ảnh của bản đồ {map.Name}");
|
||||
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"UpdateImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"UpdateImage {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
[Route("import")]
|
||||
public async Task<MessageResult<MapInfoDto>> ImportNewMap([FromBody] MapExportDto model)
|
||||
{
|
||||
if (model == null || model.Data == null || model.Data.ImageData == null || model.Data.ImageData.Length == 0)
|
||||
{
|
||||
return new(false, "Dữ liệu đầu vào không hợp lệ");
|
||||
}
|
||||
|
||||
using var transaction = await MapDb.Database.BeginTransactionAsync();
|
||||
try
|
||||
{
|
||||
if (await MapDb.Maps.AnyAsync(map => map.Name == model.Name)) return new(false, "Tên của map đã tồn tại, Hãy đặt tên khác!");
|
||||
|
||||
using var stream = new MemoryStream(model.Data.ImageData);
|
||||
var imageFile = new FormFile(stream, 0, model.Data.ImageData.Length, "", $"{model.Name}.png")
|
||||
{
|
||||
Headers = new HeaderDictionary(),
|
||||
ContentType = "image/png",
|
||||
};
|
||||
var image = SixLabors.ImageSharp.Image.Load(imageFile.OpenReadStream());
|
||||
|
||||
var entityMap = await MapDb.Maps.AddAsync(new Map()
|
||||
{
|
||||
Name = model.Name,
|
||||
Description = model.Description,
|
||||
OriginX = model.Info.OriginX,
|
||||
OriginY = model.Info.OriginY,
|
||||
Resolution = model.Info.Resolution,
|
||||
ImageHeight = (ushort)image.Height,
|
||||
ImageWidth = (ushort)image.Width,
|
||||
Active = false,
|
||||
ViewX = model.Info.ViewX,
|
||||
ViewY = model.Info.ViewY,
|
||||
ViewWidth = model.Info.ViewWidth,
|
||||
ViewHeight = model.Info.ViewHeight,
|
||||
VDA5050 = model.Info.VDA5050,
|
||||
|
||||
NodeCount = model.Data.NodeCount,
|
||||
NodeNameAutoGenerate = model.Setting.NodeNameAutoGenerate,
|
||||
NodeNameTemplateDefault = model.Setting.NodeNameTemplate,
|
||||
NodeAllowedDeviationXyDefault = model.Setting.NodeAllowedDeviationXy,
|
||||
NodeAllowedDeviationThetaDefault = model.Setting.NodeAllowedDeviationTheta,
|
||||
|
||||
EdgeMinLengthDefault = model.Setting.EdgeMinLength,
|
||||
EdgeMaxHeightDefault = model.Setting.EdgeMaxHeight,
|
||||
EdgeMinHeightDefault = model.Setting.EdgeMinHeight,
|
||||
EdgeStraightMaxSpeedDefault = model.Setting.EdgeStraightMaxSpeed,
|
||||
EdgeCurveMaxSpeedDefault = model.Setting.EdgeCurveMaxSpeed,
|
||||
EdgeMaxRotationSpeedDefault = model.Setting.EdgeMaxRotationSpeed,
|
||||
EdgeAllowedDeviationXyDefault = model.Setting.EdgeAllowedDeviationXy,
|
||||
EdgeAllowedDeviationThetaDefault = model.Setting.EdgeAllowedDeviationTheta,
|
||||
EdgeRotationAllowedDefault = model.Setting.EdgeRotationAllowed,
|
||||
EdgeDirectionAllowedDefault = model.Setting.EdgeDirectionAllowed,
|
||||
|
||||
ZoneMinSquareDefault = model.Setting.ZoneMinSquare,
|
||||
});
|
||||
|
||||
var (isSuccess, message) = await StorageRepo.UploadAsync("MapImages", $"{entityMap.Entity.Id}", imageFile.OpenReadStream(), imageFile.Length, imageFile.ContentType, CancellationToken.None);
|
||||
if (!isSuccess)
|
||||
{
|
||||
await transaction.RollbackAsync();
|
||||
return new(false, message);
|
||||
}
|
||||
|
||||
Dictionary<Guid, Guid> actionSwap = [];
|
||||
foreach (var action in model.Data.Actions)
|
||||
{
|
||||
var actionDb = await MapDb.Actions.AddAsync(new Data.Action()
|
||||
{
|
||||
MapId = entityMap.Entity.Id,
|
||||
Name = action.Name,
|
||||
Content = action.Content,
|
||||
});
|
||||
actionSwap.Add(action.Id, actionDb.Entity.Id);
|
||||
}
|
||||
|
||||
Dictionary<Guid, Guid> nodeSwap = [];
|
||||
foreach (var node in model.Data.Nodes)
|
||||
{
|
||||
var actions = System.Text.Json.JsonSerializer.Deserialize<Guid[]>(node.Actions ?? "");
|
||||
List<Guid> newActions = [];
|
||||
if (actions is not null && actions.Length > 0)
|
||||
{
|
||||
foreach (var actionId in actions)
|
||||
{
|
||||
if (actionSwap.TryGetValue(actionId, out Guid newActionId) && newActionId != Guid.Empty) newActions.Add(newActionId);
|
||||
}
|
||||
}
|
||||
var nodeDb = await MapDb.Nodes.AddAsync(new Node()
|
||||
{
|
||||
Name = node.Name,
|
||||
MapId = entityMap.Entity.Id,
|
||||
X = node.X,
|
||||
Y = node.Y,
|
||||
Theta = node.Theta,
|
||||
AllowedDeviationXy = node.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = node.AllowedDeviationTheta,
|
||||
Actions = System.Text.Json.JsonSerializer.Serialize(newActions),
|
||||
});
|
||||
nodeSwap.Add(node.Id, nodeDb.Entity.Id);
|
||||
}
|
||||
|
||||
var Edges = model.Data.Edges.Select(e => new Edge()
|
||||
{
|
||||
MapId = entityMap.Entity.Id,
|
||||
StartNodeId = nodeSwap[e.StartNodeId],
|
||||
EndNodeId = nodeSwap[e.EndNodeId],
|
||||
ControlPoint1X = e.ControlPoint1X,
|
||||
ControlPoint1Y = e.ControlPoint1Y,
|
||||
ControlPoint2X = e.ControlPoint2X,
|
||||
ControlPoint2Y = e.ControlPoint2Y,
|
||||
TrajectoryDegree = e.TrajectoryDegree,
|
||||
MaxHeight = e.MaxHeight,
|
||||
MinHeight = e.MinHeight,
|
||||
MaxSpeed = e.MaxSpeed,
|
||||
MaxRotationSpeed = e.MaxRotationSpeed,
|
||||
AllowedDeviationXy = e.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = e.AllowedDeviationTheta,
|
||||
DirectionAllowed = e.DirectionAllowed,
|
||||
RotationAllowed = e.RotationAllowed,
|
||||
Actions = e.Actions,
|
||||
}).ToList();
|
||||
|
||||
var Zones = model.Data.Zones.Select(z => new Zone()
|
||||
{
|
||||
MapId = entityMap.Entity.Id,
|
||||
Type = z.Type,
|
||||
X1 = z.X1,
|
||||
X2 = z.X2,
|
||||
Y1 = z.Y1,
|
||||
Y2 = z.Y2,
|
||||
X3 = z.X3,
|
||||
X4 = z.X4,
|
||||
Y3 = z.Y3,
|
||||
Y4 = z.Y4,
|
||||
}).ToList();
|
||||
|
||||
Dictionary<Guid, Guid> elementModelSwap = [];
|
||||
foreach (var elementModel in model.Data.ElementModels)
|
||||
{
|
||||
var elementModelDb = await MapDb.ElementModels.AddAsync(new ElementModel()
|
||||
{
|
||||
MapId = entityMap.Entity.Id,
|
||||
Name = elementModel.Name,
|
||||
Height = elementModel.Height,
|
||||
Width = elementModel.Width,
|
||||
Image1Height = elementModel.Image1Height,
|
||||
Image1Width = elementModel.Image1Width,
|
||||
Image2Height = elementModel.Image2Height,
|
||||
Image2Width = elementModel.Image2Width,
|
||||
Content = elementModel.Content,
|
||||
});
|
||||
elementModelSwap.Add(elementModel.Id, elementModelDb.Entity.Id);
|
||||
|
||||
using var openStream = new MemoryStream(elementModel.ImageOpenData);
|
||||
var imageOpenFile = new FormFile(openStream, 0, elementModel.ImageOpenData.Length, "", $"{elementModel.Name}O.png")
|
||||
{
|
||||
Headers = new HeaderDictionary(),
|
||||
ContentType = "image/png",
|
||||
};
|
||||
await StorageRepo.UploadAsync("ElementOpenModels", $"{elementModelDb.Entity.Id}", imageOpenFile.OpenReadStream(), imageOpenFile.Length, imageOpenFile.ContentType, CancellationToken.None);
|
||||
|
||||
using var closeStream = new MemoryStream(elementModel.ImageCloseData);
|
||||
var imageCloseFile = new FormFile(closeStream, 0, elementModel.ImageCloseData.Length, "", $"{elementModel.Name}C.png")
|
||||
{
|
||||
Headers = new HeaderDictionary(),
|
||||
ContentType = "image/png",
|
||||
};
|
||||
await StorageRepo.UploadAsync("ElementCloseModels", $"{elementModelDb.Entity.Id}", imageCloseFile.OpenReadStream(), imageCloseFile.Length, imageCloseFile.ContentType, CancellationToken.None);
|
||||
}
|
||||
|
||||
var Elements = model.Data.Elements.Select(e => new Data.Element()
|
||||
{
|
||||
MapId = entityMap.Entity.Id,
|
||||
Name = e.Name,
|
||||
IsOpen = e.IsOpen,
|
||||
ModelId = elementModelSwap[e.ModelId],
|
||||
Content = e.Content,
|
||||
NodeId = nodeSwap[e.NodeId],
|
||||
OffsetX = e.OffsetX,
|
||||
OffsetY = e.OffsetY,
|
||||
}).ToList();
|
||||
|
||||
if (Edges.Count > 0) await MapDb.Edges.AddRangeAsync(Edges);
|
||||
if (Zones.Count > 0) await MapDb.Zones.AddRangeAsync(Zones);
|
||||
if (Elements.Count > 0) await MapDb.Elements.AddRangeAsync(Elements);
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
await transaction.CommitAsync();
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new MapInfoDto()
|
||||
{
|
||||
Id = entityMap.Entity.Id,
|
||||
Name = entityMap.Entity.Name,
|
||||
Active = entityMap.Entity.Active,
|
||||
OriginX = entityMap.Entity.OriginX,
|
||||
OriginY = entityMap.Entity.OriginY,
|
||||
Width = entityMap.Entity.ImageWidth * entityMap.Entity.Resolution,
|
||||
Height = entityMap.Entity.ImageHeight * entityMap.Entity.Resolution,
|
||||
Resolution = entityMap.Entity.Resolution,
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (IOException ex)
|
||||
{
|
||||
await transaction.RollbackAsync();
|
||||
Logger.Warning($"ImportNewMap: Lỗi khi xử lý hình ảnh: {ex.Message}");
|
||||
return new(false, $"ImportNewMap: Lỗi khi xử lý hình ảnh: {ex.Message}");
|
||||
}
|
||||
catch (DbUpdateException ex)
|
||||
{
|
||||
await transaction.RollbackAsync();
|
||||
Logger.Warning($"ImportNewMap: Lỗi khi lưu vào database: {ex.Message}");
|
||||
return new(false, $"ImportNewMap: Lỗi khi lưu vào database: {ex.Message}");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
await transaction.RollbackAsync();
|
||||
Logger.Warning($"ImportNewMap: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"ImportNewMap: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
}
|
||||
79
RobotNet.MapManager/Controllers/MapsSettingController.cs
Normal file
79
RobotNet.MapManager/Controllers/MapsSettingController.cs
Normal file
@@ -0,0 +1,79 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.Shares;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class MapsSettingController(MapEditorDbContext MapDb) : ControllerBase
|
||||
{
|
||||
[HttpGet]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult<MapSettingDefaultDto>> GetMapSetting(Guid id)
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Id == id);
|
||||
if (map == null) return new(false, $"Không tìm thấy map {id}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new MapSettingDefaultDto()
|
||||
{
|
||||
Id = map.Id,
|
||||
EdgeStraightMaxSpeed = map.EdgeStraightMaxSpeedDefault,
|
||||
EdgeCurveMaxSpeed = map.EdgeCurveMaxSpeedDefault,
|
||||
EdgeMaxHeight = map.EdgeMaxHeightDefault,
|
||||
EdgeMinHeight = map.EdgeMinHeightDefault,
|
||||
EdgeMinLength = map.EdgeMinLengthDefault,
|
||||
EdgeDirectionAllowed = map.EdgeDirectionAllowedDefault,
|
||||
EdgeMaxRotationSpeed = map.EdgeMaxRotationSpeedDefault,
|
||||
EdgeRotationAllowed = map.EdgeRotationAllowedDefault,
|
||||
EdgeAllowedDeviationXy = map.EdgeAllowedDeviationXyDefault,
|
||||
EdgeAllowedDeviationTheta = map.EdgeAllowedDeviationThetaDefault,
|
||||
|
||||
NodeAllowedDeviationTheta = map.NodeAllowedDeviationThetaDefault,
|
||||
NodeAllowedDeviationXy = map.NodeAllowedDeviationXyDefault,
|
||||
NodeNameAutoGenerate = map.NodeNameAutoGenerate,
|
||||
NodeNameTemplate = map.NodeNameTemplateDefault,
|
||||
|
||||
ZoneMinSquare = map.ZoneMinSquareDefault,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
[HttpPut]
|
||||
[Route("")]
|
||||
public async Task<MessageResult> Update([FromBody] MapSettingDefaultDto mapSetting)
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Id == mapSetting.Id);
|
||||
if (map == null) return new(false, $"Không tìm thấy map {mapSetting.Id}");
|
||||
|
||||
map.EdgeStraightMaxSpeedDefault = mapSetting.EdgeStraightMaxSpeed;
|
||||
map.EdgeCurveMaxSpeedDefault = mapSetting.EdgeCurveMaxSpeed;
|
||||
map.EdgeMaxHeightDefault = mapSetting.EdgeMaxHeight;
|
||||
map.EdgeMinHeightDefault = mapSetting.EdgeMinHeight;
|
||||
map.EdgeMinLengthDefault = mapSetting.EdgeMinLength;
|
||||
map.EdgeDirectionAllowedDefault = mapSetting.EdgeDirectionAllowed;
|
||||
map.EdgeMaxRotationSpeedDefault = mapSetting.EdgeMaxRotationSpeed;
|
||||
map.EdgeRotationAllowedDefault = mapSetting.EdgeRotationAllowed;
|
||||
map.EdgeAllowedDeviationXyDefault = mapSetting.EdgeAllowedDeviationXy;
|
||||
map.EdgeAllowedDeviationThetaDefault = mapSetting.EdgeAllowedDeviationTheta;
|
||||
|
||||
map.NodeAllowedDeviationThetaDefault = mapSetting.NodeAllowedDeviationTheta;
|
||||
map.NodeAllowedDeviationXyDefault = mapSetting.NodeAllowedDeviationXy;
|
||||
map.NodeNameAutoGenerate = mapSetting.NodeNameAutoGenerate;
|
||||
map.NodeNameTemplateDefault = mapSetting.NodeNameTemplate;
|
||||
|
||||
map.ZoneMinSquareDefault = mapSetting.ZoneMinSquare;
|
||||
|
||||
MapDb.Maps.Update(map);
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true);
|
||||
}
|
||||
}
|
||||
58
RobotNet.MapManager/Controllers/NodesController.cs
Normal file
58
RobotNet.MapManager/Controllers/NodesController.cs
Normal file
@@ -0,0 +1,58 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.Shares;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class NodesController(MapEditorDbContext MapDb) : ControllerBase
|
||||
{
|
||||
[HttpGet]
|
||||
[Route("{mapId}")]
|
||||
public async Task<NodeDto[]> GetNodes(Guid mapId)
|
||||
{
|
||||
return await (from node in MapDb.Nodes
|
||||
where node.MapId == mapId
|
||||
select new NodeDto()
|
||||
{
|
||||
Id = node.Id,
|
||||
Name = node.Name,
|
||||
MapId = mapId,
|
||||
X = node.X,
|
||||
Y = node.Y,
|
||||
Theta = node.Theta,
|
||||
AllowedDeviationXy = node.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = node.AllowedDeviationTheta,
|
||||
Actions = node.Actions,
|
||||
}).ToArrayAsync();
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("")]
|
||||
public async Task<MessageResult> Update([FromBody] NodeUpdateModel model)
|
||||
{
|
||||
var node = await MapDb.Nodes.FindAsync(model.Id);
|
||||
if (node == null) return new(false, $"Không tồn tại node id = {model.Id}");
|
||||
|
||||
if (node.Name != model.Name && !string.IsNullOrWhiteSpace(model.Name) && await MapDb.Nodes.AnyAsync(n => n.Name == model.Name && n.MapId == node.MapId))
|
||||
{
|
||||
return new(false, $"Tên node {model.Name} đã tồn tại trong map");
|
||||
}
|
||||
|
||||
node.Name = model.Name;
|
||||
node.X = model.X;
|
||||
node.Y = model.Y;
|
||||
node.Theta = model.Theta;
|
||||
node.AllowedDeviationXy = model.AllowedDeviationXy;
|
||||
node.AllowedDeviationTheta = model.AllowedDeviationTheta;
|
||||
node.Actions = System.Text.Json.JsonSerializer.Serialize(model.Actions ?? []);
|
||||
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true);
|
||||
}
|
||||
}
|
||||
232
RobotNet.MapManager/Controllers/ScriptElementsController.cs
Normal file
232
RobotNet.MapManager/Controllers/ScriptElementsController.cs
Normal file
@@ -0,0 +1,232 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.MapShares.Models;
|
||||
using RobotNet.MapShares.Property;
|
||||
using RobotNet.Shares;
|
||||
using Serialize.Linq.Serializers;
|
||||
using System.Linq.Expressions;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class ScriptElementsController(MapEditorDbContext MapDb, LoggerController<ScriptElementsController> Logger) : ControllerBase
|
||||
{
|
||||
private static readonly ExpressionSerializer expressionSerializer;
|
||||
|
||||
static ScriptElementsController()
|
||||
{
|
||||
var jss = new Serialize.Linq.Serializers.JsonSerializer();
|
||||
expressionSerializer = new ExpressionSerializer(jss);
|
||||
|
||||
expressionSerializer.AddKnownType(typeof(Script.Expressions.ElementProperties));
|
||||
}
|
||||
|
||||
[HttpPost]
|
||||
public async Task<MessageResult<IEnumerable<ElementDto>>> GetElementsWithCondition([FromBody] ElementExpressionModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Name == model.MapName);
|
||||
if (map is null) return new(false, $"Không tồn tại map tên = {model.MapName}");
|
||||
|
||||
var elModel = await MapDb.ElementModels.FirstOrDefaultAsync(m => m.MapId == map.Id && m.Name == model.ModelName);
|
||||
if (elModel is null) return new(false, $"Không tồn tại element model tên = {model.ModelName}");
|
||||
|
||||
var modelProperties = System.Text.Json.JsonSerializer.Deserialize<List<ElementProperty>>(elModel.Content, JsonOptionExtends.Read);
|
||||
if (modelProperties is null || modelProperties.Count == 0)
|
||||
return new(false, $"Không tồn tại property nào trong element model tên = {model.ModelName}");
|
||||
|
||||
var expr = expressionSerializer.DeserializeText(model.Expression);
|
||||
var lambda = (Expression<Func<Script.Expressions.ElementProperties, bool>>)expr;
|
||||
|
||||
// Compile và chạy:
|
||||
var func = lambda.Compile();
|
||||
|
||||
var elements = await MapDb.Elements.Where(e => e.MapId == map.Id && e.ModelId == elModel.Id).ToListAsync();
|
||||
List<ElementDto> elementSatisfies = [];
|
||||
foreach (var element in elements)
|
||||
{
|
||||
var properties = MapManagerExtensions.GetElementProperties(element.IsOpen, element.Content);
|
||||
if (func.Invoke(properties))
|
||||
{
|
||||
var elNode = await MapDb.Nodes.FindAsync(element.NodeId);
|
||||
if (elNode is null) continue; // Bỏ qua nếu không tìm thấy node
|
||||
elementSatisfies.Add(new ElementDto()
|
||||
{
|
||||
Id = element.Id,
|
||||
Name = element.Name,
|
||||
MapId = element.MapId,
|
||||
IsOpen = element.IsOpen,
|
||||
NodeId = element.NodeId,
|
||||
OffsetX = element.OffsetX,
|
||||
OffsetY = element.OffsetY,
|
||||
ModelId = element.ModelId,
|
||||
Content = element.Content,
|
||||
NodeName = elNode.Name,
|
||||
ModelName = elModel.Name,
|
||||
X = elNode.X,
|
||||
Y = elNode.Y,
|
||||
Theta = elNode.Theta
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = elementSatisfies
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetElement: Hệ thống có lỗi xảy ra - {ex}");
|
||||
return new(false, $"Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("{mapName}/node/{nodeName}")]
|
||||
public async Task<MessageResult<NodeDto>> GetNode([FromRoute] string mapName, [FromRoute] string nodeName)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Name == mapName);
|
||||
if (map is null) return new(false, $"Không tồn tại map tên = {mapName}");
|
||||
|
||||
var node = await MapDb.Nodes.FirstOrDefaultAsync(n => n.MapId == map.Id && n.Name == nodeName);
|
||||
if (node is null) return new(false, $"Không tồn tại node {nodeName} trong map {mapName}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new NodeDto()
|
||||
{
|
||||
Id = node.Id,
|
||||
Name = node.Name,
|
||||
MapId = node.MapId,
|
||||
X = node.X,
|
||||
Y = node.Y,
|
||||
Theta = node.Theta,
|
||||
AllowedDeviationXy = node.AllowedDeviationXy,
|
||||
AllowedDeviationTheta = node.AllowedDeviationTheta,
|
||||
Actions = node.Actions,
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetElement: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"GetElement: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpGet]
|
||||
[Route("{mapName}/element/{elementName}")]
|
||||
public async Task<MessageResult<ElementDto>> GetElement([FromRoute] string mapName, [FromRoute] string elementName)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Name == mapName);
|
||||
if (map is null) return new(false, $"Không tồn tại map tên = {mapName}");
|
||||
|
||||
var el = await MapDb.Elements.FirstOrDefaultAsync(e => e.MapId == map.Id && e.Name == elementName);
|
||||
if (el is null) return new(false, $"Không tồn tại element name = {elementName}");
|
||||
|
||||
var elModel = await MapDb.ElementModels.FindAsync(el.ModelId);
|
||||
if (elModel == null) return new(false, $"Không tồn tại element model id = {el.ModelId}");
|
||||
|
||||
var elNode = await MapDb.Nodes.FindAsync(el.NodeId);
|
||||
if (elNode is null) return new(false, $"Không tồn tại node id = {el.NodeId}");
|
||||
|
||||
return new(true)
|
||||
{
|
||||
Data = new()
|
||||
{
|
||||
Id = el.Id,
|
||||
Name = el.Name,
|
||||
MapId = el.MapId,
|
||||
IsOpen = el.IsOpen,
|
||||
NodeId = el.NodeId,
|
||||
OffsetX = el.OffsetX,
|
||||
OffsetY = el.OffsetY,
|
||||
ModelId = el.ModelId,
|
||||
Content = el.Content,
|
||||
NodeName = elNode.Name,
|
||||
ModelName = elModel.Name,
|
||||
X = elNode.X,
|
||||
Y = elNode.Y,
|
||||
Theta = elNode.Theta
|
||||
}
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"GetElement: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"GetElement: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPatch]
|
||||
[Route("{mapName}/element/{elementName}")]
|
||||
public async Task<MessageResult> UpdateElementProperty([FromRoute] string mapName, [FromRoute] string elementName, [FromBody] ElementPropertyUpdateModel model)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Name == mapName);
|
||||
if (map is null) return new(false, $"Không tồn tại map tên = {mapName}");
|
||||
|
||||
var element = await MapDb.Elements.FirstOrDefaultAsync(m => m.Name == elementName && m.MapId == map.Id);
|
||||
if (element == null) return new(false, $"Không tồn tại element tên = {elementName} trong map tên = {mapName}");
|
||||
|
||||
var properties = System.Text.Json.JsonSerializer.Deserialize<List<ElementProperty>>(element.Content, JsonOptionExtends.Read);
|
||||
foreach (var property in model.Properties)
|
||||
{
|
||||
var existingProperty = properties?.FirstOrDefault(p => p.Name == property.Name);
|
||||
if (existingProperty != null)
|
||||
{
|
||||
existingProperty.DefaultValue = property.DefaultValue;
|
||||
}
|
||||
else return new(false, $"Không tồn tại property name = {property.Name} trong element");
|
||||
}
|
||||
var content = System.Text.Json.JsonSerializer.Serialize(properties, JsonOptionExtends.Write);
|
||||
element.Content = content;
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPatch]
|
||||
[Route("{mapName}/element/{elementName}/IsOpen")]
|
||||
public async Task<MessageResult> UpdateOpenOfElement([FromRoute] string mapName, [FromRoute] string elementName, [FromQuery] bool isOpen)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FirstOrDefaultAsync(m => m.Name == mapName);
|
||||
if (map is null) return new(false, $"Không tồn tại map tên = {mapName}");
|
||||
|
||||
var element = await MapDb.Elements.FirstOrDefaultAsync(m => m.Name == elementName && m.MapId == map.Id);
|
||||
if (element == null) return new(false, $"Không tồn tại element tên = {elementName} trong map tên = {mapName}");
|
||||
|
||||
element.IsOpen = isOpen;
|
||||
await MapDb.SaveChangesAsync();
|
||||
|
||||
return new(true);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
}
|
||||
114
RobotNet.MapManager/Controllers/ZonesController.cs
Normal file
114
RobotNet.MapManager/Controllers/ZonesController.cs
Normal file
@@ -0,0 +1,114 @@
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
using RobotNet.MapManager.Data;
|
||||
using RobotNet.MapManager.Services;
|
||||
using RobotNet.MapShares;
|
||||
using RobotNet.MapShares.Dtos;
|
||||
using RobotNet.Shares;
|
||||
|
||||
namespace RobotNet.MapManager.Controllers;
|
||||
|
||||
[Route("api/[controller]")]
|
||||
[ApiController]
|
||||
[Authorize]
|
||||
public class ZonesController(MapEditorDbContext MapDb, LoggerController<ZonesController> Logger) : ControllerBase
|
||||
{
|
||||
[HttpPost]
|
||||
[Route("")]
|
||||
public async Task<MessageResult<ZoneDto>> Create([FromBody] ZoneCreateModel zone)
|
||||
{
|
||||
try
|
||||
{
|
||||
var map = await MapDb.Maps.FindAsync(zone.MapId);
|
||||
if (map == null) return new(false, $"Không tồn tại map id = {zone.MapId}");
|
||||
|
||||
if (MapEditorHelper.CalculateQuadrilateralArea(zone.X1, zone.Y1, zone.X2, zone.Y2, zone.X3, zone.Y3, zone.X4, zone.Y4) < map.ZoneMinSquareDefault)
|
||||
return new(false, "Kích thước Zone quá nhỏ");
|
||||
|
||||
var entity = await MapDb.Zones.AddAsync(new()
|
||||
{
|
||||
MapId = zone.MapId,
|
||||
Type = zone.Type,
|
||||
Name = "",
|
||||
X1 = zone.X1,
|
||||
X2 = zone.X2,
|
||||
X3 = zone.X3,
|
||||
X4 = zone.X4,
|
||||
Y1 = zone.Y1,
|
||||
Y2 = zone.Y2,
|
||||
Y3 = zone.Y3,
|
||||
Y4 = zone.Y4,
|
||||
});
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true)
|
||||
{
|
||||
Data = new ZoneDto() { Id = entity.Entity.Id, MapId = entity.Entity.MapId, Type = entity.Entity.Type, X1 = entity.Entity.X1, X2 = entity.Entity.X2, X3 = entity.Entity.X3, X4 = entity.Entity.X4, Y1 = entity.Entity.Y1, Y2 = entity.Entity.Y2, Y3 = entity.Entity.Y3, Y4 = entity.Entity.Y4 }
|
||||
};
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Create: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, "Hệ thống có lỗi xảy ra");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpDelete]
|
||||
[Route("{id}")]
|
||||
public async Task<MessageResult> Delete(Guid id)
|
||||
{
|
||||
try
|
||||
{
|
||||
var zoneExisted = await MapDb.Zones.FindAsync(id);
|
||||
if (zoneExisted is not null)
|
||||
{
|
||||
MapDb.Zones.Remove(zoneExisted);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true);
|
||||
}
|
||||
return new(false, "Hệ thống không tìm thấy khu vực Zone này");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Delete {id}: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, "Hệ thống có lỗi xảy ra");
|
||||
}
|
||||
}
|
||||
|
||||
[HttpPut]
|
||||
[Route("")]
|
||||
public async Task<MessageResult> Update([FromBody] ZoneUpdateModel zone)
|
||||
{
|
||||
try
|
||||
{
|
||||
var zoneExisted = await MapDb.Zones.FindAsync(zone.Id);
|
||||
if (zoneExisted is not null)
|
||||
{
|
||||
if (zoneExisted.Name != zone.Name && !string.IsNullOrWhiteSpace(zone.Name) && await MapDb.Zones.AnyAsync(z => z.Name == zone.Name && z.MapId == zoneExisted.MapId))
|
||||
{
|
||||
return new(false, $"Tên zone {zone.Name} đã tồn tại trong map");
|
||||
}
|
||||
|
||||
zoneExisted.Type = zone.Type;
|
||||
zoneExisted.Name = zone.Name;
|
||||
zoneExisted.X1 = zone.X1;
|
||||
zoneExisted.X2 = zone.X2;
|
||||
zoneExisted.X3 = zone.X3;
|
||||
zoneExisted.X4 = zone.X4;
|
||||
zoneExisted.Y1 = zone.Y1;
|
||||
zoneExisted.Y2 = zone.Y2;
|
||||
zoneExisted.Y3 = zone.Y3;
|
||||
zoneExisted.Y4 = zone.Y4;
|
||||
MapDb.Zones.Update(zoneExisted);
|
||||
await MapDb.SaveChangesAsync();
|
||||
return new(true);
|
||||
}
|
||||
return new(false, "Hệ thống không tìm thấy khu vực Zone này");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Logger.Warning($"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
return new(false, $"Update: Hệ thống có lỗi xảy ra - {ex.Message}");
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user