feat: Add CutList.Web Blazor Server application
Add a new web-based frontend for cut list optimization using: - Blazor Server with .NET 8 - Entity Framework Core with MSSQL LocalDB - Full CRUD for Materials, Suppliers, Projects, and Cutting Tools - Supplier stock length management for quick project setup - Integration with CutList.Core for bin packing optimization - Print-friendly HTML reports with efficiency statistics Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
124
CutList.Web/Data/ApplicationDbContext.cs
Normal file
124
CutList.Web/Data/ApplicationDbContext.cs
Normal file
@@ -0,0 +1,124 @@
|
||||
using CutList.Web.Data.Entities;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
|
||||
namespace CutList.Web.Data;
|
||||
|
||||
public class ApplicationDbContext : DbContext
|
||||
{
|
||||
public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
|
||||
: base(options)
|
||||
{
|
||||
}
|
||||
|
||||
public DbSet<Material> Materials => Set<Material>();
|
||||
public DbSet<Supplier> Suppliers => Set<Supplier>();
|
||||
public DbSet<SupplierStock> SupplierStocks => Set<SupplierStock>();
|
||||
public DbSet<CuttingTool> CuttingTools => Set<CuttingTool>();
|
||||
public DbSet<Project> Projects => Set<Project>();
|
||||
public DbSet<ProjectPart> ProjectParts => Set<ProjectPart>();
|
||||
public DbSet<ProjectStockBin> ProjectStockBins => Set<ProjectStockBin>();
|
||||
|
||||
protected override void OnModelCreating(ModelBuilder modelBuilder)
|
||||
{
|
||||
base.OnModelCreating(modelBuilder);
|
||||
|
||||
// Material
|
||||
modelBuilder.Entity<Material>(entity =>
|
||||
{
|
||||
entity.HasKey(e => e.Id);
|
||||
entity.Property(e => e.Shape).HasMaxLength(50).IsRequired();
|
||||
entity.Property(e => e.Size).HasMaxLength(100).IsRequired();
|
||||
entity.Property(e => e.Description).HasMaxLength(255);
|
||||
entity.Property(e => e.CreatedAt).HasDefaultValueSql("GETUTCDATE()");
|
||||
});
|
||||
|
||||
// Supplier
|
||||
modelBuilder.Entity<Supplier>(entity =>
|
||||
{
|
||||
entity.HasKey(e => e.Id);
|
||||
entity.Property(e => e.Name).HasMaxLength(100).IsRequired();
|
||||
entity.Property(e => e.ContactInfo).HasMaxLength(500);
|
||||
entity.Property(e => e.CreatedAt).HasDefaultValueSql("GETUTCDATE()");
|
||||
});
|
||||
|
||||
// SupplierStock
|
||||
modelBuilder.Entity<SupplierStock>(entity =>
|
||||
{
|
||||
entity.HasKey(e => e.Id);
|
||||
entity.Property(e => e.LengthInches).HasPrecision(10, 4);
|
||||
entity.Property(e => e.Price).HasPrecision(10, 2);
|
||||
entity.Property(e => e.Notes).HasMaxLength(255);
|
||||
|
||||
entity.HasOne(e => e.Supplier)
|
||||
.WithMany(s => s.Stocks)
|
||||
.HasForeignKey(e => e.SupplierId)
|
||||
.OnDelete(DeleteBehavior.Cascade);
|
||||
|
||||
entity.HasOne(e => e.Material)
|
||||
.WithMany(m => m.SupplierStocks)
|
||||
.HasForeignKey(e => e.MaterialId)
|
||||
.OnDelete(DeleteBehavior.Cascade);
|
||||
|
||||
entity.HasIndex(e => new { e.SupplierId, e.MaterialId, e.LengthInches }).IsUnique();
|
||||
});
|
||||
|
||||
// CuttingTool
|
||||
modelBuilder.Entity<CuttingTool>(entity =>
|
||||
{
|
||||
entity.HasKey(e => e.Id);
|
||||
entity.Property(e => e.Name).HasMaxLength(50).IsRequired();
|
||||
entity.Property(e => e.KerfInches).HasPrecision(6, 4);
|
||||
});
|
||||
|
||||
// Project
|
||||
modelBuilder.Entity<Project>(entity =>
|
||||
{
|
||||
entity.HasKey(e => e.Id);
|
||||
entity.Property(e => e.Name).HasMaxLength(100).IsRequired();
|
||||
entity.Property(e => e.CreatedAt).HasDefaultValueSql("GETUTCDATE()");
|
||||
|
||||
entity.HasOne(e => e.Material)
|
||||
.WithMany(m => m.Projects)
|
||||
.HasForeignKey(e => e.MaterialId)
|
||||
.OnDelete(DeleteBehavior.SetNull);
|
||||
|
||||
entity.HasOne(e => e.CuttingTool)
|
||||
.WithMany(t => t.Projects)
|
||||
.HasForeignKey(e => e.CuttingToolId)
|
||||
.OnDelete(DeleteBehavior.SetNull);
|
||||
});
|
||||
|
||||
// ProjectPart
|
||||
modelBuilder.Entity<ProjectPart>(entity =>
|
||||
{
|
||||
entity.HasKey(e => e.Id);
|
||||
entity.Property(e => e.Name).HasMaxLength(100).IsRequired();
|
||||
entity.Property(e => e.LengthInches).HasPrecision(10, 4);
|
||||
|
||||
entity.HasOne(e => e.Project)
|
||||
.WithMany(p => p.Parts)
|
||||
.HasForeignKey(e => e.ProjectId)
|
||||
.OnDelete(DeleteBehavior.Cascade);
|
||||
});
|
||||
|
||||
// ProjectStockBin
|
||||
modelBuilder.Entity<ProjectStockBin>(entity =>
|
||||
{
|
||||
entity.HasKey(e => e.Id);
|
||||
entity.Property(e => e.LengthInches).HasPrecision(10, 4);
|
||||
|
||||
entity.HasOne(e => e.Project)
|
||||
.WithMany(p => p.StockBins)
|
||||
.HasForeignKey(e => e.ProjectId)
|
||||
.OnDelete(DeleteBehavior.Cascade);
|
||||
});
|
||||
|
||||
// Seed default cutting tools
|
||||
modelBuilder.Entity<CuttingTool>().HasData(
|
||||
new CuttingTool { Id = 1, Name = "Bandsaw", KerfInches = 0.0625m, IsDefault = true, IsActive = true },
|
||||
new CuttingTool { Id = 2, Name = "Chop Saw", KerfInches = 0.125m, IsDefault = false, IsActive = true },
|
||||
new CuttingTool { Id = 3, Name = "Cold Cut Saw", KerfInches = 0.0625m, IsDefault = false, IsActive = true },
|
||||
new CuttingTool { Id = 4, Name = "Hacksaw", KerfInches = 0.0625m, IsDefault = false, IsActive = true }
|
||||
);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user