Skip to content

Commit

Permalink
Pl credit debit notes 2 (#125)
Browse files Browse the repository at this point in the history
* search/getbyid routes

* build rel self links, tests

* lookup page

* allow search by supplier id

* Note page

* wip

* get all the data we need to print the credit note

* remove un-needed AuthorisedAction

* render debit note

* delete temp file

* typo

* allow cancelling notes

* add new line to eof

* fix param name
  • Loading branch information
lewisrenfrew authored Mar 3, 2022
1 parent 610fde2 commit 1e46e45
Show file tree
Hide file tree
Showing 40 changed files with 984 additions and 91 deletions.
4 changes: 4 additions & 0 deletions src/Domain.LinnApps/AuthorisedAction.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,5 +17,9 @@ public class AuthorisedAction
public const string PurchaseOrderUpdate = "purchase-order.update";

public const string PlCreditDebitNoteClose = "purchasing.pl-debit-credit-note.close";

public const string PlCreditDebitNoteCancel = "purchasing.pl-debit-credit-note.close";

public const string PlCreditDebitNoteUpdate = "purchasing.pl-debit-credit-note.update";
}
}
13 changes: 12 additions & 1 deletion src/Domain.LinnApps/PurchaseOrders/IPlCreditDebitNoteService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,21 @@

public interface IPlCreditDebitNoteService
{
public PlCreditDebitNote CloseDebitNote(
public void CloseDebitNote(
PlCreditDebitNote toClose,
string reason,
int closedBy,
IEnumerable<string> privileges);

public void CancelDebitNote(
PlCreditDebitNote toCancel,
string reason,
int cancelledBy,
IEnumerable<string> privileges);

public void UpdatePlCreditDebitNote(
PlCreditDebitNote current,
PlCreditDebitNote updated,
IEnumerable<string> privileges);
}
}
28 changes: 24 additions & 4 deletions src/Domain.LinnApps/PurchaseOrders/PlCreditDebitNote.cs
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,20 @@ public class PlCreditDebitNote

public int OrderQty { get; set; }

public int? OriginalOrderNumber { get; set; }

public int? ReturnsOrderNumber { get; set; }

public int? ReturnsOrderLine { get; set; }

public decimal NetTotal { get; set; }

public decimal Total { get; set; }

public decimal OrderUnitPrice { get; set; }

public string OrderUnitOfMeasure { get; set; }

public decimal VatTotal { get; set; }

public string Notes { get; set; }

public DateTime? DateClosed { get; set; }
Expand All @@ -30,8 +38,20 @@ public class PlCreditDebitNote

public string ReasonClosed { get; set; }

public int? SupplierId { get; set; }

public Supplier Supplier { get; set; }

public string SuppliersDesignation { get; set; }

public PurchaseOrder PurchaseOrder { get; set; }

public Currency Currency { get; set; }

public decimal? VatRate { get; set; }

public int? CancelledBy { get; set; }

public DateTime? DateCancelled { get; set; }

public string ReasonCancelled { get; set; }
}
}
25 changes: 23 additions & 2 deletions src/Domain.LinnApps/PurchaseOrders/PlCreditDebitNoteService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ public PlCreditDebitNoteService(IAuthorisationService authService)
this.authService = authService;
}

public PlCreditDebitNote CloseDebitNote(
public void CloseDebitNote(
PlCreditDebitNote toClose,
string reason,
int closedBy,
Expand All @@ -29,7 +29,28 @@ public PlCreditDebitNote CloseDebitNote(
toClose.DateClosed = DateTime.Today;
toClose.ReasonClosed = reason;
toClose.ClosedBy = closedBy;
return toClose;
}

public void CancelDebitNote(PlCreditDebitNote toCancel, string reason, int cancelledBy, IEnumerable<string> privileges)
{
if (!this.authService.HasPermissionFor(AuthorisedAction.PlCreditDebitNoteCancel, privileges))
{
throw new UnauthorisedActionException("You are not authorised to cancel debit notes");
}

toCancel.DateCancelled = DateTime.Today;
toCancel.ReasonCancelled = reason;
toCancel.CancelledBy = cancelledBy;
}

public void UpdatePlCreditDebitNote(PlCreditDebitNote current, PlCreditDebitNote updated, IEnumerable<string> privileges)
{
if (!this.authService.HasPermissionFor(AuthorisedAction.PlCreditDebitNoteUpdate, privileges))
{
throw new UnauthorisedActionException("You are not authorised to update credit/debit notes");
}

current.Notes = updated.Notes;
}
}
}
2 changes: 2 additions & 0 deletions src/Domain.LinnApps/PurchaseOrders/PurchaseOrder.cs
Original file line number Diff line number Diff line change
Expand Up @@ -26,5 +26,7 @@ public class PurchaseOrder
public decimal? OverbookQty { get; set; }

public Currency Currency { get; set; }

public string OrderContactName { get; set; }
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
{
using System.Collections.Generic;

using Linn.Purchasing.Domain.LinnApps.Parts;

public class PurchaseOrderDetail
{
public string Cancelled { get; set; }
Expand All @@ -17,12 +19,10 @@ public class PurchaseOrderDetail

public int? OurQty { get; set; }

public string PartNumber { get; set; }
public Part Part { get; set; }

public IEnumerable<PurchaseOrderDelivery> PurchaseDeliveries { get; set; }

public PurchaseOrder PurchaseOrder { get; set; }

public string RohsCompliant { get; set; }

public string SuppliersDesignation { get; set; }
Expand Down
8 changes: 4 additions & 4 deletions src/Domain.LinnApps/Reports/PurchaseOrdersReportService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,7 @@ public PurchaseOrdersReportService(
public ResultsModel GetOrdersByPartReport(DateTime from, DateTime to, string partNumber, bool includeCancelled)
{
var purchaseOrders = this.purchaseOrderRepository.FilterBy(
x => x.Details.Any(z => z.PartNumber == partNumber) && from <= x.OrderDate && x.OrderDate < to);
x => x.Details.Any(z => z.Part.PartNumber == partNumber) && from <= x.OrderDate && x.OrderDate < to);

var reportLayout = new SimpleGridLayout(
this.reportingHelper,
Expand All @@ -83,7 +83,7 @@ public ResultsModel GetOrdersByPartReport(DateTime from, DateTime to, string par
continue;
}

foreach (var orderDetail in order.Details.Where(d => d.PartNumber == partNumber))
foreach (var orderDetail in order.Details.Where(d => d.Part.PartNumber == partNumber))
{
foreach (var delivery in orderDetail.PurchaseDeliveries)
{
Expand Down Expand Up @@ -154,7 +154,7 @@ public ResultsModel GetOrdersBySupplierReport(
continue;
}

var part = this.partRepository.FindBy(x => x.PartNumber == orderDetail.PartNumber);
var part = this.partRepository.FindBy(x => x.PartNumber == orderDetail.Part.PartNumber);
if (stockControlled != "A" && ((stockControlled == "N" && part.StockControlled != "N")
|| (stockControlled == "O" && part.StockControlled != "Y")))
{
Expand Down Expand Up @@ -400,7 +400,7 @@ private static void ExtractSupplierReportDetails(
values.Add(
new CalculationValueModel
{
RowId = currentRowId, ColumnId = "PartNo", TextDisplay = $"{orderDetail.PartNumber}"
RowId = currentRowId, ColumnId = "PartNo", TextDisplay = $"{orderDetail.Part.PartNumber}"
});

values.Add(
Expand Down
2 changes: 1 addition & 1 deletion src/Domain.LinnApps/Reports/SpendsReportService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -149,7 +149,7 @@ public ResultsModel GetSpendByPartReport(int supplierId)
OrderNumber = s.OrderNumber.Value,
OrderLine = s.OrderLine.Value,
PartNumber = purchaseOrders.First(po => po.OrderNumber == s.OrderNumber.Value).Details
.First(x => x.Line == s.OrderLine.Value).PartNumber
.First(x => x.Line == s.OrderLine.Value).Part?.PartNumber
}).ToList();

var distinctPartSpends = partSpends.DistinctBy(x => x.PartNumber).Select(
Expand Down
54 changes: 41 additions & 13 deletions src/Facade/ResourceBuilders/PlCreditDebitNoteResourceBuilder.cs
Original file line number Diff line number Diff line change
@@ -1,38 +1,66 @@
namespace Linn.Purchasing.Facade.ResourceBuilders
{
using System;
using System.Collections.Generic;
using System.Linq;

using Linn.Common.Facade;
using Linn.Common.Resources;
using Linn.Purchasing.Domain.LinnApps.PurchaseOrders;
using Linn.Purchasing.Resources;

public class PlCreditDebitNoteResourceBuilder : IBuilder<PlCreditDebitNote>
{
public PlCreditDebitNoteResource Build(PlCreditDebitNote note, IEnumerable<string> claims)
{
return new PlCreditDebitNoteResource
public PlCreditDebitNoteResource Build(PlCreditDebitNote note, IEnumerable<string> claims)
{
return new PlCreditDebitNoteResource
{
OrderQty = note.OrderQty,
PartNumber = note.PartNumber,
DateClosed = note.DateClosed?.ToString("o"),
SupplierId = note.SupplierId,
SupplierId = note.Supplier.SupplierId,
ClosedBy = note.ClosedBy,
NetTotal = note.NetTotal,
NoteNumber = note.NoteNumber,
OriginalOrderNumber = note.OriginalOrderNumber,
OriginalOrderNumber = note.PurchaseOrder?.OrderNumber,
ReturnsOrderNumber = note.ReturnsOrderNumber,
ReturnsOrderLine = note.ReturnsOrderLine,
Notes = note.Notes,
SupplierName = note.Supplier?.Name,
DateCreated = note.DateCreated.ToShortDateString()
DateCreated = note.DateCreated.ToString("o"),
NoteType = note.NoteType,
SupplierFullAddress = note.Supplier.OrderFullAddress?.AddressString,
OrderUnitOfMeasure = note.OrderUnitOfMeasure,
OrderUnitPrice = note.OrderUnitPrice,
Total = note.Total,
VatTotal = note.VatTotal,
SuppliersDesignation = note.SuppliersDesignation,
OrderContactName = note.PurchaseOrder?.OrderContactName,
SupplierAddress = note.Supplier.OrderFullAddress?.AddressString,
Currency = note.Currency?.Name,
OrderDetails = note.PurchaseOrder?.Details
?.Select(d => new PurchaseOrderDetailResource
{
Line = d.Line,
PartNumber = d.Part?.PartNumber,
PartDescription = d.Part?.Description
}),
VatRate = note.VatRate,
Cancelled = note.CancelledBy.HasValue,
Links = this.BuildLinks(note, claims).ToArray()
};
}
}

public string GetLocation(PlCreditDebitNote p)
{
throw new NotImplementedException();
}
public string GetLocation(PlCreditDebitNote p)
{
return $"/purchasing/pl-credit-debit-notes/{p.NoteNumber}";
}

object IBuilder<PlCreditDebitNote>.Build(PlCreditDebitNote entity, IEnumerable<string> claims)
=> this.Build(entity, claims);

object IBuilder<PlCreditDebitNote>.Build(PlCreditDebitNote entity, IEnumerable<string> claims) => this.Build(entity, claims);
private IEnumerable<LinkResource> BuildLinks(PlCreditDebitNote model, IEnumerable<string> claims)
{
yield return new LinkResource { Rel = "self", Href = this.GetLocation(model) };
}
}
}
26 changes: 21 additions & 5 deletions src/Facade/Services/PlCreditDebitNoteFacadeService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
{
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;

using Linn.Common.Facade;
Expand Down Expand Up @@ -36,22 +37,37 @@ protected override void UpdateFromResource(
PlCreditDebitNoteResource updateResource,
IEnumerable<string> privileges = null)
{
if (updateResource.ClosedBy.HasValue && updateResource.Close.HasValue && (bool)updateResource.Close)
var enumerable = privileges?.ToList();
if (updateResource.Who.HasValue && updateResource.Close.HasValue && (bool)updateResource.Close)
{
this.domainService.CloseDebitNote(
entity,
updateResource.ReasonClosed,
(int)updateResource.ClosedBy,
privileges);
(int)updateResource.Who,
enumerable);
}

entity.Notes = updateResource.Notes;
if (updateResource.Who.HasValue && !string.IsNullOrEmpty(updateResource.ReasonCancelled))
{
this.domainService.CloseDebitNote(
entity,
updateResource.ReasonClosed,
(int)updateResource.Who,
enumerable);
}

this.domainService.UpdatePlCreditDebitNote(
entity,
new PlCreditDebitNote { Notes = updateResource.Notes },
enumerable);
}

protected override Expression<Func<PlCreditDebitNote, bool>> SearchExpression(
string searchTerm)
{
throw new NotImplementedException();
return x => x.NoteNumber.ToString() == searchTerm
|| x.Supplier.SupplierId.ToString() == searchTerm
|| x.Supplier.Name.ToUpper().Contains(searchTerm.ToUpper());
}

protected override void SaveToLogTable(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,20 @@ public PlCreditDebitNoteRepository(ServiceDbContext serviceDbContext)
{
}

public override IQueryable<PlCreditDebitNote> FilterBy(Expression<Func<PlCreditDebitNote, bool>> expression)
public override PlCreditDebitNote FindById(int key)
{
return base.FilterBy(expression).Include(n => n.Supplier);
return this.FindAll().Include(x => x.Supplier).ThenInclude(s => s.OrderFullAddress)
.Include(x => x.PurchaseOrder).ThenInclude(o => o.Details).ThenInclude(d => d.Part)
.Include(x => x.Currency)
.FirstOrDefault(x => x.NoteNumber == key);
}

public override IQueryable<PlCreditDebitNote> FilterBy(
Expression<Func<PlCreditDebitNote, bool>> expression)
{
return base.FilterBy(expression)
.Include(n => n.Supplier)
.Include(x => x.PurchaseOrder).AsNoTracking();
}
}
}
12 changes: 7 additions & 5 deletions src/Persistence.LinnApps/Repositories/PurchaseOrderRepository.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,9 @@ public PurchaseOrderRepository(ServiceDbContext serviceDbContext)

public override IQueryable<PurchaseOrder> FilterBy(Expression<Func<PurchaseOrder, bool>> expression)
{
return this.serviceDbContext.PurchaseOrders.Where(expression).Include(o => o.Details)
.ThenInclude(d => d.PurchaseDeliveries).Include(x => x.Supplier)
return this.serviceDbContext.PurchaseOrders.Where(expression)
.Include(o => o.Details).ThenInclude(d => d.Part)
.Include(o => o.Details).ThenInclude(d => d.PurchaseDeliveries).Include(x => x.Supplier)
.Include(x => x.Currency)
.AsNoTracking();
}
Expand All @@ -34,9 +35,10 @@ public override IQueryable<PurchaseOrder> FindAll()

public override PurchaseOrder FindById(int key)
{
var purchaseOrder = this.serviceDbContext.PurchaseOrders.Find(key);
this.serviceDbContext.Entry(purchaseOrder).Collection(p => p.Details).Load();
return purchaseOrder;
return this.serviceDbContext
.PurchaseOrders
.Include(o => o.Details).ThenInclude(d => d.Part)
.First(o => o.OrderNumber == key);
}
}
}
Loading

0 comments on commit 1e46e45

Please sign in to comment.