Add chips virgens and controle recebidos support

This commit is contained in:
Eduardo Lopes 2026-01-27 12:03:19 -03:00
parent 0d1305bdbe
commit 851ef027a6
11 changed files with 2017 additions and 0 deletions

View File

@ -0,0 +1,162 @@
using line_gestao_api.Data;
using line_gestao_api.Dtos;
using line_gestao_api.Models;
using Microsoft.AspNetCore.Mvc;
using Microsoft.EntityFrameworkCore;
using System.Text;
namespace line_gestao_api.Controllers
{
[ApiController]
[Route("api/chips-virgens")]
public class ChipsVirgensController : ControllerBase
{
private readonly AppDbContext _db;
public ChipsVirgensController(AppDbContext db)
{
_db = db;
}
[HttpGet]
public async Task<ActionResult<PagedResult<ChipVirgemListDto>>> GetAll(
[FromQuery] string? search,
[FromQuery] int page = 1,
[FromQuery] int pageSize = 20,
[FromQuery] string? sortBy = "item",
[FromQuery] string? sortDir = "asc")
{
page = page < 1 ? 1 : page;
pageSize = pageSize < 1 ? 20 : pageSize;
var q = _db.ChipVirgemLines.AsNoTracking();
if (!string.IsNullOrWhiteSpace(search))
{
var s = search.Trim();
q = q.Where(x =>
EF.Functions.ILike(x.NumeroDoChip ?? "", $"%{s}%") ||
EF.Functions.ILike(x.Observacoes ?? "", $"%{s}%") ||
EF.Functions.ILike(x.Item.ToString(), $"%{s}%"));
}
var total = await q.CountAsync();
var sb = (sortBy ?? "item").Trim().ToLowerInvariant();
var desc = string.Equals((sortDir ?? "asc").Trim(), "desc", StringComparison.OrdinalIgnoreCase);
q = sb switch
{
"numerodochip" => desc ? q.OrderByDescending(x => x.NumeroDoChip ?? "").ThenBy(x => x.Item)
: q.OrderBy(x => x.NumeroDoChip ?? "").ThenBy(x => x.Item),
"observacoes" => desc ? q.OrderByDescending(x => x.Observacoes ?? "").ThenBy(x => x.Item)
: q.OrderBy(x => x.Observacoes ?? "").ThenBy(x => x.Item),
_ => desc ? q.OrderByDescending(x => x.Item) : q.OrderBy(x => x.Item)
};
var items = await q
.Skip((page - 1) * pageSize)
.Take(pageSize)
.Select(x => new ChipVirgemListDto
{
Id = x.Id,
Item = x.Item,
NumeroDoChip = x.NumeroDoChip,
Observacoes = x.Observacoes
})
.ToListAsync();
return Ok(new PagedResult<ChipVirgemListDto>
{
Page = page,
PageSize = pageSize,
Total = total,
Items = items
});
}
[HttpGet("{id:guid}")]
public async Task<ActionResult<ChipVirgemDetailDto>> GetById(Guid id)
{
var x = await _db.ChipVirgemLines.AsNoTracking().FirstOrDefaultAsync(a => a.Id == id);
if (x == null) return NotFound();
return Ok(ToDetailDto(x));
}
[HttpPost]
public async Task<ActionResult<ChipVirgemDetailDto>> Create([FromBody] CreateChipVirgemDto req)
{
var now = DateTime.UtcNow;
var e = new ChipVirgemLine
{
Id = Guid.NewGuid(),
Item = req.Item ?? 0,
NumeroDoChip = NullIfEmptyDigits(req.NumeroDoChip),
Observacoes = string.IsNullOrWhiteSpace(req.Observacoes) ? null : req.Observacoes.Trim(),
CreatedAt = now,
UpdatedAt = now
};
_db.ChipVirgemLines.Add(e);
await _db.SaveChangesAsync();
return CreatedAtAction(nameof(GetById), new { id = e.Id }, ToDetailDto(e));
}
[HttpPut("{id:guid}")]
public async Task<IActionResult> Update(Guid id, [FromBody] UpdateChipVirgemRequest req)
{
var x = await _db.ChipVirgemLines.FirstOrDefaultAsync(a => a.Id == id);
if (x == null) return NotFound();
if (req.Item.HasValue) x.Item = req.Item.Value;
x.NumeroDoChip = NullIfEmptyDigits(req.NumeroDoChip);
x.Observacoes = string.IsNullOrWhiteSpace(req.Observacoes) ? null : req.Observacoes.Trim();
x.UpdatedAt = DateTime.UtcNow;
await _db.SaveChangesAsync();
return NoContent();
}
[HttpDelete("{id:guid}")]
public async Task<IActionResult> Delete(Guid id)
{
var x = await _db.ChipVirgemLines.FirstOrDefaultAsync(a => a.Id == id);
if (x == null) return NotFound();
_db.ChipVirgemLines.Remove(x);
await _db.SaveChangesAsync();
return NoContent();
}
private static ChipVirgemDetailDto ToDetailDto(ChipVirgemLine x) => new()
{
Id = x.Id,
Item = x.Item,
NumeroDoChip = x.NumeroDoChip,
Observacoes = x.Observacoes,
CreatedAt = x.CreatedAt,
UpdatedAt = x.UpdatedAt
};
private static string? NullIfEmptyDigits(string? s)
{
var d = OnlyDigits(s);
return string.IsNullOrWhiteSpace(d) ? null : d;
}
private static string OnlyDigits(string? s)
{
if (string.IsNullOrWhiteSpace(s)) return "";
var sb = new StringBuilder();
foreach (var c in s)
{
if (char.IsDigit(c)) sb.Append(c);
}
return sb.ToString();
}
}
}

View File

@ -0,0 +1,237 @@
using line_gestao_api.Data;
using line_gestao_api.Dtos;
using line_gestao_api.Models;
using Microsoft.AspNetCore.Mvc;
using Microsoft.EntityFrameworkCore;
using System.Text;
namespace line_gestao_api.Controllers
{
[ApiController]
[Route("api/controle-recebidos")]
public class ControleRecebidosController : ControllerBase
{
private readonly AppDbContext _db;
public ControleRecebidosController(AppDbContext db)
{
_db = db;
}
[HttpGet]
public async Task<ActionResult<PagedResult<ControleRecebidoListDto>>> GetAll(
[FromQuery] int? ano,
[FromQuery] bool? isResumo,
[FromQuery] string? search,
[FromQuery] int page = 1,
[FromQuery] int pageSize = 20,
[FromQuery] string? sortBy = "item",
[FromQuery] string? sortDir = "asc")
{
page = page < 1 ? 1 : page;
pageSize = pageSize < 1 ? 20 : pageSize;
var q = _db.ControleRecebidoLines.AsNoTracking();
if (ano.HasValue)
q = q.Where(x => x.Ano == ano.Value);
if (isResumo.HasValue)
q = q.Where(x => x.IsResumo == isResumo.Value);
if (!string.IsNullOrWhiteSpace(search))
{
var s = search.Trim();
q = q.Where(x =>
EF.Functions.ILike(x.NotaFiscal ?? "", $"%{s}%") ||
EF.Functions.ILike(x.Chip ?? "", $"%{s}%") ||
EF.Functions.ILike(x.Serial ?? "", $"%{s}%") ||
EF.Functions.ILike(x.ConteudoDaNf ?? "", $"%{s}%") ||
EF.Functions.ILike(x.NumeroDaLinha ?? "", $"%{s}%") ||
EF.Functions.ILike(x.Item.ToString(), $"%{s}%") ||
EF.Functions.ILike(x.Ano.ToString(), $"%{s}%"));
}
var total = await q.CountAsync();
var sb = (sortBy ?? "item").Trim().ToLowerInvariant();
var desc = string.Equals((sortDir ?? "asc").Trim(), "desc", StringComparison.OrdinalIgnoreCase);
q = sb switch
{
"ano" => desc ? q.OrderByDescending(x => x.Ano).ThenBy(x => x.Item)
: q.OrderBy(x => x.Ano).ThenBy(x => x.Item),
"notafiscal" => desc ? q.OrderByDescending(x => x.NotaFiscal ?? "").ThenBy(x => x.Item)
: q.OrderBy(x => x.NotaFiscal ?? "").ThenBy(x => x.Item),
"datadanf" => desc ? q.OrderByDescending(x => x.DataDaNf).ThenBy(x => x.Item)
: q.OrderBy(x => x.DataDaNf).ThenBy(x => x.Item),
"datadorecebimento" => desc ? q.OrderByDescending(x => x.DataDoRecebimento).ThenBy(x => x.Item)
: q.OrderBy(x => x.DataDoRecebimento).ThenBy(x => x.Item),
"valordanf" => desc ? q.OrderByDescending(x => x.ValorDaNf ?? 0).ThenBy(x => x.Item)
: q.OrderBy(x => x.ValorDaNf ?? 0).ThenBy(x => x.Item),
"quantidade" => desc ? q.OrderByDescending(x => x.Quantidade ?? 0).ThenBy(x => x.Item)
: q.OrderBy(x => x.Quantidade ?? 0).ThenBy(x => x.Item),
_ => desc ? q.OrderByDescending(x => x.Item) : q.OrderBy(x => x.Item)
};
var items = await q
.Skip((page - 1) * pageSize)
.Take(pageSize)
.Select(x => new ControleRecebidoListDto
{
Id = x.Id,
Ano = x.Ano,
Item = x.Item,
NotaFiscal = x.NotaFiscal,
Chip = x.Chip,
Serial = x.Serial,
ConteudoDaNf = x.ConteudoDaNf,
NumeroDaLinha = x.NumeroDaLinha,
ValorUnit = x.ValorUnit,
ValorDaNf = x.ValorDaNf,
DataDaNf = x.DataDaNf,
DataDoRecebimento = x.DataDoRecebimento,
Quantidade = x.Quantidade,
IsResumo = x.IsResumo
})
.ToListAsync();
return Ok(new PagedResult<ControleRecebidoListDto>
{
Page = page,
PageSize = pageSize,
Total = total,
Items = items
});
}
[HttpGet("{id:guid}")]
public async Task<ActionResult<ControleRecebidoDetailDto>> GetById(Guid id)
{
var x = await _db.ControleRecebidoLines.AsNoTracking().FirstOrDefaultAsync(a => a.Id == id);
if (x == null) return NotFound();
return Ok(ToDetailDto(x));
}
[HttpPost]
public async Task<ActionResult<ControleRecebidoDetailDto>> Create([FromBody] CreateControleRecebidoDto req)
{
var now = DateTime.UtcNow;
var e = new ControleRecebidoLine
{
Id = Guid.NewGuid(),
Ano = req.Ano ?? DateTime.UtcNow.Year,
Item = req.Item ?? 0,
NotaFiscal = TrimOrNull(req.NotaFiscal),
Chip = NullIfEmptyDigits(req.Chip),
Serial = TrimOrNull(req.Serial),
ConteudoDaNf = TrimOrNull(req.ConteudoDaNf),
NumeroDaLinha = NullIfEmptyDigits(req.NumeroDaLinha),
ValorUnit = req.ValorUnit,
ValorDaNf = req.ValorDaNf,
DataDaNf = ToUtc(req.DataDaNf),
DataDoRecebimento = ToUtc(req.DataDoRecebimento),
Quantidade = req.Quantidade,
IsResumo = req.IsResumo ?? false,
CreatedAt = now,
UpdatedAt = now
};
_db.ControleRecebidoLines.Add(e);
await _db.SaveChangesAsync();
return CreatedAtAction(nameof(GetById), new { id = e.Id }, ToDetailDto(e));
}
[HttpPut("{id:guid}")]
public async Task<IActionResult> Update(Guid id, [FromBody] UpdateControleRecebidoRequest req)
{
var x = await _db.ControleRecebidoLines.FirstOrDefaultAsync(a => a.Id == id);
if (x == null) return NotFound();
if (req.Ano.HasValue) x.Ano = req.Ano.Value;
if (req.Item.HasValue) x.Item = req.Item.Value;
x.NotaFiscal = TrimOrNull(req.NotaFiscal);
x.Chip = NullIfEmptyDigits(req.Chip);
x.Serial = TrimOrNull(req.Serial);
x.ConteudoDaNf = TrimOrNull(req.ConteudoDaNf);
x.NumeroDaLinha = NullIfEmptyDigits(req.NumeroDaLinha);
x.ValorUnit = req.ValorUnit;
x.ValorDaNf = req.ValorDaNf;
x.DataDaNf = ToUtc(req.DataDaNf);
x.DataDoRecebimento = ToUtc(req.DataDoRecebimento);
x.Quantidade = req.Quantidade;
if (req.IsResumo.HasValue) x.IsResumo = req.IsResumo.Value;
x.UpdatedAt = DateTime.UtcNow;
await _db.SaveChangesAsync();
return NoContent();
}
[HttpDelete("{id:guid}")]
public async Task<IActionResult> Delete(Guid id)
{
var x = await _db.ControleRecebidoLines.FirstOrDefaultAsync(a => a.Id == id);
if (x == null) return NotFound();
_db.ControleRecebidoLines.Remove(x);
await _db.SaveChangesAsync();
return NoContent();
}
private static ControleRecebidoDetailDto ToDetailDto(ControleRecebidoLine x) => new()
{
Id = x.Id,
Ano = x.Ano,
Item = x.Item,
NotaFiscal = x.NotaFiscal,
Chip = x.Chip,
Serial = x.Serial,
ConteudoDaNf = x.ConteudoDaNf,
NumeroDaLinha = x.NumeroDaLinha,
ValorUnit = x.ValorUnit,
ValorDaNf = x.ValorDaNf,
DataDaNf = x.DataDaNf,
DataDoRecebimento = x.DataDoRecebimento,
Quantidade = x.Quantidade,
IsResumo = x.IsResumo,
CreatedAt = x.CreatedAt,
UpdatedAt = x.UpdatedAt
};
private static DateTime? ToUtc(DateTime? dt)
{
if (dt == null) return null;
var v = dt.Value;
return v.Kind == DateTimeKind.Utc ? v :
(v.Kind == DateTimeKind.Local ? v.ToUniversalTime() : DateTime.SpecifyKind(v, DateTimeKind.Utc));
}
private static string? TrimOrNull(string? s)
{
if (string.IsNullOrWhiteSpace(s)) return null;
return s.Trim();
}
private static string? NullIfEmptyDigits(string? s)
{
var d = OnlyDigits(s);
return string.IsNullOrWhiteSpace(d) ? null : d;
}
private static string OnlyDigits(string? s)
{
if (string.IsNullOrWhiteSpace(s)) return "";
var sb = new StringBuilder();
foreach (var c in s)
{
if (char.IsDigit(c)) sb.Append(c);
}
return sb.ToString();
}
}
}

View File

@ -634,6 +634,16 @@ namespace line_gestao_api.Controllers
// ========================= // =========================
await ImportTrocaNumeroFromWorkbook(wb); await ImportTrocaNumeroFromWorkbook(wb);
// =========================
// ✅ IMPORTA CHIPS VIRGENS
// =========================
await ImportChipsVirgensFromWorkbook(wb);
// =========================
// ✅ IMPORTA CONTROLE DE RECEBIDOS
// =========================
await ImportControleRecebidosFromWorkbook(wb);
await tx.CommitAsync(); await tx.CommitAsync();
return Ok(new ImportResultDto { Imported = imported }); return Ok(new ImportResultDto { Imported = imported });
} }
@ -1303,6 +1313,225 @@ namespace line_gestao_api.Controllers
} }
} }
// ==========================================================
// ✅ IMPORTAÇÃO CHIPS VIRGENS
// ==========================================================
private async Task ImportChipsVirgensFromWorkbook(XLWorkbook wb)
{
var ws = wb.Worksheets.FirstOrDefault(w => NormalizeHeader(w.Name) == NormalizeHeader("CHIP VIRGENS E CONTROLE DE RECEBIDOS"))
?? wb.Worksheets.FirstOrDefault(w => NormalizeHeader(w.Name) == NormalizeHeader("CHIPS VIRGENS"))
?? wb.Worksheets.FirstOrDefault(w =>
{
var name = NormalizeHeader(w.Name);
return name.Contains("CHIP") && name.Contains("VIRGEN");
});
if (ws == null) return;
var headerRow = ws.RowsUsed().FirstOrDefault(r => r.CellsUsed().Any(c => NormalizeHeader(c.GetString()) == "ITEM"));
if (headerRow == null) return;
var map = BuildHeaderMap(headerRow);
int colItem = GetCol(map, "ITEM");
if (colItem == 0) return;
var startRow = headerRow.RowNumber() + 1;
var lastRow = ws.LastRowUsed()?.RowNumber() ?? startRow;
await _db.ChipVirgemLines.ExecuteDeleteAsync();
var buffer = new List<ChipVirgemLine>(500);
for (int r = startRow; r <= lastRow; r++)
{
var itemStr = GetCellString(ws, r, colItem);
if (string.IsNullOrWhiteSpace(itemStr)) break;
var numeroChip = NullIfEmptyDigits(GetCellByHeaderAny(ws, r, map,
"Nº DO CHIP", "N° DO CHIP", "NUMERO DO CHIP", "N DO CHIP", "NUM. DO CHIP"));
var observacoes = GetCellByHeaderAny(ws, r, map, "OBSERVAÇÕES", "OBSERVACOES", "OBS");
var now = DateTime.UtcNow;
var e = new ChipVirgemLine
{
Id = Guid.NewGuid(),
Item = TryInt(itemStr),
NumeroDoChip = numeroChip,
Observacoes = string.IsNullOrWhiteSpace(observacoes) ? null : observacoes.Trim(),
CreatedAt = now,
UpdatedAt = now
};
buffer.Add(e);
if (buffer.Count >= 500)
{
await _db.ChipVirgemLines.AddRangeAsync(buffer);
await _db.SaveChangesAsync();
buffer.Clear();
}
}
if (buffer.Count > 0)
{
await _db.ChipVirgemLines.AddRangeAsync(buffer);
await _db.SaveChangesAsync();
}
}
// ==========================================================
// ✅ IMPORTAÇÃO CONTROLE DE RECEBIDOS (2022-2025)
// ==========================================================
private async Task ImportControleRecebidosFromWorkbook(XLWorkbook wb)
{
await _db.ControleRecebidoLines.ExecuteDeleteAsync();
var years = new[] { 2022, 2023, 2024, 2025 };
foreach (var year in years)
{
var ws = FindControleRecebidosWorksheet(wb, year);
if (ws == null) continue;
await ImportControleRecebidosSheet(ws, year);
}
}
private async Task ImportControleRecebidosSheet(IXLWorksheet ws, int year)
{
var buffer = new List<ControleRecebidoLine>(500);
var firstRow = ws.FirstRowUsed()?.RowNumber() ?? 1;
var lastRow = ws.LastRowUsed()?.RowNumber() ?? firstRow;
var rowIndex = firstRow;
while (rowIndex <= lastRow)
{
var row = ws.Row(rowIndex);
if (!IsControleRecebidosHeader(row))
{
rowIndex++;
continue;
}
var map = BuildHeaderMap(row);
int colItem = GetCol(map, "ITEM");
if (colItem == 0)
{
rowIndex++;
continue;
}
var isResumo = GetColAny(map, "QTD.", "QTD", "QUANTIDADE") > 0
&& GetColAny(map, "CHIP") == 0
&& GetColAny(map, "SERIAL") == 0;
rowIndex++;
for (; rowIndex <= lastRow; rowIndex++)
{
var currentRow = ws.Row(rowIndex);
if (IsControleRecebidosHeader(currentRow))
{
rowIndex--;
break;
}
var itemStr = GetCellString(ws, rowIndex, colItem);
if (string.IsNullOrWhiteSpace(itemStr)) break;
var notaFiscal = GetCellByHeaderAny(ws, rowIndex, map, "NOTA FISCAL", "NOTA", "NF");
var chip = NullIfEmptyDigits(GetCellByHeaderAny(ws, rowIndex, map, "CHIP"));
var serial = GetCellByHeaderAny(ws, rowIndex, map, "SERIAL");
var conteudo = GetCellByHeaderAny(ws, rowIndex, map, "CONTEÚDO DA NF", "CONTEUDO DA NF");
var numeroLinha = NullIfEmptyDigits(GetCellByHeaderAny(ws, rowIndex, map, "NÚMERO DA LINHA", "NUMERO DA LINHA"));
var valorUnit = TryDecimal(GetCellByHeaderAny(ws, rowIndex, map, "VALOR UNIT.", "VALOR UNIT", "VALOR UNITÁRIO", "VALOR UNITARIO"));
var valorDaNf = TryDecimal(GetCellByHeaderAny(ws, rowIndex, map, "VALOR DA NF", "VALOR DA N F"));
var dataDaNf = TryDate(ws, rowIndex, map, "DATA DA NF");
var dataReceb = TryDate(ws, rowIndex, map, "DATA DO RECEBIMENTO");
var qtd = TryNullableInt(GetCellByHeaderAny(ws, rowIndex, map, "QTD.", "QTD", "QUANTIDADE"));
var now = DateTime.UtcNow;
var e = new ControleRecebidoLine
{
Id = Guid.NewGuid(),
Ano = year,
Item = TryInt(itemStr),
NotaFiscal = string.IsNullOrWhiteSpace(notaFiscal) ? null : notaFiscal.Trim(),
Chip = chip,
Serial = string.IsNullOrWhiteSpace(serial) ? null : serial.Trim(),
ConteudoDaNf = string.IsNullOrWhiteSpace(conteudo) ? null : conteudo.Trim(),
NumeroDaLinha = numeroLinha,
ValorUnit = valorUnit,
ValorDaNf = valorDaNf,
DataDaNf = dataDaNf,
DataDoRecebimento = dataReceb,
Quantidade = qtd,
IsResumo = isResumo,
CreatedAt = now,
UpdatedAt = now
};
buffer.Add(e);
if (buffer.Count >= 500)
{
await _db.ControleRecebidoLines.AddRangeAsync(buffer);
await _db.SaveChangesAsync();
buffer.Clear();
}
}
rowIndex++;
}
if (buffer.Count > 0)
{
await _db.ControleRecebidoLines.AddRangeAsync(buffer);
await _db.SaveChangesAsync();
}
}
private static IXLWorksheet? FindControleRecebidosWorksheet(XLWorkbook wb, int year)
{
var normalizedName = NormalizeHeader($"CONTROLE DE RECEBIDOS {year}");
var ws = wb.Worksheets.FirstOrDefault(w => NormalizeHeader(w.Name) == normalizedName);
if (ws != null) return ws;
ws = wb.Worksheets.FirstOrDefault(w =>
{
var name = NormalizeHeader(w.Name);
return name.Contains("CONTROLE") && name.Contains("RECEBIDOS") && name.Contains(year.ToString());
});
if (ws != null) return ws;
if (year == 2024)
{
ws = wb.Worksheets.FirstOrDefault(w => NormalizeHeader(w.Name) == NormalizeHeader("CONTROLE DE RECEBIDOS"));
}
return ws;
}
private static bool IsControleRecebidosHeader(IXLRow row)
{
var hasItem = false;
var hasNota = false;
foreach (var cell in row.CellsUsed())
{
var k = NormalizeHeader(cell.GetString());
if (k == "ITEM") hasItem = true;
if (k == "NOTAFISCAL") hasNota = true;
if (hasItem && hasNota) return true;
}
return false;
}
// ========================================================== // ==========================================================
// HELPERS (SEUS) // HELPERS (SEUS)
// ========================================================== // ==========================================================

View File

@ -35,6 +35,12 @@ public class AppDbContext : IdentityDbContext<ApplicationUser, IdentityRole<Guid
// ✅ tabela TROCA DE NÚMERO // ✅ tabela TROCA DE NÚMERO
public DbSet<TrocaNumeroLine> TrocaNumeroLines => Set<TrocaNumeroLine>(); public DbSet<TrocaNumeroLine> TrocaNumeroLines => Set<TrocaNumeroLine>();
// ✅ tabela CHIPS VIRGENS
public DbSet<ChipVirgemLine> ChipVirgemLines => Set<ChipVirgemLine>();
// ✅ tabela CONTROLE DE RECEBIDOS
public DbSet<ControleRecebidoLine> ControleRecebidoLines => Set<ControleRecebidoLine>();
// ✅ tabela NOTIFICAÇÕES // ✅ tabela NOTIFICAÇÕES
public DbSet<Notification> Notifications => Set<Notification>(); public DbSet<Notification> Notifications => Set<Notification>();
@ -147,6 +153,32 @@ public class AppDbContext : IdentityDbContext<ApplicationUser, IdentityRole<Guid
e.HasIndex(x => x.TenantId); e.HasIndex(x => x.TenantId);
}); });
// =========================
// ✅ CHIPS VIRGENS
// =========================
modelBuilder.Entity<ChipVirgemLine>(e =>
{
e.HasIndex(x => x.Item);
e.HasIndex(x => x.NumeroDoChip);
e.HasIndex(x => x.TenantId);
});
// =========================
// ✅ CONTROLE DE RECEBIDOS
// =========================
modelBuilder.Entity<ControleRecebidoLine>(e =>
{
e.HasIndex(x => x.Ano);
e.HasIndex(x => x.Item);
e.HasIndex(x => x.NotaFiscal);
e.HasIndex(x => x.Chip);
e.HasIndex(x => x.Serial);
e.HasIndex(x => x.NumeroDaLinha);
e.HasIndex(x => x.DataDaNf);
e.HasIndex(x => x.DataDoRecebimento);
e.HasIndex(x => x.TenantId);
});
// ========================= // =========================
// ✅ NOTIFICAÇÕES // ✅ NOTIFICAÇÕES
// ========================= // =========================
@ -177,6 +209,8 @@ public class AppDbContext : IdentityDbContext<ApplicationUser, IdentityRole<Guid
modelBuilder.Entity<UserData>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId); modelBuilder.Entity<UserData>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId);
modelBuilder.Entity<VigenciaLine>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId); modelBuilder.Entity<VigenciaLine>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId);
modelBuilder.Entity<TrocaNumeroLine>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId); modelBuilder.Entity<TrocaNumeroLine>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId);
modelBuilder.Entity<ChipVirgemLine>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId);
modelBuilder.Entity<ControleRecebidoLine>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId);
modelBuilder.Entity<Notification>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId); modelBuilder.Entity<Notification>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId);
modelBuilder.Entity<ApplicationUser>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId); modelBuilder.Entity<ApplicationUser>().HasQueryFilter(x => _tenantProvider.TenantId != null && x.TenantId == _tenantProvider.TenantId);
} }

29
Dtos/ChipsVirgensDtos.cs Normal file
View File

@ -0,0 +1,29 @@
using System;
namespace line_gestao_api.Dtos
{
public class ChipVirgemListDto
{
public Guid Id { get; set; }
public int Item { get; set; }
public string? NumeroDoChip { get; set; }
public string? Observacoes { get; set; }
}
public class ChipVirgemDetailDto : ChipVirgemListDto
{
public DateTime CreatedAt { get; set; }
public DateTime UpdatedAt { get; set; }
}
public class CreateChipVirgemDto
{
public int? Item { get; set; }
public string? NumeroDoChip { get; set; }
public string? Observacoes { get; set; }
}
public class UpdateChipVirgemRequest : CreateChipVirgemDto
{
}
}

View File

@ -0,0 +1,49 @@
using System;
namespace line_gestao_api.Dtos
{
public class ControleRecebidoListDto
{
public Guid Id { get; set; }
public int Ano { get; set; }
public int Item { get; set; }
public string? NotaFiscal { get; set; }
public string? Chip { get; set; }
public string? Serial { get; set; }
public string? ConteudoDaNf { get; set; }
public string? NumeroDaLinha { get; set; }
public decimal? ValorUnit { get; set; }
public decimal? ValorDaNf { get; set; }
public DateTime? DataDaNf { get; set; }
public DateTime? DataDoRecebimento { get; set; }
public int? Quantidade { get; set; }
public bool IsResumo { get; set; }
}
public class ControleRecebidoDetailDto : ControleRecebidoListDto
{
public DateTime CreatedAt { get; set; }
public DateTime UpdatedAt { get; set; }
}
public class CreateControleRecebidoDto
{
public int? Ano { get; set; }
public int? Item { get; set; }
public string? NotaFiscal { get; set; }
public string? Chip { get; set; }
public string? Serial { get; set; }
public string? ConteudoDaNf { get; set; }
public string? NumeroDaLinha { get; set; }
public decimal? ValorUnit { get; set; }
public decimal? ValorDaNf { get; set; }
public DateTime? DataDaNf { get; set; }
public DateTime? DataDoRecebimento { get; set; }
public int? Quantidade { get; set; }
public bool? IsResumo { get; set; }
}
public class UpdateControleRecebidoRequest : CreateControleRecebidoDto
{
}
}

View File

@ -0,0 +1,963 @@
// <auto-generated />
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
using Npgsql.EntityFrameworkCore.PostgreSQL.Metadata;
using line_gestao_api.Data;
#nullable disable
namespace line_gestao_api.Migrations
{
[DbContext(typeof(AppDbContext))]
[Migration("20260211120000_AddChipsVirgensControleRecebidos")]
partial class AddChipsVirgensControleRecebidos
{
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
#pragma warning disable 612, 618
modelBuilder
.HasAnnotation("ProductVersion", "10.0.1")
.HasAnnotation("Relational:MaxIdentifierLength", 63);
NpgsqlModelBuilderExtensions.UseIdentityByDefaultColumns(modelBuilder);
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityRole<System.Guid>", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<string>("ConcurrencyStamp")
.IsConcurrencyToken()
.HasColumnType("text");
b.Property<string>("Name")
.HasMaxLength(256)
.HasColumnType("character varying(256)");
b.Property<string>("NormalizedName")
.HasMaxLength(256)
.HasColumnType("character varying(256)");
b.HasKey("Id");
b.HasIndex("NormalizedName")
.IsUnique()
.HasDatabaseName("RoleNameIndex");
b.ToTable("AspNetRoles", (string)null);
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityRoleClaim<System.Guid>", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("integer");
NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property<int>("Id"));
b.Property<string>("ClaimType")
.HasColumnType("text");
b.Property<string>("ClaimValue")
.HasColumnType("text");
b.Property<Guid>("RoleId")
.HasColumnType("uuid");
b.HasKey("Id");
b.HasIndex("RoleId");
b.ToTable("AspNetRoleClaims", (string)null);
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserClaim<System.Guid>", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("integer");
NpgsqlPropertyBuilderExtensions.UseIdentityByDefaultColumn(b.Property<int>("Id"));
b.Property<string>("ClaimType")
.HasColumnType("text");
b.Property<string>("ClaimValue")
.HasColumnType("text");
b.Property<Guid>("UserId")
.HasColumnType("uuid");
b.HasKey("Id");
b.HasIndex("UserId");
b.ToTable("AspNetUserClaims", (string)null);
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserLogin<System.Guid>", b =>
{
b.Property<string>("LoginProvider")
.HasColumnType("text");
b.Property<string>("ProviderKey")
.HasColumnType("text");
b.Property<string>("ProviderDisplayName")
.HasColumnType("text");
b.Property<Guid>("UserId")
.HasColumnType("uuid");
b.HasKey("LoginProvider", "ProviderKey");
b.HasIndex("UserId");
b.ToTable("AspNetUserLogins", (string)null);
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserRole<System.Guid>", b =>
{
b.Property<Guid>("UserId")
.HasColumnType("uuid");
b.Property<Guid>("RoleId")
.HasColumnType("uuid");
b.HasKey("UserId", "RoleId");
b.HasIndex("RoleId");
b.ToTable("AspNetUserRoles", (string)null);
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserToken<System.Guid>", b =>
{
b.Property<Guid>("UserId")
.HasColumnType("uuid");
b.Property<string>("LoginProvider")
.HasColumnType("text");
b.Property<string>("Name")
.HasColumnType("text");
b.Property<string>("Value")
.HasColumnType("text");
b.HasKey("UserId", "LoginProvider", "Name");
b.ToTable("AspNetUserTokens", (string)null);
});
modelBuilder.Entity("line_gestao_api.Models.ApplicationUser", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<int>("AccessFailedCount")
.HasColumnType("integer");
b.Property<string>("ConcurrencyStamp")
.IsConcurrencyToken()
.HasColumnType("text");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<string>("Email")
.HasMaxLength(256)
.HasColumnType("character varying(256)");
b.Property<bool>("EmailConfirmed")
.HasColumnType("boolean");
b.Property<bool>("IsActive")
.HasColumnType("boolean");
b.Property<bool>("LockoutEnabled")
.HasColumnType("boolean");
b.Property<DateTimeOffset?>("LockoutEnd")
.HasColumnType("timestamp with time zone");
b.Property<string>("Name")
.IsRequired()
.HasMaxLength(120)
.HasColumnType("character varying(120)");
b.Property<string>("NormalizedEmail")
.HasMaxLength(256)
.HasColumnType("character varying(256)");
b.Property<string>("NormalizedUserName")
.HasMaxLength(256)
.HasColumnType("character varying(256)");
b.Property<string>("PasswordHash")
.HasColumnType("text");
b.Property<string>("PhoneNumber")
.HasColumnType("text");
b.Property<bool>("PhoneNumberConfirmed")
.HasColumnType("boolean");
b.Property<string>("SecurityStamp")
.HasColumnType("text");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<bool>("TwoFactorEnabled")
.HasColumnType("boolean");
b.Property<string>("UserName")
.HasMaxLength(256)
.HasColumnType("character varying(256)");
b.HasKey("Id");
b.HasIndex("NormalizedEmail")
.HasDatabaseName("EmailIndex");
b.HasIndex("NormalizedUserName")
.IsUnique()
.HasDatabaseName("UserNameIndex");
b.HasIndex("TenantId", "NormalizedEmail")
.IsUnique();
b.ToTable("AspNetUsers", (string)null);
});
modelBuilder.Entity("line_gestao_api.Models.BillingClient", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<string>("Aparelho")
.HasColumnType("text");
b.Property<string>("Cliente")
.IsRequired()
.HasMaxLength(255)
.HasColumnType("character varying(255)");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<string>("FormaPagamento")
.HasColumnType("text");
b.Property<decimal?>("FranquiaLine")
.HasColumnType("numeric");
b.Property<decimal?>("FranquiaVivo")
.HasColumnType("numeric");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<decimal?>("Lucro")
.HasColumnType("numeric");
b.Property<int?>("QtdLinhas")
.HasColumnType("integer");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<string>("Tipo")
.IsRequired()
.HasMaxLength(2)
.HasColumnType("character varying(2)");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.Property<decimal?>("ValorContratoLine")
.HasColumnType("numeric");
b.Property<decimal?>("ValorContratoVivo")
.HasColumnType("numeric");
b.HasKey("Id");
b.HasIndex("Cliente");
b.HasIndex("Item");
b.HasIndex("TenantId");
b.HasIndex("Tipo");
b.HasIndex("Tipo", "Cliente");
b.ToTable("billing_clients", (string)null);
});
modelBuilder.Entity("line_gestao_api.Models.MobileLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<string>("Cedente")
.HasMaxLength(150)
.HasColumnType("character varying(150)");
b.Property<string>("Chip")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<string>("Cliente")
.HasMaxLength(200)
.HasColumnType("character varying(200)");
b.Property<string>("Conta")
.HasMaxLength(80)
.HasColumnType("character varying(80)");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataBloqueio")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataEntregaCliente")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataEntregaOpera")
.HasColumnType("timestamp with time zone");
b.Property<decimal?>("Desconto")
.HasColumnType("numeric");
b.Property<decimal?>("FranquiaGestao")
.HasColumnType("numeric");
b.Property<decimal?>("FranquiaLine")
.HasColumnType("numeric");
b.Property<decimal?>("FranquiaVivo")
.HasColumnType("numeric");
b.Property<decimal?>("GestaoVozDados")
.HasColumnType("numeric");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("Linha")
.HasMaxLength(30)
.HasColumnType("character varying(30)");
b.Property<decimal?>("LocacaoAp")
.HasColumnType("numeric");
b.Property<decimal?>("Lucro")
.HasColumnType("numeric");
b.Property<string>("Modalidade")
.HasMaxLength(80)
.HasColumnType("character varying(80)");
b.Property<string>("PlanoContrato")
.HasMaxLength(200)
.HasColumnType("character varying(200)");
b.Property<decimal?>("Skeelo")
.HasColumnType("numeric");
b.Property<string>("Skil")
.HasMaxLength(80)
.HasColumnType("character varying(80)");
b.Property<string>("Solicitante")
.HasMaxLength(150)
.HasColumnType("character varying(150)");
b.Property<string>("Status")
.HasMaxLength(80)
.HasColumnType("character varying(80)");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.Property<string>("Usuario")
.HasMaxLength(200)
.HasColumnType("character varying(200)");
b.Property<decimal?>("ValorContratoLine")
.HasColumnType("numeric");
b.Property<decimal?>("ValorContratoVivo")
.HasColumnType("numeric");
b.Property<decimal?>("ValorPlanoVivo")
.HasColumnType("numeric");
b.Property<string>("VencConta")
.HasMaxLength(50)
.HasColumnType("character varying(50)");
b.Property<decimal?>("VivoGestaoDispositivo")
.HasColumnType("numeric");
b.Property<decimal?>("VivoNewsPlus")
.HasColumnType("numeric");
b.Property<decimal?>("VivoTravelMundo")
.HasColumnType("numeric");
b.HasKey("Id");
b.HasIndex("Chip");
b.HasIndex("Cliente");
b.HasIndex("Skil");
b.HasIndex("Status");
b.HasIndex("Usuario");
b.HasIndex("TenantId", "Linha")
.IsUnique();
b.ToTable("MobileLines");
});
modelBuilder.Entity("line_gestao_api.Models.MuregLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataDaMureg")
.HasColumnType("timestamp with time zone");
b.Property<string>("ICCID")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("LinhaAntiga")
.HasMaxLength(30)
.HasColumnType("character varying(30)");
b.Property<string>("LinhaNova")
.HasMaxLength(30)
.HasColumnType("character varying(30)");
b.Property<Guid>("MobileLineId")
.HasColumnType("uuid");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.HasKey("Id");
b.HasIndex("ICCID");
b.HasIndex("Item");
b.HasIndex("LinhaAntiga");
b.HasIndex("LinhaNova");
b.HasIndex("MobileLineId");
b.HasIndex("TenantId");
b.ToTable("MuregLines");
});
modelBuilder.Entity("line_gestao_api.Models.Notification", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<string>("Cliente")
.HasColumnType("text");
b.Property<DateTime>("Data")
.HasColumnType("timestamp with time zone");
b.Property<string>("DedupKey")
.IsRequired()
.HasColumnType("text");
b.Property<int?>("DiasParaVencer")
.HasColumnType("integer");
b.Property<bool>("Lida")
.HasColumnType("boolean");
b.Property<DateTime?>("LidaEm")
.HasColumnType("timestamp with time zone");
b.Property<string>("Linha")
.HasColumnType("text");
b.Property<string>("Mensagem")
.IsRequired()
.HasColumnType("text");
b.Property<DateTime?>("ReferenciaData")
.HasColumnType("timestamp with time zone");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<string>("Tipo")
.IsRequired()
.HasColumnType("text");
b.Property<string>("Titulo")
.IsRequired()
.HasColumnType("text");
b.Property<Guid?>("UserId")
.HasColumnType("uuid");
b.Property<string>("Usuario")
.HasColumnType("text");
b.Property<Guid?>("VigenciaLineId")
.HasColumnType("uuid");
b.HasKey("Id");
b.HasIndex("Cliente");
b.HasIndex("Data");
b.HasIndex("DedupKey")
.IsUnique();
b.HasIndex("Lida");
b.HasIndex("TenantId");
b.HasIndex("UserId");
b.HasIndex("VigenciaLineId");
b.ToTable("Notifications");
});
modelBuilder.Entity("line_gestao_api.Models.Tenant", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<string>("Name")
.IsRequired()
.HasColumnType("text");
b.HasKey("Id");
b.ToTable("Tenants");
});
modelBuilder.Entity("line_gestao_api.Models.ChipVirgemLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("NumeroDoChip")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<string>("Observacoes")
.HasMaxLength(500)
.HasColumnType("character varying(500)");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.HasKey("Id");
b.HasIndex("Item");
b.HasIndex("NumeroDoChip");
b.HasIndex("TenantId");
b.ToTable("ChipVirgemLines");
});
modelBuilder.Entity("line_gestao_api.Models.ControleRecebidoLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<int>("Ano")
.HasColumnType("integer");
b.Property<string>("Chip")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<string>("ConteudoDaNf")
.HasMaxLength(255)
.HasColumnType("character varying(255)");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataDaNf")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataDoRecebimento")
.HasColumnType("timestamp with time zone");
b.Property<bool>("IsResumo")
.HasColumnType("boolean");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("NotaFiscal")
.HasMaxLength(50)
.HasColumnType("character varying(50)");
b.Property<string>("NumeroDaLinha")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<int?>("Quantidade")
.HasColumnType("integer");
b.Property<string>("Serial")
.HasMaxLength(80)
.HasColumnType("character varying(80)");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.Property<decimal?>("ValorDaNf")
.HasColumnType("numeric");
b.Property<decimal?>("ValorUnit")
.HasColumnType("numeric");
b.HasKey("Id");
b.HasIndex("Ano");
b.HasIndex("Chip");
b.HasIndex("DataDaNf");
b.HasIndex("DataDoRecebimento");
b.HasIndex("Item");
b.HasIndex("NotaFiscal");
b.HasIndex("NumeroDaLinha");
b.HasIndex("Serial");
b.HasIndex("TenantId");
b.ToTable("ControleRecebidoLines");
});
modelBuilder.Entity("line_gestao_api.Models.TrocaNumeroLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataTroca")
.HasColumnType("timestamp with time zone");
b.Property<string>("ICCID")
.HasColumnType("text");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("LinhaAntiga")
.HasColumnType("text");
b.Property<string>("LinhaNova")
.HasColumnType("text");
b.Property<string>("Motivo")
.HasColumnType("text");
b.Property<string>("Observacao")
.HasColumnType("text");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.HasKey("Id");
b.HasIndex("DataTroca");
b.HasIndex("ICCID");
b.HasIndex("Item");
b.HasIndex("LinhaAntiga");
b.HasIndex("LinhaNova");
b.HasIndex("TenantId");
b.ToTable("TrocaNumeroLines");
});
modelBuilder.Entity("line_gestao_api.Models.UserData", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<string>("Celular")
.HasColumnType("text");
b.Property<string>("Cliente")
.HasColumnType("text");
b.Property<string>("Cpf")
.HasColumnType("text");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataNascimento")
.HasColumnType("timestamp with time zone");
b.Property<string>("Email")
.HasColumnType("text");
b.Property<string>("Endereco")
.HasColumnType("text");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("Linha")
.HasColumnType("text");
b.Property<string>("Rg")
.HasColumnType("text");
b.Property<string>("TelefoneFixo")
.HasColumnType("text");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.HasKey("Id");
b.HasIndex("Cliente");
b.HasIndex("Cpf");
b.HasIndex("Email");
b.HasIndex("Item");
b.HasIndex("Linha");
b.HasIndex("TenantId");
b.ToTable("UserDatas");
});
modelBuilder.Entity("line_gestao_api.Models.VigenciaLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<string>("Cliente")
.HasColumnType("text");
b.Property<string>("Conta")
.HasColumnType("text");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DtEfetivacaoServico")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DtTerminoFidelizacao")
.HasColumnType("timestamp with time zone");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("Linha")
.HasColumnType("text");
b.Property<string>("PlanoContrato")
.HasColumnType("text");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<decimal?>("Total")
.HasColumnType("numeric");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.Property<string>("Usuario")
.HasColumnType("text");
b.HasKey("Id");
b.HasIndex("Cliente");
b.HasIndex("DtTerminoFidelizacao");
b.HasIndex("Item");
b.HasIndex("Linha");
b.HasIndex("TenantId");
b.ToTable("VigenciaLines");
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityRoleClaim<System.Guid>", b =>
{
b.HasOne("Microsoft.AspNetCore.Identity.IdentityRole<System.Guid>", null)
.WithMany()
.HasForeignKey("RoleId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserClaim<System.Guid>", b =>
{
b.HasOne("line_gestao_api.Models.ApplicationUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserLogin<System.Guid>", b =>
{
b.HasOne("line_gestao_api.Models.ApplicationUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserRole<System.Guid>", b =>
{
b.HasOne("Microsoft.AspNetCore.Identity.IdentityRole<System.Guid>", null)
.WithMany()
.HasForeignKey("RoleId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
b.HasOne("line_gestao_api.Models.ApplicationUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});
modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserToken<System.Guid>", b =>
{
b.HasOne("line_gestao_api.Models.ApplicationUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});
modelBuilder.Entity("line_gestao_api.Models.MuregLine", b =>
{
b.HasOne("line_gestao_api.Models.MobileLine", "MobileLine")
.WithMany("Muregs")
.HasForeignKey("MobileLineId")
.OnDelete(DeleteBehavior.Restrict)
.IsRequired();
b.Navigation("MobileLine");
});
modelBuilder.Entity("line_gestao_api.Models.Notification", b =>
{
b.HasOne("line_gestao_api.Models.ApplicationUser", "User")
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Restrict);
b.HasOne("line_gestao_api.Models.VigenciaLine", "VigenciaLine")
.WithMany()
.HasForeignKey("VigenciaLineId")
.OnDelete(DeleteBehavior.Restrict);
b.Navigation("User");
b.Navigation("VigenciaLine");
});
modelBuilder.Entity("line_gestao_api.Models.MobileLine", b =>
{
b.Navigation("Muregs");
});
#pragma warning restore 612, 618
}
}
}

View File

@ -0,0 +1,129 @@
using System;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace line_gestao_api.Migrations
{
/// <inheritdoc />
public partial class AddChipsVirgensControleRecebidos : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "ChipVirgemLines",
columns: table => new
{
Id = table.Column<Guid>(type: "uuid", nullable: false),
TenantId = table.Column<Guid>(type: "uuid", nullable: false),
Item = table.Column<int>(type: "integer", nullable: false),
NumeroDoChip = table.Column<string>(type: "character varying(40)", maxLength: 40, nullable: true),
Observacoes = table.Column<string>(type: "character varying(500)", maxLength: 500, nullable: true),
CreatedAt = table.Column<DateTime>(type: "timestamp with time zone", nullable: false),
UpdatedAt = table.Column<DateTime>(type: "timestamp with time zone", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("PK_ChipVirgemLines", x => x.Id);
});
migrationBuilder.CreateTable(
name: "ControleRecebidoLines",
columns: table => new
{
Id = table.Column<Guid>(type: "uuid", nullable: false),
TenantId = table.Column<Guid>(type: "uuid", nullable: false),
Ano = table.Column<int>(type: "integer", nullable: false),
Item = table.Column<int>(type: "integer", nullable: false),
NotaFiscal = table.Column<string>(type: "character varying(50)", maxLength: 50, nullable: true),
Chip = table.Column<string>(type: "character varying(40)", maxLength: 40, nullable: true),
Serial = table.Column<string>(type: "character varying(80)", maxLength: 80, nullable: true),
ConteudoDaNf = table.Column<string>(type: "character varying(255)", maxLength: 255, nullable: true),
NumeroDaLinha = table.Column<string>(type: "character varying(40)", maxLength: 40, nullable: true),
ValorUnit = table.Column<decimal>(type: "numeric", nullable: true),
ValorDaNf = table.Column<decimal>(type: "numeric", nullable: true),
DataDaNf = table.Column<DateTime>(type: "timestamp with time zone", nullable: true),
DataDoRecebimento = table.Column<DateTime>(type: "timestamp with time zone", nullable: true),
Quantidade = table.Column<int>(type: "integer", nullable: true),
IsResumo = table.Column<bool>(type: "boolean", nullable: false),
CreatedAt = table.Column<DateTime>(type: "timestamp with time zone", nullable: false),
UpdatedAt = table.Column<DateTime>(type: "timestamp with time zone", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("PK_ControleRecebidoLines", x => x.Id);
});
migrationBuilder.CreateIndex(
name: "IX_ChipVirgemLines_Item",
table: "ChipVirgemLines",
column: "Item");
migrationBuilder.CreateIndex(
name: "IX_ChipVirgemLines_NumeroDoChip",
table: "ChipVirgemLines",
column: "NumeroDoChip");
migrationBuilder.CreateIndex(
name: "IX_ChipVirgemLines_TenantId",
table: "ChipVirgemLines",
column: "TenantId");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_Ano",
table: "ControleRecebidoLines",
column: "Ano");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_Chip",
table: "ControleRecebidoLines",
column: "Chip");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_DataDaNf",
table: "ControleRecebidoLines",
column: "DataDaNf");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_DataDoRecebimento",
table: "ControleRecebidoLines",
column: "DataDoRecebimento");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_Item",
table: "ControleRecebidoLines",
column: "Item");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_NotaFiscal",
table: "ControleRecebidoLines",
column: "NotaFiscal");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_NumeroDaLinha",
table: "ControleRecebidoLines",
column: "NumeroDaLinha");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_Serial",
table: "ControleRecebidoLines",
column: "Serial");
migrationBuilder.CreateIndex(
name: "IX_ControleRecebidoLines_TenantId",
table: "ControleRecebidoLines",
column: "TenantId");
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "ChipVirgemLines");
migrationBuilder.DropTable(
name: "ControleRecebidoLines");
}
}
}

View File

@ -582,6 +582,125 @@ namespace line_gestao_api.Migrations
b.ToTable("Tenants"); b.ToTable("Tenants");
}); });
modelBuilder.Entity("line_gestao_api.Models.ChipVirgemLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("NumeroDoChip")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<string>("Observacoes")
.HasMaxLength(500)
.HasColumnType("character varying(500)");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.HasKey("Id");
b.HasIndex("Item");
b.HasIndex("NumeroDoChip");
b.HasIndex("TenantId");
b.ToTable("ChipVirgemLines");
});
modelBuilder.Entity("line_gestao_api.Models.ControleRecebidoLine", b =>
{
b.Property<Guid>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("uuid");
b.Property<int>("Ano")
.HasColumnType("integer");
b.Property<string>("Chip")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<string>("ConteudoDaNf")
.HasMaxLength(255)
.HasColumnType("character varying(255)");
b.Property<DateTime>("CreatedAt")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataDaNf")
.HasColumnType("timestamp with time zone");
b.Property<DateTime?>("DataDoRecebimento")
.HasColumnType("timestamp with time zone");
b.Property<bool>("IsResumo")
.HasColumnType("boolean");
b.Property<int>("Item")
.HasColumnType("integer");
b.Property<string>("NotaFiscal")
.HasMaxLength(50)
.HasColumnType("character varying(50)");
b.Property<string>("NumeroDaLinha")
.HasMaxLength(40)
.HasColumnType("character varying(40)");
b.Property<int?>("Quantidade")
.HasColumnType("integer");
b.Property<string>("Serial")
.HasMaxLength(80)
.HasColumnType("character varying(80)");
b.Property<Guid>("TenantId")
.HasColumnType("uuid");
b.Property<DateTime>("UpdatedAt")
.HasColumnType("timestamp with time zone");
b.Property<decimal?>("ValorDaNf")
.HasColumnType("numeric");
b.Property<decimal?>("ValorUnit")
.HasColumnType("numeric");
b.HasKey("Id");
b.HasIndex("Ano");
b.HasIndex("Chip");
b.HasIndex("DataDaNf");
b.HasIndex("DataDoRecebimento");
b.HasIndex("Item");
b.HasIndex("NotaFiscal");
b.HasIndex("NumeroDaLinha");
b.HasIndex("Serial");
b.HasIndex("TenantId");
b.ToTable("ControleRecebidoLines");
});
modelBuilder.Entity("line_gestao_api.Models.TrocaNumeroLine", b => modelBuilder.Entity("line_gestao_api.Models.TrocaNumeroLine", b =>
{ {
b.Property<Guid>("Id") b.Property<Guid>("Id")

23
Models/ChipVirgemLine.cs Normal file
View File

@ -0,0 +1,23 @@
using System;
using System.ComponentModel.DataAnnotations;
namespace line_gestao_api.Models
{
public class ChipVirgemLine : ITenantEntity
{
public Guid Id { get; set; } = Guid.NewGuid();
public Guid TenantId { get; set; }
public int Item { get; set; }
[MaxLength(40)]
public string? NumeroDoChip { get; set; }
[MaxLength(500)]
public string? Observacoes { get; set; }
public DateTime CreatedAt { get; set; } = DateTime.UtcNow;
public DateTime UpdatedAt { get; set; } = DateTime.UtcNow;
}
}

View File

@ -0,0 +1,43 @@
using System;
using System.ComponentModel.DataAnnotations;
namespace line_gestao_api.Models
{
public class ControleRecebidoLine : ITenantEntity
{
public Guid Id { get; set; } = Guid.NewGuid();
public Guid TenantId { get; set; }
public int Ano { get; set; }
public int Item { get; set; }
[MaxLength(50)]
public string? NotaFiscal { get; set; }
[MaxLength(40)]
public string? Chip { get; set; }
[MaxLength(80)]
public string? Serial { get; set; }
[MaxLength(255)]
public string? ConteudoDaNf { get; set; }
[MaxLength(40)]
public string? NumeroDaLinha { get; set; }
public decimal? ValorUnit { get; set; }
public decimal? ValorDaNf { get; set; }
public DateTime? DataDaNf { get; set; }
public DateTime? DataDoRecebimento { get; set; }
public int? Quantidade { get; set; }
public bool IsResumo { get; set; }
public DateTime CreatedAt { get; set; } = DateTime.UtcNow;
public DateTime UpdatedAt { get; set; } = DateTime.UtcNow;
}
}