diff --git a/Public/css/main.css b/Public/css/main.css
index 0ebaeba..7a519f5 100644
--- a/Public/css/main.css
+++ b/Public/css/main.css
@@ -301,3 +301,38 @@ tr.htmx-swapping td {
margin-right: 15px;
font-size: 1.5em;
}
+
+.btn-row button {
+ border: none;
+ text-decoration: none;
+ color: grey;
+ background-color: inherit;
+ font-size: 1.3em;
+ padding-bottom: 10px;
+}
+
+.btn-row button:hover {
+ color: blue;
+}
+
+.btn-detail {
+ border: none;
+ text-decoration: none;
+ color: grey;
+ background-color: inherit;
+ font-size: 1.3em;
+}
+
+.po-detail table {
+ border-collapse: collapse;
+ border: none;
+ max-width: 300px;
+}
+
+.po-detail td {
+ border: none;
+}
+
+.label {
+ color: #00ffcc;
+}
diff --git a/Resources/Views/navbar.leaf b/Resources/Views/navbar.leaf
index a2a1b05..975a90a 100644
--- a/Resources/Views/navbar.leaf
+++ b/Resources/Views/navbar.leaf
@@ -1,6 +1,6 @@
#endexport
diff --git a/Resources/Views/purchaseOrders/table-row.leaf b/Resources/Views/purchaseOrders/table-row.leaf
index 50acb84..4fd1791 100644
--- a/Resources/Views/purchaseOrders/table-row.leaf
+++ b/Resources/Views/purchaseOrders/table-row.leaf
@@ -7,7 +7,14 @@
#capitalized(createdFor.firstName) #capitalized(createdFor.lastName) |
#(createdBy.username) |
#capitalized(truckStock) |
-
+ |
+
|
diff --git a/Sources/App/Controllers/View/PurchaseOrderViewController.swift b/Sources/App/Controllers/View/PurchaseOrderViewController.swift
index d6b826f..508a089 100644
--- a/Sources/App/Controllers/View/PurchaseOrderViewController.swift
+++ b/Sources/App/Controllers/View/PurchaseOrderViewController.swift
@@ -12,24 +12,36 @@ struct PurchaseOrderViewController: RouteCollection {
pos.get(use: index(req:))
pos.post(use: create(req:))
+ pos.group(":id") {
+ $0.get(use: detail(req:))
+ }
}
- // TODO: Use pageinated version.
@Sendable
func index(req: Request) async throws -> View {
- let purchaseOrders = try await api2.fetchAll(on: req.db)
+ let params = try? req.query.decode(PurchaseOrderIndex.self)
+ let purchaseOrdersPage = try await api2.fetchPage(params?.page ?? 1, limit: params?.limit ?? 50, on: req.db)
let branches = try await self.branches.getBranches(req: req)
let employees = try await employeesApi.index(req: req)
req.logger.debug("Branches: \(branches)")
return try await req.view.render(
"purchaseOrders/index",
PurchaseOrderCTX(
- purchaseOrders: purchaseOrders,
+ page: purchaseOrdersPage,
form: .create(branches: branches, employees: employees)
)
)
}
+ @Sendable
+ func detail(req: Request) async throws -> View {
+ guard let id = req.parameters.get("id", as: PurchaseOrder.IDValue.self) else {
+ throw Abort(.badRequest, reason: "Id not supplied.")
+ }
+ let purchaseOrder = try await api2.get(id: id, on: req.db)
+ return try await req.view.render("purchaseOrders/detail", ["purchaseOrder": purchaseOrder])
+ }
+
@Sendable
func create(req: Request) async throws -> View {
try PurchaseOrder.FormCreate.validate(content: req)
@@ -40,9 +52,33 @@ struct PurchaseOrderViewController: RouteCollection {
}
}
+private struct PurchaseOrderIndex: Content {
+ let page: Int?
+ let limit: Int?
+}
+
private struct PurchaseOrderCTX: Content {
let purchaseOrders: [PurchaseOrder.DTO]
+ let page: Int
+ let limit: Int
+ let hasNext: Bool
+ let hasPrevious: Bool
let form: PurchaseOrderFormCTX?
+
+ init(page: Page, form: PurchaseOrderFormCTX?) {
+ self.purchaseOrders = page.items
+ self.page = page.metadata.page
+ self.limit = page.metadata.per
+ self.hasNext = page.metadata.hasNext
+ self.hasPrevious = page.metadata.page > 1
+ self.form = form
+ }
+}
+
+private extension PageMetadata {
+ var hasNext: Bool {
+ total > (page * per)
+ }
}
private struct PurchaseOrderFormCTX: Content {
diff --git a/Sources/App/Controllers/View/UsersViewController.swift b/Sources/App/Controllers/View/UsersViewController.swift
index 32a262a..c172dbd 100644
--- a/Sources/App/Controllers/View/UsersViewController.swift
+++ b/Sources/App/Controllers/View/UsersViewController.swift
@@ -49,7 +49,7 @@ struct UserFormCTX: Content {
htmxForm: .init(
formClass: "user-form",
formId: "user-form",
- htmxTargetUrl: .post("/login\(next != nil ? "?next=\(next!)" : "")"),
+ htmxTargetUrl: .post("/login\((next != nil && next != "/") ? "?next=\(next!)" : "")"),
htmxTarget: "body",
htmxPushUrl: true,
htmxResetAfterRequest: true,
diff --git a/Sources/App/Controllers/ViewController.swift b/Sources/App/Controllers/ViewController.swift
index 4d3fd24..43c4be3 100644
--- a/Sources/App/Controllers/ViewController.swift
+++ b/Sources/App/Controllers/ViewController.swift
@@ -35,7 +35,9 @@ struct ViewController: RouteCollection {
func getLogin(req: Request) async throws -> View {
req.logger.debug("Login Query: \(req.url.query ?? "n/a")")
let params = try? req.query.decode(LoginParameter.self)
- return try await req.view.render("login", UserFormCTX.signIn(next: params?.next))
+ return try await req.view.render(
+ "login", UserFormCTX.signIn(next: params?.next)
+ )
}
@Sendable
@@ -95,6 +97,7 @@ private struct UserForm: Content {
enum HomeRoute: String, Content {
case employees
+ case purchaseOrders
case users
case vendors
}