1009 lines
38 KiB
C#
1009 lines
38 KiB
C#
using Zentral.Domain.Entities;
|
|
using Zentral.Domain.Entities.Warehouse;
|
|
using Zentral.Domain.Entities.Purchases;
|
|
using Zentral.Domain.Entities.Sales;
|
|
using Zentral.Domain.Entities.Production;
|
|
using Zentral.Domain.Entities.HR;
|
|
using Zentral.Domain.Entities.Communications;
|
|
using Microsoft.EntityFrameworkCore;
|
|
|
|
namespace Zentral.Infrastructure.Data;
|
|
|
|
public class ZentralDbContext : DbContext
|
|
{
|
|
public ZentralDbContext(DbContextOptions<ZentralDbContext> options) : base(options)
|
|
{
|
|
}
|
|
|
|
public DbSet<Cliente> Clienti => Set<Cliente>();
|
|
public DbSet<Location> Location => Set<Location>();
|
|
public DbSet<Evento> Eventi => Set<Evento>();
|
|
public DbSet<TipoEvento> TipiEvento => Set<TipoEvento>();
|
|
public DbSet<TipoPasto> TipiPasto => Set<TipoPasto>();
|
|
public DbSet<TipoOspite> TipiOspite => Set<TipoOspite>();
|
|
public DbSet<TipoRisorsa> TipiRisorsa => Set<TipoRisorsa>();
|
|
public DbSet<TipoMateriale> TipiMateriale => Set<TipoMateriale>();
|
|
public DbSet<CodiceCategoria> CodiciCategoria => Set<CodiceCategoria>();
|
|
public DbSet<Risorsa> Risorse => Set<Risorsa>();
|
|
public DbSet<Articolo> Articoli => Set<Articolo>();
|
|
public DbSet<EventoDettaglioOspiti> EventiDettaglioOspiti => Set<EventoDettaglioOspiti>();
|
|
public DbSet<EventoDettaglioPrelievo> EventiDettaglioPrelievo => Set<EventoDettaglioPrelievo>();
|
|
public DbSet<EventoDettaglioRisorsa> EventiDettaglioRisorse => Set<EventoDettaglioRisorsa>();
|
|
public DbSet<EventoAcconto> EventiAcconti => Set<EventoAcconto>();
|
|
public DbSet<EventoAltroCosto> EventiAltriCosti => Set<EventoAltroCosto>();
|
|
public DbSet<EventoAllegato> EventiAllegati => Set<EventoAllegato>();
|
|
public DbSet<EventoDegustazione> EventiDegustazioni => Set<EventoDegustazione>();
|
|
public DbSet<Configurazione> Configurazioni => Set<Configurazione>();
|
|
public DbSet<Utente> Utenti => Set<Utente>();
|
|
public DbSet<UserDashboardPreference> UserDashboardPreferences => Set<UserDashboardPreference>();
|
|
|
|
// Report entities
|
|
public DbSet<ReportTemplate> ReportTemplates => Set<ReportTemplate>();
|
|
public DbSet<ReportFont> ReportFonts => Set<ReportFont>();
|
|
public DbSet<ReportImage> ReportImages => Set<ReportImage>();
|
|
public DbSet<VirtualDataset> VirtualDatasets => Set<VirtualDataset>();
|
|
|
|
// App system entities
|
|
public DbSet<App> Apps => Set<App>();
|
|
public DbSet<AppSubscription> AppSubscriptions => Set<AppSubscription>();
|
|
|
|
// Auto Code system
|
|
public DbSet<AutoCode> AutoCodes => Set<AutoCode>();
|
|
|
|
// Custom Fields system
|
|
public DbSet<CustomFieldDefinition> CustomFieldDefinitions => Set<CustomFieldDefinition>();
|
|
|
|
// Warehouse module entities
|
|
public DbSet<WarehouseLocation> WarehouseLocations => Set<WarehouseLocation>();
|
|
public DbSet<WarehouseArticle> WarehouseArticles => Set<WarehouseArticle>();
|
|
public DbSet<WarehouseArticleCategory> WarehouseArticleCategories => Set<WarehouseArticleCategory>();
|
|
public DbSet<ArticleBatch> ArticleBatches => Set<ArticleBatch>();
|
|
public DbSet<ArticleSerial> ArticleSerials => Set<ArticleSerial>();
|
|
public DbSet<ArticleBarcode> ArticleBarcodes => Set<ArticleBarcode>();
|
|
public DbSet<StockLevel> StockLevels => Set<StockLevel>();
|
|
public DbSet<StockMovement> StockMovements => Set<StockMovement>();
|
|
public DbSet<StockMovementLine> StockMovementLines => Set<StockMovementLine>();
|
|
public DbSet<MovementReason> MovementReasons => Set<MovementReason>();
|
|
public DbSet<StockValuation> StockValuations => Set<StockValuation>();
|
|
public DbSet<StockValuationLayer> StockValuationLayers => Set<StockValuationLayer>();
|
|
public DbSet<InventoryCount> InventoryCounts => Set<InventoryCount>();
|
|
public DbSet<InventoryCountLine> InventoryCountLines => Set<InventoryCountLine>();
|
|
|
|
// Purchases module entities
|
|
public DbSet<Supplier> Suppliers => Set<Supplier>();
|
|
public DbSet<PurchaseOrder> PurchaseOrders => Set<PurchaseOrder>();
|
|
public DbSet<PurchaseOrderLine> PurchaseOrderLines => Set<PurchaseOrderLine>();
|
|
|
|
// Sales module entities
|
|
public DbSet<SalesOrder> SalesOrders => Set<SalesOrder>();
|
|
public DbSet<SalesOrderLine> SalesOrderLines => Set<SalesOrderLine>();
|
|
|
|
// Production module entities
|
|
public DbSet<BillOfMaterials> BillOfMaterials => Set<BillOfMaterials>();
|
|
public DbSet<BillOfMaterialsComponent> BillOfMaterialsComponents => Set<BillOfMaterialsComponent>();
|
|
public DbSet<ProductionOrder> ProductionOrders => Set<ProductionOrder>();
|
|
public DbSet<ProductionOrderComponent> ProductionOrderComponents => Set<ProductionOrderComponent>();
|
|
public DbSet<WorkCenter> WorkCenters => Set<WorkCenter>();
|
|
public DbSet<ProductionCycle> ProductionCycles => Set<ProductionCycle>();
|
|
public DbSet<ProductionCyclePhase> ProductionCyclePhases => Set<ProductionCyclePhase>();
|
|
public DbSet<ProductionOrderPhase> ProductionOrderPhases => Set<ProductionOrderPhase>();
|
|
public DbSet<MrpSuggestion> MrpSuggestions => Set<MrpSuggestion>();
|
|
|
|
// Personale module entities
|
|
public DbSet<Dipendente> Dipendenti => Set<Dipendente>();
|
|
public DbSet<Contratto> Contratti => Set<Contratto>();
|
|
public DbSet<Assenza> Assenze => Set<Assenza>();
|
|
public DbSet<Pagamento> Pagamenti => Set<Pagamento>();
|
|
public DbSet<Rimborso> Rimborsi => Set<Rimborso>();
|
|
|
|
// Communications module entities
|
|
public DbSet<EmailLog> EmailLogs => Set<EmailLog>();
|
|
|
|
protected override void OnModelCreating(ModelBuilder modelBuilder)
|
|
{
|
|
base.OnModelCreating(modelBuilder);
|
|
|
|
// ===============================================
|
|
// PERSONALE MODULE ENTITIES
|
|
// ===============================================
|
|
|
|
modelBuilder.Entity<Dipendente>(entity =>
|
|
{
|
|
entity.ToTable("Dipendenti");
|
|
entity.HasIndex(e => e.CodiceFiscale).IsUnique();
|
|
});
|
|
|
|
modelBuilder.Entity<Contratto>(entity =>
|
|
{
|
|
entity.ToTable("Contratti");
|
|
entity.Property(e => e.RetribuzioneLorda).HasPrecision(18, 2);
|
|
|
|
entity.HasOne(e => e.Dipendente)
|
|
.WithMany(d => d.Contratti)
|
|
.HasForeignKey(e => e.DipendenteId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
modelBuilder.Entity<Assenza>(entity =>
|
|
{
|
|
entity.ToTable("Assenze");
|
|
|
|
entity.HasOne(e => e.Dipendente)
|
|
.WithMany(d => d.Assenze)
|
|
.HasForeignKey(e => e.DipendenteId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
modelBuilder.Entity<Pagamento>(entity =>
|
|
{
|
|
entity.ToTable("Pagamenti");
|
|
entity.Property(e => e.ImportoNetto).HasPrecision(18, 2);
|
|
|
|
entity.HasOne(e => e.Dipendente)
|
|
.WithMany(d => d.Pagamenti)
|
|
.HasForeignKey(e => e.DipendenteId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
modelBuilder.Entity<Rimborso>(entity =>
|
|
{
|
|
entity.ToTable("Rimborsi");
|
|
entity.Property(e => e.Importo).HasPrecision(18, 2);
|
|
|
|
entity.HasOne(e => e.Dipendente)
|
|
.WithMany(d => d.Rimborsi)
|
|
.HasForeignKey(e => e.DipendenteId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// Cliente
|
|
modelBuilder.Entity<Cliente>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.RagioneSociale);
|
|
entity.HasIndex(e => e.PartitaIva);
|
|
});
|
|
|
|
// Location
|
|
modelBuilder.Entity<Location>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Nome);
|
|
});
|
|
|
|
// Evento
|
|
modelBuilder.Entity<Evento>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.DataEvento);
|
|
entity.HasIndex(e => e.Stato);
|
|
entity.HasIndex(e => e.Codice);
|
|
|
|
entity.HasOne(e => e.Cliente)
|
|
.WithMany(c => c.Eventi)
|
|
.HasForeignKey(e => e.ClienteId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.Location)
|
|
.WithMany(l => l.Eventi)
|
|
.HasForeignKey(e => e.LocationId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.TipoEvento)
|
|
.WithMany(t => t.Eventi)
|
|
.HasForeignKey(e => e.TipoEventoId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// TipoEvento
|
|
modelBuilder.Entity<TipoEvento>(entity =>
|
|
{
|
|
entity.HasOne(e => e.TipoPasto)
|
|
.WithMany(t => t.TipiEvento)
|
|
.HasForeignKey(e => e.TipoPastoId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// Articolo
|
|
modelBuilder.Entity<Articolo>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Codice).IsUnique();
|
|
|
|
entity.HasOne(e => e.TipoMateriale)
|
|
.WithMany(t => t.Articoli)
|
|
.HasForeignKey(e => e.TipoMaterialeId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.Categoria)
|
|
.WithMany(c => c.Articoli)
|
|
.HasForeignKey(e => e.CategoriaId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// Risorsa
|
|
modelBuilder.Entity<Risorsa>(entity =>
|
|
{
|
|
entity.HasOne(e => e.TipoRisorsa)
|
|
.WithMany(t => t.Risorse)
|
|
.HasForeignKey(e => e.TipoRisorsaId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// EventoDettaglioOspiti
|
|
modelBuilder.Entity<EventoDettaglioOspiti>(entity =>
|
|
{
|
|
entity.HasOne(e => e.Evento)
|
|
.WithMany(ev => ev.DettagliOspiti)
|
|
.HasForeignKey(e => e.EventoId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.TipoOspite)
|
|
.WithMany(t => t.DettagliOspiti)
|
|
.HasForeignKey(e => e.TipoOspiteId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// EventoDettaglioPrelievo
|
|
modelBuilder.Entity<EventoDettaglioPrelievo>(entity =>
|
|
{
|
|
entity.HasOne(e => e.Evento)
|
|
.WithMany(ev => ev.DettagliPrelievo)
|
|
.HasForeignKey(e => e.EventoId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Articolo)
|
|
.WithMany(a => a.DettagliPrelievo)
|
|
.HasForeignKey(e => e.ArticoloId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// EventoDettaglioRisorsa
|
|
modelBuilder.Entity<EventoDettaglioRisorsa>(entity =>
|
|
{
|
|
entity.HasOne(e => e.Evento)
|
|
.WithMany(ev => ev.DettagliRisorse)
|
|
.HasForeignKey(e => e.EventoId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Risorsa)
|
|
.WithMany(r => r.DettagliRisorse)
|
|
.HasForeignKey(e => e.RisorsaId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// EventoAcconto
|
|
modelBuilder.Entity<EventoAcconto>(entity =>
|
|
{
|
|
entity.HasOne(e => e.Evento)
|
|
.WithMany(ev => ev.Acconti)
|
|
.HasForeignKey(e => e.EventoId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// EventoAltroCosto
|
|
modelBuilder.Entity<EventoAltroCosto>(entity =>
|
|
{
|
|
entity.HasOne(e => e.Evento)
|
|
.WithMany(ev => ev.AltriCosti)
|
|
.HasForeignKey(e => e.EventoId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// EventoAllegato
|
|
modelBuilder.Entity<EventoAllegato>(entity =>
|
|
{
|
|
entity.HasOne(e => e.Evento)
|
|
.WithMany(ev => ev.Allegati)
|
|
.HasForeignKey(e => e.EventoId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// EventoDegustazione
|
|
modelBuilder.Entity<EventoDegustazione>(entity =>
|
|
{
|
|
entity.HasOne(e => e.Evento)
|
|
.WithMany(ev => ev.Degustazioni)
|
|
.HasForeignKey(e => e.EventoId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// Configurazione
|
|
modelBuilder.Entity<Configurazione>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Chiave).IsUnique();
|
|
});
|
|
|
|
// Utente
|
|
modelBuilder.Entity<Utente>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Username).IsUnique();
|
|
});
|
|
|
|
// UserDashboardPreference
|
|
modelBuilder.Entity<UserDashboardPreference>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.UtenteId).IsUnique();
|
|
entity.HasOne(e => e.Utente)
|
|
.WithOne()
|
|
.HasForeignKey<UserDashboardPreference>(e => e.UtenteId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// ReportTemplate
|
|
modelBuilder.Entity<ReportTemplate>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Nome);
|
|
entity.HasIndex(e => e.Categoria);
|
|
});
|
|
|
|
// ReportFont
|
|
modelBuilder.Entity<ReportFont>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.FontFamily);
|
|
});
|
|
|
|
// ReportImage
|
|
modelBuilder.Entity<ReportImage>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Categoria);
|
|
});
|
|
|
|
// VirtualDataset
|
|
modelBuilder.Entity<VirtualDataset>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Nome).IsUnique();
|
|
entity.HasIndex(e => e.Categoria);
|
|
});
|
|
|
|
// App
|
|
modelBuilder.Entity<App>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.SortOrder);
|
|
|
|
entity.Property(e => e.BasePrice)
|
|
.HasPrecision(18, 2);
|
|
|
|
entity.Property(e => e.MonthlyMultiplier)
|
|
.HasPrecision(5, 2);
|
|
});
|
|
|
|
// AppSubscription
|
|
modelBuilder.Entity<AppSubscription>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.AppId).IsUnique();
|
|
|
|
entity.Property(e => e.PaidPrice)
|
|
.HasPrecision(18, 2);
|
|
|
|
entity.HasOne(e => e.App)
|
|
.WithOne(m => m.Subscription)
|
|
.HasForeignKey<AppSubscription>(e => e.AppId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// AutoCode
|
|
modelBuilder.Entity<AutoCode>(entity =>
|
|
{
|
|
entity.HasIndex(e => e.EntityCode).IsUnique();
|
|
entity.HasIndex(e => e.ModuleCode);
|
|
});
|
|
|
|
// CustomFieldDefinition
|
|
modelBuilder.Entity<CustomFieldDefinition>(entity =>
|
|
{
|
|
entity.HasIndex(e => new { e.EntityName, e.FieldName }).IsUnique();
|
|
entity.HasIndex(e => e.EntityName);
|
|
});
|
|
|
|
// ===============================================
|
|
// WAREHOUSE MODULE ENTITIES
|
|
// ===============================================
|
|
|
|
// WarehouseLocation
|
|
modelBuilder.Entity<WarehouseLocation>(entity =>
|
|
{
|
|
entity.ToTable("WarehouseLocations");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.IsDefault);
|
|
entity.HasIndex(e => e.IsActive);
|
|
});
|
|
|
|
// WarehouseArticleCategory
|
|
modelBuilder.Entity<WarehouseArticleCategory>(entity =>
|
|
{
|
|
entity.ToTable("WarehouseArticleCategories");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.ParentCategoryId);
|
|
entity.HasIndex(e => e.FullPath);
|
|
|
|
entity.HasOne(e => e.ParentCategory)
|
|
.WithMany(c => c.ChildCategories)
|
|
.HasForeignKey(e => e.ParentCategoryId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// WarehouseArticle
|
|
modelBuilder.Entity<WarehouseArticle>(entity =>
|
|
{
|
|
entity.ToTable("WarehouseArticles");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.Barcode);
|
|
entity.HasIndex(e => e.CategoryId);
|
|
entity.HasIndex(e => e.IsActive);
|
|
|
|
entity.Property(e => e.StandardCost).HasPrecision(18, 4);
|
|
entity.Property(e => e.LastPurchaseCost).HasPrecision(18, 4);
|
|
entity.Property(e => e.WeightedAverageCost).HasPrecision(18, 4);
|
|
entity.Property(e => e.BaseSellingPrice).HasPrecision(18, 4);
|
|
entity.Property(e => e.MinimumStock).HasPrecision(18, 4);
|
|
entity.Property(e => e.MaximumStock).HasPrecision(18, 4);
|
|
entity.Property(e => e.ReorderPoint).HasPrecision(18, 4);
|
|
entity.Property(e => e.ReorderQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitConversionFactor).HasPrecision(18, 6);
|
|
entity.Property(e => e.Weight).HasPrecision(18, 4);
|
|
entity.Property(e => e.Volume).HasPrecision(18, 6);
|
|
|
|
entity.HasOne(e => e.Category)
|
|
.WithMany(c => c.Articles)
|
|
.HasForeignKey(e => e.CategoryId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// ArticleBatch
|
|
modelBuilder.Entity<ArticleBatch>(entity =>
|
|
{
|
|
entity.ToTable("ArticleBatches");
|
|
entity.HasIndex(e => new { e.ArticleId, e.BatchNumber }).IsUnique();
|
|
entity.HasIndex(e => e.ExpiryDate);
|
|
entity.HasIndex(e => e.Status);
|
|
|
|
entity.Property(e => e.UnitCost).HasPrecision(18, 4);
|
|
entity.Property(e => e.InitialQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.CurrentQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.ReservedQuantity).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany(a => a.Batches)
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// ArticleSerial
|
|
modelBuilder.Entity<ArticleSerial>(entity =>
|
|
{
|
|
entity.ToTable("ArticleSerials");
|
|
entity.HasIndex(e => new { e.ArticleId, e.SerialNumber }).IsUnique();
|
|
entity.HasIndex(e => e.Status);
|
|
entity.HasIndex(e => e.CurrentWarehouseId);
|
|
|
|
entity.Property(e => e.UnitCost).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany(a => a.Serials)
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Batch)
|
|
.WithMany(b => b.Serials)
|
|
.HasForeignKey(e => e.BatchId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.CurrentWarehouse)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.CurrentWarehouseId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// ArticleBarcode
|
|
modelBuilder.Entity<ArticleBarcode>(entity =>
|
|
{
|
|
entity.ToTable("ArticleBarcodes");
|
|
entity.HasIndex(e => e.Barcode).IsUnique();
|
|
entity.HasIndex(e => e.ArticleId);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany(a => a.Barcodes)
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// StockLevel
|
|
modelBuilder.Entity<StockLevel>(entity =>
|
|
{
|
|
entity.ToTable("StockLevels");
|
|
entity.HasIndex(e => new { e.ArticleId, e.WarehouseId, e.BatchId }).IsUnique();
|
|
entity.HasIndex(e => e.WarehouseId);
|
|
entity.HasIndex(e => e.LocationCode);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.ReservedQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.OnOrderQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.StockValue).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitCost).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany(a => a.StockLevels)
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Warehouse)
|
|
.WithMany(w => w.StockLevels)
|
|
.HasForeignKey(e => e.WarehouseId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Batch)
|
|
.WithMany(b => b.StockLevels)
|
|
.HasForeignKey(e => e.BatchId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// MovementReason
|
|
modelBuilder.Entity<MovementReason>(entity =>
|
|
{
|
|
entity.ToTable("MovementReasons");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.MovementType);
|
|
entity.HasIndex(e => e.IsActive);
|
|
});
|
|
|
|
// StockMovement
|
|
modelBuilder.Entity<StockMovement>(entity =>
|
|
{
|
|
entity.ToTable("StockMovements");
|
|
entity.HasIndex(e => e.DocumentNumber).IsUnique();
|
|
entity.HasIndex(e => e.MovementDate);
|
|
entity.HasIndex(e => e.Type);
|
|
entity.HasIndex(e => e.Status);
|
|
entity.HasIndex(e => e.ExternalReference);
|
|
|
|
entity.Property(e => e.TotalValue).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.SourceWarehouse)
|
|
.WithMany(w => w.SourceMovements)
|
|
.HasForeignKey(e => e.SourceWarehouseId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
|
|
entity.HasOne(e => e.DestinationWarehouse)
|
|
.WithMany(w => w.DestinationMovements)
|
|
.HasForeignKey(e => e.DestinationWarehouseId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
|
|
entity.HasOne(e => e.Reason)
|
|
.WithMany(r => r.Movements)
|
|
.HasForeignKey(e => e.ReasonId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// StockMovementLine
|
|
modelBuilder.Entity<StockMovementLine>(entity =>
|
|
{
|
|
entity.ToTable("StockMovementLines");
|
|
entity.HasIndex(e => new { e.MovementId, e.LineNumber }).IsUnique();
|
|
entity.HasIndex(e => e.ArticleId);
|
|
entity.HasIndex(e => e.BatchId);
|
|
entity.HasIndex(e => e.SerialId);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitCost).HasPrecision(18, 4);
|
|
entity.Property(e => e.LineValue).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Movement)
|
|
.WithMany(m => m.Lines)
|
|
.HasForeignKey(e => e.MovementId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany(a => a.MovementLines)
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
|
|
entity.HasOne(e => e.Batch)
|
|
.WithMany(b => b.MovementLines)
|
|
.HasForeignKey(e => e.BatchId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.Serial)
|
|
.WithMany(s => s.MovementLines)
|
|
.HasForeignKey(e => e.SerialId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// StockValuation
|
|
modelBuilder.Entity<StockValuation>(entity =>
|
|
{
|
|
entity.ToTable("StockValuations");
|
|
entity.HasIndex(e => new { e.Period, e.ArticleId, e.WarehouseId }).IsUnique();
|
|
entity.HasIndex(e => e.ValuationDate);
|
|
entity.HasIndex(e => e.IsClosed);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitCost).HasPrecision(18, 4);
|
|
entity.Property(e => e.TotalValue).HasPrecision(18, 4);
|
|
entity.Property(e => e.InboundQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.InboundValue).HasPrecision(18, 4);
|
|
entity.Property(e => e.OutboundQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.OutboundValue).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Warehouse)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WarehouseId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// StockValuationLayer
|
|
modelBuilder.Entity<StockValuationLayer>(entity =>
|
|
{
|
|
entity.ToTable("StockValuationLayers");
|
|
entity.HasIndex(e => new { e.ArticleId, e.WarehouseId, e.LayerDate });
|
|
entity.HasIndex(e => e.IsExhausted);
|
|
|
|
entity.Property(e => e.OriginalQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.RemainingQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitCost).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Warehouse)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WarehouseId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Batch)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.BatchId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.SourceMovement)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.SourceMovementId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// InventoryCount
|
|
modelBuilder.Entity<InventoryCount>(entity =>
|
|
{
|
|
entity.ToTable("InventoryCounts");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.InventoryDate);
|
|
entity.HasIndex(e => e.Status);
|
|
|
|
entity.Property(e => e.PositiveDifferenceValue).HasPrecision(18, 4);
|
|
entity.Property(e => e.NegativeDifferenceValue).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Warehouse)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WarehouseId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.Category)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.CategoryId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
|
|
entity.HasOne(e => e.AdjustmentMovement)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.AdjustmentMovementId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// InventoryCountLine
|
|
modelBuilder.Entity<InventoryCountLine>(entity =>
|
|
{
|
|
entity.ToTable("InventoryCountLines");
|
|
entity.HasIndex(e => new { e.InventoryCountId, e.ArticleId, e.WarehouseId, e.BatchId }).IsUnique();
|
|
entity.HasIndex(e => e.ArticleId);
|
|
|
|
entity.Property(e => e.TheoreticalQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.CountedQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.SecondCountQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitCost).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.InventoryCount)
|
|
.WithMany(i => i.Lines)
|
|
.HasForeignKey(e => e.InventoryCountId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
|
|
entity.HasOne(e => e.Warehouse)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WarehouseId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
|
|
entity.HasOne(e => e.Batch)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.BatchId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// ===============================================
|
|
// PURCHASES MODULE ENTITIES
|
|
// ===============================================
|
|
|
|
// Supplier
|
|
modelBuilder.Entity<Supplier>(entity =>
|
|
{
|
|
entity.ToTable("Suppliers");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.Name);
|
|
entity.HasIndex(e => e.VatNumber);
|
|
entity.HasIndex(e => e.IsActive);
|
|
});
|
|
|
|
// PurchaseOrder
|
|
modelBuilder.Entity<PurchaseOrder>(entity =>
|
|
{
|
|
entity.ToTable("PurchaseOrders");
|
|
entity.HasIndex(e => e.OrderNumber).IsUnique();
|
|
entity.HasIndex(e => e.OrderDate);
|
|
entity.HasIndex(e => e.SupplierId);
|
|
entity.HasIndex(e => e.Status);
|
|
|
|
entity.Property(e => e.TotalNet).HasPrecision(18, 4);
|
|
entity.Property(e => e.TotalTax).HasPrecision(18, 4);
|
|
entity.Property(e => e.TotalGross).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Supplier)
|
|
.WithMany(s => s.PurchaseOrders)
|
|
.HasForeignKey(e => e.SupplierId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
|
|
entity.HasOne(e => e.DestinationWarehouse)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.DestinationWarehouseId)
|
|
.OnDelete(DeleteBehavior.SetNull);
|
|
});
|
|
|
|
// PurchaseOrderLine
|
|
modelBuilder.Entity<PurchaseOrderLine>(entity =>
|
|
{
|
|
entity.ToTable("PurchaseOrderLines");
|
|
entity.HasIndex(e => e.PurchaseOrderId);
|
|
entity.HasIndex(e => e.WarehouseArticleId);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.ReceivedQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitPrice).HasPrecision(18, 4);
|
|
entity.Property(e => e.TaxRate).HasPrecision(18, 2);
|
|
entity.Property(e => e.DiscountPercent).HasPrecision(18, 2);
|
|
entity.Property(e => e.LineTotal).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.PurchaseOrder)
|
|
.WithMany(o => o.Lines)
|
|
.HasForeignKey(e => e.PurchaseOrderId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.WarehouseArticle)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WarehouseArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// ===============================================
|
|
// SALES MODULE ENTITIES
|
|
// ===============================================
|
|
|
|
// SalesOrder
|
|
modelBuilder.Entity<SalesOrder>(entity =>
|
|
{
|
|
entity.ToTable("SalesOrders");
|
|
entity.HasIndex(e => e.OrderNumber).IsUnique();
|
|
entity.HasIndex(e => e.OrderDate);
|
|
entity.HasIndex(e => e.CustomerId);
|
|
entity.HasIndex(e => e.Status);
|
|
|
|
entity.Property(e => e.TotalNet).HasPrecision(18, 4);
|
|
entity.Property(e => e.TotalTax).HasPrecision(18, 4);
|
|
entity.Property(e => e.TotalGross).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Customer)
|
|
.WithMany(c => c.SalesOrders)
|
|
.HasForeignKey(e => e.CustomerId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// SalesOrderLine
|
|
modelBuilder.Entity<SalesOrderLine>(entity =>
|
|
{
|
|
entity.ToTable("SalesOrderLines");
|
|
entity.HasIndex(e => e.SalesOrderId);
|
|
entity.HasIndex(e => e.WarehouseArticleId);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.ShippedQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.UnitPrice).HasPrecision(18, 4);
|
|
entity.Property(e => e.TaxRate).HasPrecision(18, 2);
|
|
entity.Property(e => e.DiscountPercent).HasPrecision(18, 2);
|
|
entity.Property(e => e.LineTotal).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.SalesOrder)
|
|
.WithMany(o => o.Lines)
|
|
.HasForeignKey(e => e.SalesOrderId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.WarehouseArticle)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WarehouseArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// ===============================================
|
|
// PRODUCTION MODULE ENTITIES
|
|
// ===============================================
|
|
|
|
// BillOfMaterials
|
|
modelBuilder.Entity<BillOfMaterials>(entity =>
|
|
{
|
|
entity.ToTable("BillOfMaterials");
|
|
entity.HasIndex(e => e.ArticleId);
|
|
entity.HasIndex(e => e.IsActive);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// BillOfMaterialsComponent
|
|
modelBuilder.Entity<BillOfMaterialsComponent>(entity =>
|
|
{
|
|
entity.ToTable("BillOfMaterialsComponents");
|
|
entity.HasIndex(e => e.BillOfMaterialsId);
|
|
entity.HasIndex(e => e.ComponentArticleId);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.ScrapPercentage).HasPrecision(18, 2);
|
|
|
|
entity.HasOne(e => e.BillOfMaterials)
|
|
.WithMany(b => b.Components)
|
|
.HasForeignKey(e => e.BillOfMaterialsId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.ComponentArticle)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ComponentArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// ProductionOrder
|
|
modelBuilder.Entity<ProductionOrder>(entity =>
|
|
{
|
|
entity.ToTable("ProductionOrders");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.ArticleId);
|
|
entity.HasIndex(e => e.Status);
|
|
entity.HasIndex(e => e.StartDate);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// ProductionOrderComponent
|
|
modelBuilder.Entity<ProductionOrderComponent>(entity =>
|
|
{
|
|
entity.ToTable("ProductionOrderComponents");
|
|
entity.HasIndex(e => e.ProductionOrderId);
|
|
entity.HasIndex(e => e.ArticleId);
|
|
|
|
entity.Property(e => e.RequiredQuantity).HasPrecision(18, 4);
|
|
entity.Property(e => e.ConsumedQuantity).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.ProductionOrder)
|
|
.WithMany(o => o.Components)
|
|
.HasForeignKey(e => e.ProductionOrderId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// WorkCenter
|
|
modelBuilder.Entity<WorkCenter>(entity =>
|
|
{
|
|
entity.ToTable("WorkCenters");
|
|
entity.HasIndex(e => e.Code).IsUnique();
|
|
entity.HasIndex(e => e.IsActive);
|
|
entity.Property(e => e.CostPerHour).HasPrecision(18, 4);
|
|
});
|
|
|
|
// ProductionCycle
|
|
modelBuilder.Entity<ProductionCycle>(entity =>
|
|
{
|
|
entity.ToTable("ProductionCycles");
|
|
entity.HasIndex(e => e.ArticleId);
|
|
entity.HasIndex(e => e.IsActive);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// ProductionCyclePhase
|
|
modelBuilder.Entity<ProductionCyclePhase>(entity =>
|
|
{
|
|
entity.ToTable("ProductionCyclePhases");
|
|
entity.HasIndex(e => e.ProductionCycleId);
|
|
entity.HasIndex(e => e.WorkCenterId);
|
|
|
|
entity.HasOne(e => e.ProductionCycle)
|
|
.WithMany(c => c.Phases)
|
|
.HasForeignKey(e => e.ProductionCycleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.WorkCenter)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WorkCenterId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// ProductionOrderPhase
|
|
modelBuilder.Entity<ProductionOrderPhase>(entity =>
|
|
{
|
|
entity.ToTable("ProductionOrderPhases");
|
|
entity.HasIndex(e => e.ProductionOrderId);
|
|
entity.HasIndex(e => e.WorkCenterId);
|
|
entity.HasIndex(e => e.Status);
|
|
|
|
entity.Property(e => e.QuantityCompleted).HasPrecision(18, 4);
|
|
entity.Property(e => e.QuantityScrapped).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.ProductionOrder)
|
|
.WithMany(o => o.Phases)
|
|
.HasForeignKey(e => e.ProductionOrderId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
|
|
entity.HasOne(e => e.WorkCenter)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.WorkCenterId)
|
|
.OnDelete(DeleteBehavior.Restrict);
|
|
});
|
|
|
|
// MrpSuggestion
|
|
modelBuilder.Entity<MrpSuggestion>(entity =>
|
|
{
|
|
entity.ToTable("MrpSuggestions");
|
|
entity.HasIndex(e => e.ArticleId);
|
|
entity.HasIndex(e => e.CalculationDate);
|
|
entity.HasIndex(e => e.IsProcessed);
|
|
|
|
entity.Property(e => e.Quantity).HasPrecision(18, 4);
|
|
|
|
entity.HasOne(e => e.Article)
|
|
.WithMany()
|
|
.HasForeignKey(e => e.ArticleId)
|
|
.OnDelete(DeleteBehavior.Cascade);
|
|
});
|
|
|
|
// ===============================================
|
|
// COMMUNICATIONS MODULE ENTITIES
|
|
// ===============================================
|
|
modelBuilder.Entity<EmailLog>(entity =>
|
|
{
|
|
entity.ToTable("EmailLogs");
|
|
entity.HasIndex(e => e.SentDate);
|
|
entity.HasIndex(e => e.Status);
|
|
entity.HasIndex(e => e.Recipient);
|
|
});
|
|
}
|
|
}
|