Add mocks for the various setting pages.

This commit is contained in:
Eli Ribble 2025-12-12 21:52:55 +00:00
parent 637decea11
commit 5f86274b16
No known key found for this signature in database
9 changed files with 1205 additions and 18 deletions

54
html.go
View file

@ -62,6 +62,12 @@ var (
serviceRequestQuick = newBuiltTemplate("service-request-quick", "base")
serviceRequestQuickConfirmation = newBuiltTemplate("service-request-quick-confirmation", "base")
serviceRequestUpdates = newBuiltTemplate("service-request-updates", "base")
settingRoot = newBuiltTemplate("setting-mock", "base")
settingIntegration = newBuiltTemplate("setting-integration", "base")
settingPesticide = newBuiltTemplate("setting-pesticide", "base")
settingPesticideAdd = newBuiltTemplate("setting-pesticide-add", "base")
settingUsers = newBuiltTemplate("setting-user", "base")
settingUsersAdd = newBuiltTemplate("setting-user-add", "base")
signin = newBuiltTemplate("signin", "base")
signup = newBuiltTemplate("signup", "base")
)
@ -103,15 +109,21 @@ type ContentCell struct {
User User
}
type ContentMockURLs struct {
Dispatch string
DispatchResults string
ReportConfirmation string
ReportDetail string
ReportContribute string
ReportEvidence string
ReportSchedule string
ReportUpdate string
Root string
Dispatch string
DispatchResults string
ReportConfirmation string
ReportDetail string
ReportContribute string
ReportEvidence string
ReportSchedule string
ReportUpdate string
Root string
Setting string
SettingIntegration string
SettingPesticide string
SettingPesticideAdd string
SettingUser string
SettingUserAdd string
}
type ContentMock struct {
DistrictName string
@ -358,15 +370,21 @@ func htmlMock(t string, w http.ResponseWriter, code string) {
data := ContentMock{
DistrictName: "Delta MVCD",
URLs: ContentMockURLs{
Dispatch: "/mock/dispatch",
DispatchResults: "/mock/dispatch-results",
ReportConfirmation: fmt.Sprintf("/mock/report/%s/confirm", code),
ReportDetail: fmt.Sprintf("/mock/report/%s", code),
ReportContribute: fmt.Sprintf("/mock/report/%s/contribute", code),
ReportEvidence: fmt.Sprintf("/mock/report/%s/evidence", code),
ReportSchedule: fmt.Sprintf("/mock/report/%s/schedule", code),
ReportUpdate: fmt.Sprintf("/mock/report/%s/update", code),
Root: "/mock",
Dispatch: "/mock/dispatch",
DispatchResults: "/mock/dispatch-results",
ReportConfirmation: fmt.Sprintf("/mock/report/%s/confirm", code),
ReportDetail: fmt.Sprintf("/mock/report/%s", code),
ReportContribute: fmt.Sprintf("/mock/report/%s/contribute", code),
ReportEvidence: fmt.Sprintf("/mock/report/%s/evidence", code),
ReportSchedule: fmt.Sprintf("/mock/report/%s/schedule", code),
ReportUpdate: fmt.Sprintf("/mock/report/%s/update", code),
Root: "/mock",
Setting: "/mock/setting",
SettingIntegration: "/mock/setting/integration",
SettingPesticide: "/mock/setting/pesticide",
SettingPesticideAdd: "/mock/setting/pesticide/add",
SettingUser: "/mock/setting/user",
SettingUserAdd: "/mock/setting/user/add",
},
}
template, ok := templatesByFilename[t]

View file

@ -117,6 +117,12 @@ func main() {
r.Get("/mock/service-request-quick", renderMock("service-request-quick"))
r.Get("/mock/service-request-quick-confirmation", renderMock("service-request-quick-confirmation"))
r.Get("/mock/service-request-updates", renderMock("service-request-updates"))
r.Get("/mock/setting", renderMock("setting-mock"))
r.Get("/mock/setting/integration", renderMock("setting-integration"))
r.Get("/mock/setting/pesticide", renderMock("setting-pesticide"))
r.Get("/mock/setting/pesticide/add", renderMock("setting-pesticide-add"))
r.Get("/mock/setting/user", renderMock("setting-user"))
r.Get("/mock/setting/user/add", renderMock("setting-user-add"))
r.Get("/oauth/refresh", getOAuthRefresh)

View file

@ -45,6 +45,11 @@
<td>Service Request</td>
<td>A page for members of the public to make a direct service request</td>
</tr>
<tr>
<td><a href="/mock/setting">/mock/setting</a></td>
<td>Settings</td>
<td>A page for management to control the behavior of Nidus</td>
</tr>
</tbody>
</table>
</div>

View file

@ -0,0 +1,257 @@
{{template "base.html" .}}
{{define "title"}}Dash{{end}}
{{define "extraheader"}}
<style>
.integration-card {
border-left: 5px solid #0d6efd;
transition: all 0.2s;
}
.integration-card:hover {
box-shadow: 0 0.5rem 1rem rgba(0, 0, 0, 0.15);
}
.integration-card.fieldseeker {
border-left-color: #0d6efd;
}
.integration-card.vectorsurv {
border-left-color: #198754;
}
.integration-card.veemac {
border-left-color: #dc3545;
}
.status-active {
color: #198754;
}
.status-inactive {
color: #dc3545;
}
.token-display {
font-family: monospace;
background-color: #f8f9fa;
padding: 0.25rem 0.5rem;
border-radius: 0.25rem;
border: 1px solid #dee2e6;
}
</style>
{{end}}
{{define "content"}}
<div class="container py-4">
<!-- Header -->
<div class="mb-4">
<h1>Integrations</h1>
<div class="alert alert-warning">
<i class="bi bi-exclamation-triangle me-2"></i>
<strong>Important:</strong> This page allows you to configure integration with third-party services. The credentials and tokens stored here provide access to external systems and should be protected. Only authorized personnel should modify these settings.
</div>
</div>
<!-- FieldSeeker GIS Integration -->
<div class="card mb-4 integration-card fieldseeker">
<div class="card-header d-flex justify-content-between align-items-center">
<div>
<h2 class="h5 mb-0">Frontier Precision's FieldSeeker GIS</h2>
</div>
<img src="https://via.placeholder.com/100x40?text=FieldSeeker" alt="FieldSeeker Logo" height="40">
</div>
<div class="card-body">
<div class="table-responsive mb-3">
<table class="table table-borderless">
<tbody>
<tr>
<td width="30%"><strong>OAuth Token Status</strong></td>
<td>
<span class="status-active">
<i class="bi bi-check-circle-fill me-1"></i> Active
</span>
</td>
</tr>
<tr>
<td><strong>Token Expiration</strong></td>
<td>26 days remaining (Expires on Dec 31, 2025)</td>
</tr>
<tr>
<td><strong>Integration Method</strong></td>
<td>Web Hooks</td>
</tr>
<tr>
<td><strong>Permission Level</strong></td>
<td>Read & Write</td>
</tr>
</tbody>
</table>
</div>
<div class="d-flex gap-2">
<button class="btn btn-primary">
<i class="bi bi-arrow-repeat me-2"></i>Refresh OAuth Token
</button>
<button class="btn btn-outline-danger">
<i class="bi bi-trash me-2"></i>Delete Token
</button>
</div>
</div>
</div>
<!-- VectorSurv Integration -->
<div class="card mb-4 integration-card vectorsurv">
<div class="card-header d-flex justify-content-between align-items-center">
<div>
<h2 class="h5 mb-0">VectorSurv</h2>
</div>
<img src="https://via.placeholder.com/100x40?text=VectorSurv" alt="VectorSurv Logo" height="40">
</div>
<div class="card-body">
<div class="table-responsive mb-3">
<table class="table table-borderless">
<tbody>
<tr>
<td width="30%"><strong>API Token</strong></td>
<td>
<span class="token-display">vs_9f72b5e3******************************c11d</span>
</td>
</tr>
<tr>
<td><strong>Last Synchronization</strong></td>
<td>December 5, 2025 at 08:34 AM (2 days ago)</td>
</tr>
<tr>
<td><strong>Synchronization Status</strong></td>
<td>
<span class="status-active">
<i class="bi bi-check-circle-fill me-1"></i> Active (Scheduled daily at 2:00 AM)
</span>
</td>
</tr>
</tbody>
</table>
</div>
<div class="d-flex gap-2">
<button class="btn btn-success" data-bs-toggle="modal" data-bs-target="#vectorsurvModal">
<i class="bi bi-pencil-square me-2"></i>Edit Token
</button>
<button class="btn btn-outline-danger">
<i class="bi bi-trash me-2"></i>Remove Integration
</button>
</div>
</div>
</div>
<!-- VeeMac Integration -->
<div class="card mb-4 integration-card veemac">
<div class="card-header d-flex justify-content-between align-items-center">
<div>
<h2 class="h5 mb-0">VeeMac</h2>
</div>
<img src="https://via.placeholder.com/100x40?text=VeeMac" alt="VeeMac Logo" height="40">
</div>
<div class="card-body">
<div class="table-responsive mb-3">
<table class="table table-borderless">
<tbody>
<tr>
<td width="30%"><strong>Username</strong></td>
<td>mosquito_district21</td>
</tr>
<tr>
<td><strong>Password</strong></td>
<td>••••••••••••</td>
</tr>
<tr>
<td><strong>Last Synchronization</strong></td>
<td>December 6, 2025 at 11:15 PM (Yesterday)</td>
</tr>
<tr>
<td><strong>Synchronization Status</strong></td>
<td>
<span class="status-inactive">
<i class="bi bi-x-circle-fill me-1"></i> Inactive (Manual sync only)
</span>
</td>
</tr>
</tbody>
</table>
</div>
<div class="d-flex gap-2">
<button class="btn btn-success" data-bs-toggle="modal" data-bs-target="#veemacModal">
<i class="bi bi-pencil-square me-2"></i>Edit Credentials
</button>
<button class="btn btn-outline-danger">
<i class="bi bi-trash me-2"></i>Remove Integration
</button>
</div>
</div>
</div>
</div>
<!-- VectorSurv Edit Token Modal -->
<div class="modal fade" id="vectorsurvModal" tabindex="-1" aria-labelledby="vectorsurvModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="vectorsurvModalLabel">Edit VectorSurv API Token</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<form>
<div class="mb-3">
<label for="vectorsurvToken" class="form-label">API Token</label>
<input type="text" class="form-control" id="vectorsurvToken" value="vs_9f72b5e3c8a1d492f6b7e54321098c11d">
<div class="form-text">You can find this token in your VectorSurv account settings.</div>
</div>
<div class="mb-3 form-check">
<input type="checkbox" class="form-check-input" id="vectorsurvSyncCheck" checked>
<label class="form-check-label" for="vectorsurvSyncCheck">Enable automatic synchronization</label>
</div>
<div class="mb-3">
<label for="vectorsurvSyncTime" class="form-label">Sync Time</label>
<input type="time" class="form-control" id="vectorsurvSyncTime" value="02:00">
</div>
</form>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Cancel</button>
<button type="button" class="btn btn-success">Save Changes</button>
</div>
</div>
</div>
</div>
<!-- VeeMac Edit Credentials Modal -->
<div class="modal fade" id="veemacModal" tabindex="-1" aria-labelledby="veemacModalLabel" aria-hidden="true">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title" id="veemacModalLabel">Edit VeeMac Credentials</h5>
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
</div>
<div class="modal-body">
<form>
<div class="mb-3">
<label for="veemacUsername" class="form-label">Username</label>
<input type="text" class="form-control" id="veemacUsername" value="mosquito_district21">
</div>
<div class="mb-3">
<label for="veemacPassword" class="form-label">Password</label>
<input type="password" class="form-control" id="veemacPassword" value="password123">
</div>
<div class="mb-3 form-check">
<input type="checkbox" class="form-check-input" id="veemacSyncCheck">
<label class="form-check-label" for="veemacSyncCheck">Enable automatic synchronization</label>
</div>
<div class="mb-3">
<label for="veemacSyncFrequency" class="form-label">Sync Frequency</label>
<select class="form-select" id="veemacSyncFrequency" disabled>
<option value="daily">Daily</option>
<option value="weekly">Weekly</option>
<option value="hourly">Hourly</option>
</select>
</div>
</form>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Cancel</button>
<button type="button" class="btn btn-danger">Save Changes</button>
</div>
</div>
</div>
</div>
{{end}}

192
templates/setting-mock.html Normal file
View file

@ -0,0 +1,192 @@
{{template "base.html" .}}
{{define "title"}}Dash{{end}}
{{define "extraheader"}}
<style>
.settings-card {
transition: transform 0.2s, box-shadow 0.2s;
height: 100%;
}
.settings-card:hover {
transform: translateY(-5px);
box-shadow: 0 10px 20px rgba(0, 0, 0, 0.1);
}
.settings-icon {
font-size: 2.5rem;
width: 80px;
height: 80px;
display: flex;
align-items: center;
justify-content: center;
border-radius: 50%;
margin-bottom: 1.5rem;
}
.icon-users {
color: #6f42c1;
background-color: rgba(111, 66, 193, 0.1);
}
.icon-pesticides {
color: #198754;
background-color: rgba(25, 135, 84, 0.1);
}
.icon-integrations {
color: #0d6efd;
background-color: rgba(13, 110, 253, 0.1);
}
.icon-notifications {
color: #fd7e14;
background-color: rgba(253, 126, 20, 0.1);
}
.icon-general {
color: #6c757d;
background-color: rgba(108, 117, 125, 0.1);
}
.icon-equipment {
color: #dc3545;
background-color: rgba(220, 53, 69, 0.1);
}
.last-updated {
font-size: 0.8rem;
color: #6c757d;
}
</style>
{{end}}
{{define "content"}}
<div class="container py-5">
<div class="row mb-4">
<div class="col">
<h1 class="display-5 mb-3">Settings</h1>
<p class="text-muted lead">Configure your organization's preferences and integrations</p>
</div>
</div>
<div class="row g-4">
<!-- User Management Card -->
<div class="col-12 col-md-6 col-lg-4">
<div class="card settings-card border-0 shadow-sm">
<div class="card-body p-4">
<div class="settings-icon icon-users">
<i class="bi bi-people-fill"></i>
</div>
<h2 class="h4 mb-2">User Management</h2>
<p class="text-muted mb-4">Manage staff accounts, roles, and permissions for your organization.</p>
<div class="d-flex justify-content-between align-items-center">
<a href="{{ .URLs.SettingUser }}" class="btn btn-outline-primary">
Manage Users
<i class="bi bi-arrow-right ms-1"></i>
</a>
<span class="last-updated">23 users</span>
</div>
</div>
</div>
</div>
<!-- Pesticide Products Card -->
<div class="col-12 col-md-6 col-lg-4">
<div class="card settings-card border-0 shadow-sm">
<div class="card-body p-4">
<div class="settings-icon icon-pesticides">
<i class="bi bi-droplet-fill"></i>
</div>
<h2 class="h4 mb-2">Pesticide Products</h2>
<p class="text-muted mb-4">Configure products, application rates, and field recommendations.</p>
<div class="d-flex justify-content-between align-items-center">
<a href="{{ .URLs.SettingPesticide }}" class="btn btn-outline-success">
Manage Products
<i class="bi bi-arrow-right ms-1"></i>
</a>
<span class="last-updated">12 active products</span>
</div>
</div>
</div>
</div>
<!-- Integrations Card -->
<div class="col-12 col-md-6 col-lg-4">
<div class="card settings-card border-0 shadow-sm">
<div class="card-body p-4">
<div class="settings-icon icon-integrations">
<i class="bi bi-gear-wide-connected"></i>
</div>
<h2 class="h4 mb-2">Integrations</h2>
<p class="text-muted mb-4">Configure connections with FieldSeeker, VectorSurv, and other services.</p>
<div class="d-flex justify-content-between align-items-center">
<a href="{{ .URLs.SettingIntegration }}" class="btn btn-outline-primary">
Manage Integrations
<i class="bi bi-arrow-right ms-1"></i>
</a>
<span class="last-updated">3 active connections</span>
</div>
</div>
</div>
</div>
<!-- Equipment Card -->
<div class="col-12 col-md-6 col-lg-4">
<div class="card settings-card border-0 shadow-sm">
<div class="card-body p-4">
<div class="settings-icon icon-equipment">
<i class="bi bi-tools"></i>
</div>
<h2 class="h4 mb-2">Equipment</h2>
<p class="text-muted mb-4">Manage your field equipment inventory, calibration, and maintenance.</p>
<div class="d-flex justify-content-between align-items-center">
<a href="equipment.html" class="btn btn-outline-danger">
Manage Equipment
<i class="bi bi-arrow-right ms-1"></i>
</a>
<span class="last-updated">Updated 5 days ago</span>
</div>
</div>
</div>
</div>
<!-- Notifications Card -->
<div class="col-12 col-md-6 col-lg-4">
<div class="card settings-card border-0 shadow-sm">
<div class="card-body p-4">
<div class="settings-icon icon-notifications">
<i class="bi bi-bell-fill"></i>
</div>
<h2 class="h4 mb-2">Notifications</h2>
<p class="text-muted mb-4">Configure email alerts, SMS notifications, and reporting preferences.</p>
<div class="d-flex justify-content-between align-items-center">
<a href="notifications.html" class="btn btn-outline-warning">
Manage Notifications
<i class="bi bi-arrow-right ms-1"></i>
</a>
<span class="last-updated">5 active alerts</span>
</div>
</div>
</div>
</div>
<!-- General Settings Card -->
<div class="col-12 col-md-6 col-lg-4">
<div class="card settings-card border-0 shadow-sm">
<div class="card-body p-4">
<div class="settings-icon icon-general">
<i class="bi bi-sliders"></i>
</div>
<h2 class="h4 mb-2">General Settings</h2>
<p class="text-muted mb-4">Configure organization details, branding, and system preferences.</p>
<div class="d-flex justify-content-between align-items-center">
<a href="general-settings.html" class="btn btn-outline-secondary">
Manage Settings
<i class="bi bi-arrow-right ms-1"></i>
</a>
<span class="last-updated">Updated yesterday</span>
</div>
</div>
</div>
</div>
</div>
<div class="mt-5 text-center text-muted">
<p class="small">
<i class="bi bi-shield-lock me-1"></i>
All changes made in settings are logged for audit purposes
</p>
</div>
</div>
{{end}}

View file

@ -0,0 +1,231 @@
{{template "base.html" .}}
{{define "title"}}Dash{{end}}
{{define "extraheader"}}
<style>
.section-heading {
font-size: 1.2rem;
font-weight: 600;
margin-bottom: 1rem;
padding-bottom: 0.5rem;
border-bottom: 1px solid #dee2e6;
}
.info-label {
font-weight: 600;
color: #495057;
}
.target-icon {
display: inline-block;
width: 30px;
height: 30px;
text-align: center;
line-height: 30px;
border-radius: 50%;
font-size: 14px;
font-weight: bold;
margin-right: 4px;
color: white;
}
.target-active {
background-color: #0d6efd;
}
.target-inactive {
background-color: #dee2e6;
color: #6c757d;
}
.tag {
display: inline-flex;
align-items: center;
padding: 0.4rem 0.8rem;
margin: 0.2rem;
border-radius: 30px;
background-color: #f8f9fa;
border: 1px solid #dee2e6;
font-size: 0.9rem;
}
.tag i {
margin-right: 0.5rem;
}
.tag-enabled {
background-color: #d1e7dd;
color: #0f5132;
border-color: #a3cfbb;
}
.tag-ppe {
background-color: #e2e3e5;
color: #41464b;
border-color: #d3d6d8;
}
.tag-equipment {
background-color: #cff4fc;
color: #055160;
border-color: #9eeaf9;
}
.tag-suitability {
background-color: #fff3cd;
color: #664d03;
border-color: #ffecb5;
}
.tag-optional {
background-color: #f8f9fa;
color: #6c757d;
border-color: #dee2e6;
}
</style>
{{end}}
{{define "content"}}
<div class="container py-4">
<!-- Breadcrumb -->
<nav aria-label="breadcrumb" class="mb-4">
<ol class="breadcrumb">
<li class="breadcrumb-item"><a href="#">Settings</a></li>
<li class="breadcrumb-item"><a href="pesticide-config.html">Pesticide</a></li>
<li class="breadcrumb-item active" aria-current="page">VectoMax FG</li>
</ol>
</nav>
<!-- Main Content -->
<div class="card shadow-sm mb-4">
<div class="card-body">
<!-- Product Header -->
<div class="d-flex justify-content-between align-items-start mb-4">
<div>
<h1 class="mb-2">VectoMax FG</h1>
<p class="text-muted mb-0">Biological larvicide granules combining Bacillus thuringiensis subspecies israelensis and Bacillus sphaericus for extended residual control of mosquito larvae.</p>
</div>
<span class="tag tag-enabled">
<i class="bi bi-check-circle-fill"></i> Enabled
</span>
</div>
<!-- General Information -->
<div class="mb-4">
<h2 class="section-heading">General Information</h2>
<div class="row g-3">
<div class="col-md-6 col-lg-4">
<div class="info-label">Formulation</div>
<div>Granule</div>
</div>
<div class="col-md-6 col-lg-4">
<div class="info-label">EPA Registration Number</div>
<div>73049-429</div>
</div>
<div class="col-md-6 col-lg-4">
<div class="info-label">Active Ingredients</div>
<div>Bacillus thuringiensis subspecies israelensis (2.7%)<br>
Bacillus sphaericus (4.5%)</div>
</div>
<div class="col-md-6 col-lg-4">
<div class="info-label">Biological Targeting</div>
<div class="mt-1">
<span class="target-icon target-active" title="Instar Stage 1">I1</span>
<span class="target-icon target-active" title="Instar Stage 2">I2</span>
<span class="target-icon target-active" title="Instar Stage 3">I3</span>
<span class="target-icon target-active" title="Instar Stage 4">I4</span>
<span class="target-icon target-inactive" title="Pupae">P</span>
</div>
</div>
<div class="col-md-6 col-lg-4">
<div class="info-label">Application Rates</div>
<div>Low: 5 lbs/acre<br>
High: 20 lbs/acre</div>
</div>
<div class="col-md-6 col-lg-4">
<div class="info-label">Residual</div>
<div>Up to 30 days (environmental conditions dependent)</div>
</div>
</div>
</div>
<!-- Usage Notes -->
<div class="alert alert-info mb-4">
<div class="d-flex">
<div class="me-3">
<i class="bi bi-info-circle-fill fs-4"></i>
</div>
<div>
<h5 class="alert-heading">Key Usage Notes</h5>
<p class="mb-0">Apply evenly across water surface. Use higher rate when L4 present or when organic load is high. Avoid application in ponds with fish unless approved by a supervisor.</p>
</div>
</div>
</div>
<!-- PPE Requirements -->
<div class="mb-4">
<h2 class="section-heading">PPE Requirements</h2>
<div>
<span class="tag tag-ppe">
<i class="bi bi-hand-thumbs-up"></i> Gloves
</span>
<span class="tag tag-ppe">
<i class="bi bi-eyeglasses"></i> Eye Protection
</span>
<span class="tag tag-optional">
<i class="bi bi-mask"></i> Respirator (Optional)
</span>
</div>
</div>
<!-- Equipment Supported -->
<div class="mb-4">
<h2 class="section-heading">Equipment Supported</h2>
<div>
<span class="tag tag-equipment">
<i class="bi bi-backpack"></i> Backpack Spreader
</span>
<span class="tag tag-equipment">
<i class="bi bi-hand-index-thumb"></i> Hand Spreader
</span>
<span class="tag tag-equipment">
<i class="bi bi-truck"></i> Truck Granule Unit
</span>
</div>
</div>
<!-- Suitability -->
<div class="mb-4">
<h2 class="section-heading">Suitability</h2>
<div class="row g-3">
<div class="col-md-6 col-lg-3">
<div class="info-label">Pools</div>
<div><span class="badge bg-success">Recommended</span></div>
</div>
<div class="col-md-6 col-lg-3">
<div class="info-label">Vegetation</div>
<div><span class="badge bg-info text-dark">OK</span></div>
</div>
<div class="col-md-6 col-lg-3">
<div class="info-label">High Organics</div>
<div><span class="badge bg-info text-dark">OK</span></div>
</div>
<div class="col-md-6 col-lg-3">
<div class="info-label">Organic Crop Restriction</div>
<div><span class="badge bg-secondary">None</span></div>
</div>
</div>
</div>
<!-- Actions -->
<div class="d-flex justify-content-between mt-5 pt-3 border-top">
<button class="btn btn-outline-danger">
<i class="bi bi-trash me-2"></i> Remove from Inventory
</button>
<button class="btn btn-success">
<i class="bi bi-plus-circle me-2"></i> Add to Allowed Inventory
</button>
</div>
</div>
</div>
</div>
{{end}}

View file

@ -0,0 +1,211 @@
{{template "base.html" .}}
{{define "title"}}Dash{{end}}
{{define "extraheader"}}
<style>
.target-icon {
display: inline-block;
width: 24px;
height: 24px;
text-align: center;
line-height: 24px;
border-radius: 50%;
font-size: 12px;
font-weight: bold;
margin-right: 2px;
color: white;
}
.target-active {
background-color: #0d6efd;
}
.target-inactive {
background-color: #dee2e6;
color: #6c757d;
}
.table-responsive {
overflow-x: auto;
}
th {
white-space: nowrap;
}
</style>
{{end}}
{{define "content"}}
<div class="container-fluid p-4">
<div class="d-flex justify-content-between align-items-center mb-4">
<h1 class="mb-0">Pesticide Products Configuration</h1>
<a href="{{ .URLs.SettingPesticideAdd }}" class="btn btn-primary" id="addProductBtn">
<i class="bi bi-plus-circle me-2"></i>Add New Product
</a>
</div>
<div class="card">
<div class="card-body">
<div class="table-responsive">
<table class="table table-striped table-hover align-middle">
<thead class="table-light">
<tr>
<th>Product</th>
<th>Formulation</th>
<th>Targets</th>
<th>Residual (days)</th>
<th>Low Rate</th>
<th>Max Rate</th>
<th>Pools</th>
<th>Info</th>
<th>Actions</th>
</tr>
</thead>
<tbody>
<!-- Sample pesticide data -->
<tr>
<td><strong>BVA Oil</strong></td>
<td>Liquid</td>
<td>
<span class="target-icon target-inactive" title="Instar Stage 1">I1</span>
<span class="target-icon target-inactive" title="Instar Stage 2">I2</span>
<span class="target-icon target-inactive" title="Instar Stage 3">I3</span>
<span class="target-icon target-inactive" title="Instar Stage 4">I4</span>
<span class="target-icon target-active" title="Pupae">P</span>
</td>
<td>1</td>
<td>0.5 gal/acre</td>
<td>5 gal/acre</td>
<td><span class="badge bg-success">Recommended</span></td>
<td>
<a href="product-details.html?id=bva-oil" class="btn btn-sm btn-info" title="Product Information">
<i class="bi bi-info-circle"></i>
</a>
</td>
<td>
<button class="btn btn-sm btn-primary" title="Edit">
<i class="bi bi-pencil"></i>
</button>
<button class="btn btn-sm btn-danger" title="Delete">
<i class="bi bi-trash"></i>
</button>
</td>
</tr>
<tr>
<td><strong>VectoMax FG</strong></td>
<td>Granule</td>
<td>
<span class="target-icon target-active" title="Instar Stage 1">I1</span>
<span class="target-icon target-active" title="Instar Stage 2">I2</span>
<span class="target-icon target-active" title="Instar Stage 3">I3</span>
<span class="target-icon target-active" title="Instar Stage 4">I4</span>
<span class="target-icon target-inactive" title="Pupae">P</span>
</td>
<td>30</td>
<td>5 lbs/acre</td>
<td>20 lbs/acre</td>
<td><span class="badge bg-success">Recommended</span></td>
<td>
<a href="product-details.html?id=vectomax-fg" class="btn btn-sm btn-info" title="Product Information">
<i class="bi bi-info-circle"></i>
</a>
</td>
<td>
<button class="btn btn-sm btn-primary" title="Edit">
<i class="bi bi-pencil"></i>
</button>
<button class="btn btn-sm btn-danger" title="Delete">
<i class="bi bi-trash"></i>
</button>
</td>
</tr>
<tr>
<td><strong>Censor</strong></td>
<td>Liquid</td>
<td>
<span class="target-icon target-active" title="Instar Stage 1">I1</span>
<span class="target-icon target-active" title="Instar Stage 2">I2</span>
<span class="target-icon target-active" title="Instar Stage 3">I3</span>
<span class="target-icon target-active" title="Instar Stage 4">I4</span>
<span class="target-icon target-inactive" title="Pupae">P</span>
</td>
<td>21</td>
<td>0.75 gal/acre</td>
<td>2.5 gal/acre</td>
<td><span class="badge bg-warning text-dark">Allowed</span></td>
<td>
<a href="product-details.html?id=censor" class="btn btn-sm btn-info" title="Product Information">
<i class="bi bi-info-circle"></i>
</a>
</td>
<td>
<button class="btn btn-sm btn-primary" title="Edit">
<i class="bi bi-pencil"></i>
</button>
<button class="btn btn-sm btn-danger" title="Delete">
<i class="bi bi-trash"></i>
</button>
</td>
</tr>
<tr>
<td><strong>AquaBac XT</strong></td>
<td>Liquid</td>
<td>
<span class="target-icon target-active" title="Instar Stage 1">I1</span>
<span class="target-icon target-active" title="Instar Stage 2">I2</span>
<span class="target-icon target-active" title="Instar Stage 3">I3</span>
<span class="target-icon target-inactive" title="Instar Stage 4">I4</span>
<span class="target-icon target-inactive" title="Pupae">P</span>
</td>
<td>14</td>
<td>0.25 gal/acre</td>
<td>2 gal/acre</td>
<td><span class="badge bg-danger">Prohibited</span></td>
<td>
<a href="product-details.html?id=aquabac-xt" class="btn btn-sm btn-info" title="Product Information">
<i class="bi bi-info-circle"></i>
</a>
</td>
<td>
<button class="btn btn-sm btn-primary" title="Edit">
<i class="bi bi-pencil"></i>
</button>
<button class="btn btn-sm btn-danger" title="Delete">
<i class="bi bi-trash"></i>
</button>
</td>
</tr>
<tr>
<td><strong>Natular G30</strong></td>
<td>Granule</td>
<td>
<span class="target-icon target-active" title="Instar Stage 1">I1</span>
<span class="target-icon target-active" title="Instar Stage 2">I2</span>
<span class="target-icon target-active" title="Instar Stage 3">I3</span>
<span class="target-icon target-active" title="Instar Stage 4">I4</span>
<span class="target-icon target-inactive" title="Pupae">P</span>
</td>
<td>30</td>
<td>5 lbs/acre</td>
<td>12 lbs/acre</td>
<td><span class="badge bg-secondary">Discouraged</span></td>
<td>
<a href="product-details.html?id=natular-g30" class="btn btn-sm btn-info" title="Product Information">
<i class="bi bi-info-circle"></i>
</a>
</td>
<td>
<button class="btn btn-sm btn-primary" title="Edit">
<i class="bi bi-pencil"></i>
</button>
<button class="btn btn-sm btn-danger" title="Delete">
<i class="bi bi-trash"></i>
</button>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
{{end}}

View file

@ -0,0 +1,123 @@
{{template "base.html" .}}
{{define "title"}}Dash{{end}}
{{define "extraheader"}}
<style>
.form-check-input.switch-lg {
width: 3em;
height: 1.5em;
}
.required-field::after {
content: " *";
color: red;
}
</style>
{{end}}
{{define "content"}}
<div class="container py-5">
<div class="row justify-content-center">
<div class="col-lg-8">
<div class="card shadow">
<div class="card-header bg-white">
<div class="d-flex justify-content-between align-items-center">
<h3 class="mb-0">Add New User</h3>
<a href="user-management.html" class="btn btn-outline-secondary btn-sm">
<i class="bi bi-arrow-left me-1"></i> Back to Users
</a>
</div>
</div>
<div class="card-body">
<form id="addUserForm" class="needs-validation" novalidate>
<!-- Full Name -->
<div class="mb-3">
<label for="fullName" class="form-label required-field">Full Name</label>
<input type="text" class="form-control" id="fullName" required>
<div class="invalid-feedback">
Please provide the user's full name.
</div>
</div>
<!-- Email Address -->
<div class="mb-3">
<label for="emailAddress" class="form-label required-field">Email Address</label>
<input type="email" class="form-control" id="emailAddress" required>
<div class="invalid-feedback">
Please provide a valid email address.
</div>
<div class="form-text">An invitation will be sent to this email address.</div>
</div>
<!-- Username -->
<div class="mb-3">
<label for="username" class="form-label required-field">Username</label>
<input type="text" class="form-control" id="username" required>
<div class="invalid-feedback">
Please provide a username.
</div>
<div class="form-text">Username must be unique and contain only letters, numbers, and underscores.</div>
</div>
<div class="row">
<!-- Role -->
<div class="col-md-6 mb-3">
<label for="userRole" class="form-label required-field">Role</label>
<select class="form-select" id="userRole" required>
<option value="" selected disabled>Select a role</option>
<option value="lead">Lead</option>
<option value="technician">Technician</option>
<option value="administrator">Administrator</option>
</select>
<div class="invalid-feedback">
Please select a role.
</div>
</div>
<!-- Initial Status -->
<div class="col-md-6 mb-3">
<label for="initialStatus" class="form-label">Initial Status</label>
<select class="form-select" id="initialStatus">
<option value="invited" selected>Invited</option>
<option value="active">Active</option>
</select>
</div>
</div>
<!-- Permissions -->
<div class="mb-4">
<label class="form-label d-block">Permissions</label>
<div class="form-check form-switch">
<input class="form-check-input switch-lg" type="checkbox" id="serveWarrants">
<label class="form-check-label" for="serveWarrants">
Can serve warrants
</label>
</div>
</div>
<!-- Send welcome email checkbox -->
<div class="mb-4">
<div class="form-check">
<input class="form-check-input" type="checkbox" id="sendWelcomeEmail" checked>
<label class="form-check-label" for="sendWelcomeEmail">
Send welcome email with login instructions
</label>
</div>
</div>
<hr>
<!-- Form actions -->
<div class="d-flex justify-content-end gap-2">
<a href="user-management.html" class="btn btn-secondary">
Cancel
</a>
<button type="submit" class="btn btn-primary">
<i class="bi bi-person-plus me-1"></i> Add User
</button>
</div>
</form>
</div>
</div>
</div>
</div>
</div>
{{end}}

144
templates/setting-user.html Normal file
View file

@ -0,0 +1,144 @@
{{template "base.html" .}}
{{define "title"}}Dash{{end}}
{{define "extraheader"}}
<style>
.form-check-input.switch-lg {
width: 3em;
height: 1.5em;
}
.status-badge {
width: 100px;
}
</style>
{{end}}
{{define "content"}}
<div class="container-fluid p-4">
<div class="d-flex justify-content-between align-items-center mb-4">
<h1 class="mb-0">User Management</h1>
<a href="{{ .URLs.SettingUserAdd }}" class="btn btn-primary" id="addUserBtn">
<i class="bi bi-plus-circle me-2"></i>Add New User
</a>
</div>
<div class="card">
<div class="card-body">
<div class="table-responsive">
<table class="table table-striped table-hover">
<thead class="table-light">
<tr>
<th>Full Name</th>
<th>Email Address</th>
<th>Username</th>
<th>Role</th>
<th>Serve Warrants</th>
<th>Status</th>
<th>Last Login</th>
<th>Actions</th>
</tr>
</thead>
<tbody>
<!-- Sample user data -->
<tr>
<td>John Doe</td>
<td>john.doe@example.com</td>
<td>johndoe</td>
<td>
<select class="form-select form-select-sm">
<option>Lead</option>
<option selected>Technician</option>
<option>Administrator</option>
</select>
</td>
<td>
<div class="form-check form-switch">
<input class="form-check-input switch-lg" type="checkbox" checked>
</div>
</td>
<td><span class="badge bg-success status-badge">Active</span></td>
<td>2023-06-15 09:45 AM</td>
<td>
<button class="btn btn-sm btn-warning" title="Deactivate">
<i class="bi bi-person-x"></i>
</button>
</td>
</tr>
<tr>
<td>Jane Smith</td>
<td>jane.smith@example.com</td>
<td>janesmith</td>
<td>
<select class="form-select form-select-sm">
<option selected>Lead</option>
<option>Technician</option>
<option>Administrator</option>
</select>
</td>
<td>
<div class="form-check form-switch">
<input class="form-check-input switch-lg" type="checkbox">
</div>
</td>
<td><span class="badge bg-success status-badge">Active</span></td>
<td>2023-06-17 14:20 PM</td>
<td>
<button class="btn btn-sm btn-warning" title="Deactivate">
<i class="bi bi-person-x"></i>
</button>
</td>
</tr>
<tr>
<td>Robert Johnson</td>
<td>robert.j@example.com</td>
<td>robertj</td>
<td>
<select class="form-select form-select-sm">
<option>Lead</option>
<option>Technician</option>
<option selected>Administrator</option>
</select>
</td>
<td>
<div class="form-check form-switch">
<input class="form-check-input switch-lg" type="checkbox" checked>
</div>
</td>
<td><span class="badge bg-secondary status-badge">Deactivated</span></td>
<td>2023-06-10 11:30 AM</td>
<td>
<button class="btn btn-sm btn-success" title="Activate">
<i class="bi bi-person-check"></i>
</button>
</td>
</tr>
<tr>
<td>Emily Wilson</td>
<td>emily.w@example.com</td>
<td>emilyw</td>
<td>
<select class="form-select form-select-sm">
<option>Lead</option>
<option selected>Technician</option>
<option>Administrator</option>
</select>
</td>
<td>
<div class="form-check form-switch">
<input class="form-check-input switch-lg" type="checkbox">
</div>
</td>
<td><span class="badge bg-warning text-dark status-badge">Invited</span></td>
<td>Never</td>
<td>
<button class="btn btn-sm btn-info" title="Resend Invitation">
<i class="bi bi-envelope"></i>
</button>
</td>
</tr>
</tbody>
</table>
</div>
</div>
</div>
</div>
{{end}}