Security fixes and schema cleanup
- Fix SQL injection in displayprofile.asp (parameterized query) - Add HTMLEncode to XSS-vulnerable output in 5 display pages - Add Option Explicit to computers.asp, displaymachines.asp, displaypcs.asp, displayapplication.asp, displayprofile.asp - Update STANDARDS.md with test script reference, secrets management, column naming gotchas - Fix equipment type ranges in CLAUDE.md and QUICK_REFERENCE.md (1-15, 21-25) - Add migration SQL to cleanup redundant PC machinetypes (34-46) 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
@@ -36,8 +36,8 @@ For production tasks, user must:
|
|||||||
|
|
||||||
```
|
```
|
||||||
machines table (unified)
|
machines table (unified)
|
||||||
├── Equipment (machinetypeid 1-24, pctypeid IS NULL)
|
├── Equipment (machinetypeid 1-15 and 21-25, pctypeid IS NULL)
|
||||||
├── PCs (machinetypeid 33-35, pctypeid IS NOT NULL)
|
├── PCs (machinetypeid 33+, pctypeid IS NOT NULL)
|
||||||
└── Network Devices (machinetypeid 16-20)
|
└── Network Devices (machinetypeid 16-20)
|
||||||
|
|
||||||
printers table (separate)
|
printers table (separate)
|
||||||
@@ -51,8 +51,9 @@ machinerelationships table (PC↔equipment links)
|
|||||||
-- All PCs
|
-- All PCs
|
||||||
SELECT * FROM machines WHERE pctypeid IS NOT NULL;
|
SELECT * FROM machines WHERE pctypeid IS NOT NULL;
|
||||||
|
|
||||||
-- All Equipment
|
-- All Equipment (excludes network devices and PCs)
|
||||||
SELECT * FROM machines WHERE pctypeid IS NULL AND machinetypeid < 16;
|
SELECT * FROM machines WHERE pctypeid IS NULL
|
||||||
|
AND machinetypeid NOT IN (16,17,18,19,20) AND machinetypeid < 33;
|
||||||
|
|
||||||
-- Network devices
|
-- Network devices
|
||||||
SELECT * FROM machines WHERE machinetypeid IN (16,17,18,19,20);
|
SELECT * FROM machines WHERE machinetypeid IN (16,17,18,19,20);
|
||||||
|
|||||||
@@ -1,3 +1,8 @@
|
|||||||
|
<%@ Language=VBScript %>
|
||||||
|
<%
|
||||||
|
Option Explicit
|
||||||
|
Dim theme, strSQL, rs, objConn
|
||||||
|
%>
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
@@ -6,7 +11,6 @@
|
|||||||
</head>
|
</head>
|
||||||
|
|
||||||
<%
|
<%
|
||||||
' Force IIS recompile - timestamp: 20251110-143600
|
|
||||||
theme = Request.Cookies("theme")
|
theme = Request.Cookies("theme")
|
||||||
IF theme = "" THEN
|
IF theme = "" THEN
|
||||||
theme="bg-theme1"
|
theme="bg-theme1"
|
||||||
@@ -61,7 +65,7 @@ While Not rsTypes.EOF
|
|||||||
If CStr(rsTypes("pctypeid")) = CStr(currentPCType) Then
|
If CStr(rsTypes("pctypeid")) = CStr(currentPCType) Then
|
||||||
selectedAttr = " selected"
|
selectedAttr = " selected"
|
||||||
End If
|
End If
|
||||||
Response.Write "<option value=""" & rsTypes("pctypeid") & """" & selectedAttr & ">" & rsTypes("typename") & "</option>" & vbCrLf
|
Response.Write "<option value=""" & rsTypes("pctypeid") & """" & selectedAttr & ">" & Server.HTMLEncode(rsTypes("typename") & "") & "</option>" & vbCrLf
|
||||||
rsTypes.MoveNext
|
rsTypes.MoveNext
|
||||||
Wend
|
Wend
|
||||||
rsTypes.Close
|
rsTypes.Close
|
||||||
@@ -77,7 +81,7 @@ While Not rsStatus.EOF
|
|||||||
If CStr(rsStatus("machinestatusid")) = CStr(currentPCStatus) Then
|
If CStr(rsStatus("machinestatusid")) = CStr(currentPCStatus) Then
|
||||||
selectedAttr = " selected"
|
selectedAttr = " selected"
|
||||||
End If
|
End If
|
||||||
Response.Write "<option value=""" & rsStatus("machinestatusid") & """" & selectedAttr & ">" & rsStatus("machinestatus") & "</option>" & vbCrLf
|
Response.Write "<option value=""" & rsStatus("machinestatusid") & """" & selectedAttr & ">" & Server.HTMLEncode(rsStatus("machinestatus") & "") & "</option>" & vbCrLf
|
||||||
rsStatus.MoveNext
|
rsStatus.MoveNext
|
||||||
Wend
|
Wend
|
||||||
rsStatus.Close
|
rsStatus.Close
|
||||||
@@ -162,20 +166,20 @@ Set rsStatus = Nothing
|
|||||||
while not rs.eof
|
while not rs.eof
|
||||||
|
|
||||||
%>
|
%>
|
||||||
<td><a href="./displaypc.asp?machineid=<%Response.Write(rs("machineid"))%>" title="Click to Show PC Details"><%
|
<td><a href="./displaypc.asp?machineid=<%=rs("machineid")%>" title="Click to Show PC Details"><%
|
||||||
Dim displayName
|
Dim displayName
|
||||||
If IsNull(rs("hostname")) Or rs("hostname") = "" Then
|
If IsNull(rs("hostname")) Or rs("hostname") = "" Then
|
||||||
displayName = rs("serialnumber")
|
displayName = rs("serialnumber") & ""
|
||||||
Else
|
Else
|
||||||
displayName = rs("hostname")
|
displayName = rs("hostname") & ""
|
||||||
End If
|
End If
|
||||||
Response.Write(displayName)
|
Response.Write(Server.HTMLEncode(displayName))
|
||||||
%></a></td>
|
%></a></td>
|
||||||
<td><%Response.Write(rs("serialnumber"))%></td>
|
<td><%=Server.HTMLEncode(rs("serialnumber") & "")%></td>
|
||||||
<td><%Response.Write(rs("ipaddress"))%></td>
|
<td><%=Server.HTMLEncode(rs("ipaddress") & "")%></td>
|
||||||
<td><%Response.Write(rs("modelnumber"))%></td>
|
<td><%=Server.HTMLEncode(rs("modelnumber") & "")%></td>
|
||||||
<td><%Response.Write(rs("operatingsystem"))%></td>
|
<td><%=Server.HTMLEncode(rs("operatingsystem") & "")%></td>
|
||||||
<td><a href="./search.asp?search=<%Response.Write(rs("machinenumber"))%>" title="Click to Show Machine Details"><%Response.Write(rs("machinenumber"))%></td>
|
<td><a href="./search.asp?search=<%=Server.URLEncode(rs("machinenumber") & "")%>" title="Click to Show Machine Details"><%=Server.HTMLEncode(rs("machinenumber") & "")%></a></td>
|
||||||
</tr>
|
</tr>
|
||||||
|
|
||||||
<%
|
<%
|
||||||
|
|||||||
@@ -1,6 +1,10 @@
|
|||||||
|
<%@ Language=VBScript %>
|
||||||
|
<%
|
||||||
|
Option Explicit
|
||||||
|
%>
|
||||||
<!--#include file="./includes/sql.asp"-->
|
<!--#include file="./includes/sql.asp"-->
|
||||||
<%
|
<%
|
||||||
Dim appid
|
Dim appid, rs
|
||||||
appid = Request.Querystring("appid")
|
appid = Request.Querystring("appid")
|
||||||
|
|
||||||
' Basic validation - must be numeric and positive
|
' Basic validation - must be numeric and positive
|
||||||
@@ -59,10 +63,10 @@
|
|||||||
<div class="col-lg-4">
|
<div class="col-lg-4">
|
||||||
<div class="card profile-card-2">
|
<div class="card profile-card-2">
|
||||||
<div class="card-img-block">
|
<div class="card-img-block">
|
||||||
<img class="img-fluid" src="./images/applications/<%Response.Write(rs("image"))%>" alt="Card image cap">
|
<img class="img-fluid" src="./images/applications/<%=Server.HTMLEncode(rs("image") & "")%>" alt="Card image cap">
|
||||||
</div>
|
</div>
|
||||||
<div class="card-body pt-5">
|
<div class="card-body pt-5">
|
||||||
<img src="./images/applications/<%Response.Write(rs("image"))%>" alt="profile-image" class="profile">
|
<img src="./images/applications/<%=Server.HTMLEncode(rs("image") & "")%>" alt="profile-image" class="profile">
|
||||||
<h5 class="card-title"></h5>
|
<h5 class="card-title"></h5>
|
||||||
<p class="card-text"><a href="" title="Click to Access Support Docs" target="_blank"></a></p>
|
<p class="card-text"><a href="" title="Click to Access Support Docs" target="_blank"></a></p>
|
||||||
</div>
|
</div>
|
||||||
@@ -85,7 +89,7 @@
|
|||||||
</ul>
|
</ul>
|
||||||
<div class="tab-content p-3">
|
<div class="tab-content p-3">
|
||||||
<div class="tab-pane active" id="profile">
|
<div class="tab-pane active" id="profile">
|
||||||
<h5 class="mb-3"><%Response.Write(rs("appname"))%></h5>
|
<h5 class="mb-3"><%=Server.HTMLEncode(rs("appname") & "")%></h5>
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-3">
|
<div class="col-md-3">
|
||||||
<p class="mb-2"><strong>Support Team:</strong></p>
|
<p class="mb-2"><strong>Support Team:</strong></p>
|
||||||
|
|||||||
@@ -1,3 +1,8 @@
|
|||||||
|
<%@ Language=VBScript %>
|
||||||
|
<%
|
||||||
|
Option Explicit
|
||||||
|
Dim theme, strSQL, rs, objConn
|
||||||
|
%>
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
@@ -105,21 +110,21 @@
|
|||||||
Response.write("<tr>")
|
Response.write("<tr>")
|
||||||
%>
|
%>
|
||||||
<td>
|
<td>
|
||||||
<span class="location-link" data-machineid="<%Response.Write(rs("machineid"))%>" style="cursor:pointer;">
|
<span class="location-link" data-machineid="<%=rs("machineid")%>" style="cursor:pointer;">
|
||||||
<i class="zmdi zmdi-pin"></i>
|
<i class="zmdi zmdi-pin"></i>
|
||||||
</span>
|
</span>
|
||||||
</td>
|
</td>
|
||||||
<td><a href="./displaymachine.asp?machineid=<%Response.Write(rs("machineid"))%>" title="View Machine Details"><%
|
<td><a href="./displaymachine.asp?machineid=<%=rs("machineid")%>" title="View Machine Details"><%
|
||||||
Dim displayName
|
Dim displayName
|
||||||
displayName = rs("machinenumber") & ""
|
displayName = rs("machinenumber") & ""
|
||||||
If displayName = "" Then displayName = rs("hostname") & ""
|
If displayName = "" Then displayName = rs("hostname") & ""
|
||||||
If displayName = "" Then displayName = "ID:" & rs("machineid")
|
If displayName = "" Then displayName = "ID:" & rs("machineid")
|
||||||
Response.Write(Server.HTMLEncode(displayName))
|
Response.Write(Server.HTMLEncode(displayName))
|
||||||
%></a></td>
|
%></a></td>
|
||||||
<td><%Response.Write(rs("machinetype"))%></td>
|
<td><%=Server.HTMLEncode(rs("machinetype") & "")%></td>
|
||||||
<td><%Response.Write(rs("vendor"))%></td>
|
<td><%=Server.HTMLEncode(rs("vendor") & "")%></td>
|
||||||
<td><%Response.Write(rs("modelnumber"))%></a></td>
|
<td><%=Server.HTMLEncode(rs("modelnumber") & "")%></td>
|
||||||
<td><%Response.Write(rs("businessunit"))%></td>
|
<td><%=Server.HTMLEncode(rs("businessunit") & "")%></td>
|
||||||
|
|
||||||
</tr>
|
</tr>
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,8 @@
|
|||||||
|
<%@ Language=VBScript %>
|
||||||
|
<%
|
||||||
|
Option Explicit
|
||||||
|
Dim theme, strSQL, rs, displayName, uptimeDays, hasVnc, hasWinrm, vncHost, objConn
|
||||||
|
%>
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
@@ -6,7 +11,7 @@
|
|||||||
</head>
|
</head>
|
||||||
|
|
||||||
<%
|
<%
|
||||||
' displaypcs.asp - PC List Page (Phase 2 Schema) - Last Updated: 20251110-1440
|
' displaypcs.asp - PC List Page (Phase 2 Schema)
|
||||||
theme = Request.Cookies("theme")
|
theme = Request.Cookies("theme")
|
||||||
IF theme = "" THEN
|
IF theme = "" THEN
|
||||||
theme="bg-theme1"
|
theme="bg-theme1"
|
||||||
@@ -148,7 +153,6 @@ Set rsStatus = Nothing
|
|||||||
<%
|
<%
|
||||||
' Build query based on filters
|
' Build query based on filters
|
||||||
Dim pcStatusFilter, winrmFilterSQL, deviceTypeFilterSQL, pcTypeFilterSQL, uptimeFilterSQL, needsRelationshipFilter, whereClause
|
Dim pcStatusFilter, winrmFilterSQL, deviceTypeFilterSQL, pcTypeFilterSQL, uptimeFilterSQL, needsRelationshipFilter, whereClause
|
||||||
Dim displayName, hasVnc, vncHost, hasWinrm, uptimeDays
|
|
||||||
pcStatusFilter = Request.QueryString("pcstatus")
|
pcStatusFilter = Request.QueryString("pcstatus")
|
||||||
winrmFilterSQL = Request.QueryString("winrm")
|
winrmFilterSQL = Request.QueryString("winrm")
|
||||||
deviceTypeFilterSQL = Request.QueryString("devicetype")
|
deviceTypeFilterSQL = Request.QueryString("devicetype")
|
||||||
@@ -221,17 +225,17 @@ Set rsStatus = Nothing
|
|||||||
|
|
||||||
%>
|
%>
|
||||||
<tr>
|
<tr>
|
||||||
<td><a href="./displaypc.asp?machineid=<%Response.Write(rs("machineid"))%>" title="Click to Show PC Details"><%
|
<td><a href="./displaypc.asp?machineid=<%=rs("machineid")%>" title="Click to Show PC Details"><%
|
||||||
If IsNull(rs("hostname")) Or rs("hostname") = "" Then
|
If IsNull(rs("hostname")) Or rs("hostname") = "" Then
|
||||||
displayName = rs("serialnumber")
|
displayName = rs("serialnumber") & ""
|
||||||
Else
|
Else
|
||||||
displayName = rs("hostname")
|
displayName = rs("hostname") & ""
|
||||||
End If
|
End If
|
||||||
Response.Write(displayName)
|
Response.Write(Server.HTMLEncode(displayName))
|
||||||
%></a></td>
|
%></a></td>
|
||||||
<td><%Response.Write(rs("serialnumber"))%></td>
|
<td><%=Server.HTMLEncode(rs("serialnumber") & "")%></td>
|
||||||
<td><%Response.Write(rs("modelnumber"))%></td>
|
<td><%=Server.HTMLEncode(rs("modelnumber") & "")%></td>
|
||||||
<td><%Response.Write(rs("operatingsystem"))%></td>
|
<td><%=Server.HTMLEncode(rs("operatingsystem") & "")%></td>
|
||||||
<td><%
|
<td><%
|
||||||
' Equipment relationship column
|
' Equipment relationship column
|
||||||
If Not IsNull(rs("equipment_id")) And rs("equipment_id") <> "" Then
|
If Not IsNull(rs("equipment_id")) And rs("equipment_id") <> "" Then
|
||||||
|
|||||||
@@ -1,3 +1,7 @@
|
|||||||
|
<%@ Language=VBScript %>
|
||||||
|
<%
|
||||||
|
Option Explicit
|
||||||
|
%>
|
||||||
<!DOCTYPE html>
|
<!DOCTYPE html>
|
||||||
<html lang="en">
|
<html lang="en">
|
||||||
<head>
|
<head>
|
||||||
@@ -8,12 +12,19 @@
|
|||||||
</head>
|
</head>
|
||||||
|
|
||||||
<%
|
<%
|
||||||
|
Dim theme, sso, strSQL, rs, cmd
|
||||||
|
|
||||||
theme = Request.Cookies("theme")
|
theme = Request.Cookies("theme")
|
||||||
IF theme = "" THEN
|
IF theme = "" THEN
|
||||||
theme="bg-theme1"
|
theme="bg-theme1"
|
||||||
END IF
|
END IF
|
||||||
|
|
||||||
|
' Validate SSO - must be numeric
|
||||||
sso = Request.Querystring("sso")
|
sso = Request.Querystring("sso")
|
||||||
|
If Not IsNumeric(sso) Or sso = "" Then
|
||||||
|
sso = "1"
|
||||||
|
End If
|
||||||
|
sso = CLng(sso)
|
||||||
%>
|
%>
|
||||||
|
|
||||||
<body class="bg-theme <%Response.Write(theme)%>">
|
<body class="bg-theme <%Response.Write(theme)%>">
|
||||||
@@ -45,20 +56,33 @@
|
|||||||
<div class="card-img-block">
|
<div class="card-img-block">
|
||||||
|
|
||||||
<%
|
<%
|
||||||
|
' Use parameterized query to prevent SQL injection
|
||||||
|
Set cmd = Server.CreateObject("ADODB.Command")
|
||||||
|
cmd.ActiveConnection = objconn
|
||||||
|
cmd.CommandText = "SELECT * FROM employees WHERE SSO = ?"
|
||||||
|
cmd.CommandType = 1
|
||||||
|
cmd.Parameters.Append cmd.CreateParameter("@sso", 3, 1, , sso)
|
||||||
|
Set rs = cmd.Execute()
|
||||||
|
|
||||||
strSQL = "SELECT * from employees WHERE SSO="&sso
|
If rs.EOF Then
|
||||||
set rs = objconn.Execute(strSQL)
|
' Default to SSO 1 if not found
|
||||||
if rs.eof THEN
|
rs.Close
|
||||||
strSQL = "SELECT * from employees WHERE SSO=1"
|
Set rs = Nothing
|
||||||
set rs = objconn.Execute(strSQL)
|
Set cmd = Nothing
|
||||||
END IF
|
Set cmd = Server.CreateObject("ADODB.Command")
|
||||||
|
cmd.ActiveConnection = objconn
|
||||||
|
cmd.CommandText = "SELECT * FROM employees WHERE SSO = ?"
|
||||||
|
cmd.CommandType = 1
|
||||||
|
cmd.Parameters.Append cmd.CreateParameter("@sso", 3, 1, , 1)
|
||||||
|
Set rs = cmd.Execute()
|
||||||
|
End If
|
||||||
|
Set cmd = Nothing
|
||||||
%>
|
%>
|
||||||
|
|
||||||
<img class="img-fluid" src="https://tsgwp00525.rd.ds.ge.com/EmployeeDBAPP/images/<%Response.Write(rs("Picture"))%>" alt="Card image cap">
|
<img class="img-fluid" src="https://tsgwp00525.rd.ds.ge.com/EmployeeDBAPP/images/<%=Server.HTMLEncode(rs("Picture") & "")%>" alt="Card image cap">
|
||||||
</div>
|
</div>
|
||||||
<div class="card-body pt-5">
|
<div class="card-body pt-5">
|
||||||
<h5 class="card-title"><%Response.Write(rs("First_Name"))%> <%Response.Write(rs("Last_Name"))%></h5>
|
<h5 class="card-title"><%=Server.HTMLEncode(rs("First_Name") & "")%> <%=Server.HTMLEncode(rs("Last_Name") & "")%></h5>
|
||||||
</div>
|
</div>
|
||||||
<%
|
<%
|
||||||
' Easter Egg for SSO 570005354
|
' Easter Egg for SSO 570005354
|
||||||
@@ -234,7 +258,7 @@ END IF
|
|||||||
<h5 class="mb-3">Profile</h5>
|
<h5 class="mb-3">Profile</h5>
|
||||||
<div class="row">
|
<div class="row">
|
||||||
<div class="col-md-3">
|
<div class="col-md-3">
|
||||||
<h6><%Response.Write(rs("First_Name"))%> <%Response.Write(rs("Last_Name"))%></h6>
|
<h6><%=Server.HTMLEncode(rs("First_Name") & "")%> <%=Server.HTMLEncode(rs("Last_Name") & "")%></h6>
|
||||||
<h6>SSO</h6>
|
<h6>SSO</h6>
|
||||||
<h6>Shift</h6>
|
<h6>Shift</h6>
|
||||||
<h6>Role</h6>
|
<h6>Role</h6>
|
||||||
@@ -243,11 +267,11 @@ END IF
|
|||||||
</div>
|
</div>
|
||||||
<div class="col-md-6">
|
<div class="col-md-6">
|
||||||
<h6> <h6>
|
<h6> <h6>
|
||||||
<h6><%Response.Write(rs("SSO"))%></h6>
|
<h6><%=Server.HTMLEncode(rs("SSO") & "")%></h6>
|
||||||
<h6><%Response.Write(rs("shift"))%></h6>
|
<h6><%=Server.HTMLEncode(rs("shift") & "")%></h6>
|
||||||
<h6><%Response.Write(rs("Role"))%></h6>
|
<h6><%=Server.HTMLEncode(rs("Role") & "")%></h6>
|
||||||
<h6><%Response.Write(rs("Team"))%></h6>
|
<h6><%=Server.HTMLEncode(rs("Team") & "")%></h6>
|
||||||
<h6><%Response.Write(rs("Payno"))%></h6>
|
<h6><%=Server.HTMLEncode(rs("Payno") & "")%></h6>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<!--/row-->
|
<!--/row-->
|
||||||
|
|||||||
@@ -39,9 +39,10 @@ machines (machineid, hostname, serialnumber, alias, machinenumber,
|
|||||||
loggedinuser, machinenotes, isactive, maptop, mapleft, lastupdated)
|
loggedinuser, machinenotes, isactive, maptop, mapleft, lastupdated)
|
||||||
|
|
||||||
-- Identify record type:
|
-- Identify record type:
|
||||||
-- PCs: pctypeid IS NOT NULL (machinetypeid 33-35)
|
-- PCs: pctypeid IS NOT NULL (machinetypeid 33+)
|
||||||
-- Equipment: pctypeid IS NULL AND machinetypeid < 16
|
-- Equipment: pctypeid IS NULL AND machinetypeid NOT IN (16,17,18,19,20) AND machinetypeid < 33
|
||||||
-- Network Devices: machinetypeid IN (16,17,18,19,20)
|
-- Network Devices: machinetypeid IN (16,17,18,19,20)
|
||||||
|
-- Equipment types: 1-15, 21-25 (e.g., Lathe, Mill, CMM, Hobbing Machine, etc.)
|
||||||
```
|
```
|
||||||
|
|
||||||
### PC-Related Tables
|
### PC-Related Tables
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
# Classic ASP Development Standards
|
# Classic ASP Development Standards
|
||||||
## ShopDB Application
|
## ShopDB Application
|
||||||
|
|
||||||
**Version:** 1.0
|
**Version:** 1.1
|
||||||
**Last Updated:** 2025-10-10
|
**Last Updated:** 2025-12-11
|
||||||
**Status:** MANDATORY for all new development and modifications
|
**Status:** MANDATORY for all new development and modifications
|
||||||
|
|
||||||
---
|
---
|
||||||
@@ -414,7 +414,7 @@ Standard error codes for user messaging:
|
|||||||
' - machines (primary)
|
' - machines (primary)
|
||||||
' - machinetypes, models, vendors, businessunits
|
' - machinetypes, models, vendors, businessunits
|
||||||
' - printers (LEFT JOIN - may be NULL)
|
' - printers (LEFT JOIN - may be NULL)
|
||||||
' - pc (LEFT JOIN - may be NULL)
|
' - communications (LEFT JOIN - may be NULL)
|
||||||
'
|
'
|
||||||
' SECURITY:
|
' SECURITY:
|
||||||
' - Requires authentication
|
' - Requires authentication
|
||||||
@@ -691,9 +691,9 @@ Sub LogError(source, errorNum, errorDesc)
|
|||||||
**Style:** lowercase, plural nouns
|
**Style:** lowercase, plural nouns
|
||||||
|
|
||||||
```sql
|
```sql
|
||||||
machines
|
machines -- Unified table: Equipment, PCs, Network Devices
|
||||||
printers
|
printers
|
||||||
pc (exception - acronym)
|
communications -- Network interfaces (IP/MAC)
|
||||||
machinetypes
|
machinetypes
|
||||||
vendors
|
vendors
|
||||||
models
|
models
|
||||||
@@ -713,6 +713,23 @@ createdate
|
|||||||
lastupdated
|
lastupdated
|
||||||
```
|
```
|
||||||
|
|
||||||
|
### Column Naming Gotchas
|
||||||
|
|
||||||
|
**IMPORTANT:** Be aware of these non-obvious column names:
|
||||||
|
|
||||||
|
| Expected | Actual | Table |
|
||||||
|
|----------|--------|-------|
|
||||||
|
| `ipaddress` | `address` | communications |
|
||||||
|
| `gateway` | `defaultgateway` | communications |
|
||||||
|
| `notes` | `machinenotes` | machines |
|
||||||
|
| `pcid` | `machineid` | machines (PCs are in unified table) |
|
||||||
|
| `pc_comm_config` | `commconfig` | (table name) |
|
||||||
|
| `pc_dnc_config` | `dncconfig` | (table name) |
|
||||||
|
|
||||||
|
**PC Identification:** PCs are in the `machines` table, identified by:
|
||||||
|
- `pctypeid IS NOT NULL`
|
||||||
|
- `machinetypeid IN (33, 34, 35)`
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
## Documentation Standards
|
## Documentation Standards
|
||||||
@@ -904,6 +921,22 @@ Response.Write(RenderCachedUnitDropdown())
|
|||||||
|
|
||||||
## Testing Standards
|
## Testing Standards
|
||||||
|
|
||||||
|
### Automated Form Testing
|
||||||
|
|
||||||
|
**REQUIRED:** Run the comprehensive test suite after making changes to ASP pages.
|
||||||
|
|
||||||
|
```bash
|
||||||
|
./tests/test_forms.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
This script tests 41 endpoints including:
|
||||||
|
- Page load tests (dashboards, list views, maps)
|
||||||
|
- Add form page loads
|
||||||
|
- Form submissions (notifications, equipment, printers, subnets, applications, KB, vendors, models, network devices)
|
||||||
|
- API endpoints
|
||||||
|
|
||||||
|
Test data uses `AUTOTEST_` prefix for easy cleanup. See `tests/cleanup_test_data.sql`.
|
||||||
|
|
||||||
### Unit Testing
|
### Unit Testing
|
||||||
|
|
||||||
**REQUIRED:** Test all validation functions.
|
**REQUIRED:** Test all validation functions.
|
||||||
@@ -1021,6 +1054,20 @@ Before committing code, verify:
|
|||||||
2. Never commit `config.asp` to source control
|
2. Never commit `config.asp` to source control
|
||||||
3. Add `config.asp` to `.gitignore`
|
3. Add `config.asp` to `.gitignore`
|
||||||
|
|
||||||
|
### Secrets Management
|
||||||
|
|
||||||
|
**MANDATORY:** Store sensitive credentials in `secrets.md` (gitignored).
|
||||||
|
|
||||||
|
**Contents:**
|
||||||
|
- Zabbix API URL and token
|
||||||
|
- Gitea API URL and token
|
||||||
|
- Database credentials (per environment)
|
||||||
|
|
||||||
|
**NEVER commit:**
|
||||||
|
- API tokens
|
||||||
|
- Database passwords
|
||||||
|
- Authentication credentials
|
||||||
|
|
||||||
### Configuration Template
|
### Configuration Template
|
||||||
|
|
||||||
```vbscript
|
```vbscript
|
||||||
@@ -1216,6 +1263,7 @@ Call CleanupResources()
|
|||||||
| Version | Date | Changes | Author |
|
| Version | Date | Changes | Author |
|
||||||
|---------|------|---------|--------|
|
|---------|------|---------|--------|
|
||||||
| 1.0 | 2025-10-10 | Initial standards document created from audit findings | Claude |
|
| 1.0 | 2025-10-10 | Initial standards document created from audit findings | Claude |
|
||||||
|
| 1.1 | 2025-12-11 | Updated for Phase 2 schema (unified machines table), added test script reference, secrets management, column naming gotchas | Claude |
|
||||||
|
|
||||||
---
|
---
|
||||||
|
|
||||||
|
|||||||
110
sql/migration_cleanup_pc_types.sql
Normal file
110
sql/migration_cleanup_pc_types.sql
Normal file
@@ -0,0 +1,110 @@
|
|||||||
|
-- ============================================================================
|
||||||
|
-- ShopDB Database Migration: Cleanup Redundant PC Machinetypes
|
||||||
|
-- Date: 2025-12-12
|
||||||
|
-- Purpose: Remove redundant PC machinetypes (34-46) since pctypeid handles categorization
|
||||||
|
-- ============================================================================
|
||||||
|
--
|
||||||
|
-- CHANGES:
|
||||||
|
-- 1. Add primary key to installedapps table
|
||||||
|
-- 2. Migrate machines using PC-specific machinetypes to generic PC (33) + pctypeid
|
||||||
|
-- 3. Update models to use generic PC machinetype
|
||||||
|
-- 4. Remove unused PC machinetypes (34-43, 45-46), keep USB Device (44)
|
||||||
|
--
|
||||||
|
-- RUN ON: Production database
|
||||||
|
-- BACKUP FIRST: mysqldump -u root -p shopdb > shopdb_backup_$(date +%Y%m%d).sql
|
||||||
|
-- ============================================================================
|
||||||
|
|
||||||
|
-- Start transaction for safety
|
||||||
|
START TRANSACTION;
|
||||||
|
|
||||||
|
-- ============================================================================
|
||||||
|
-- 1. ADD PRIMARY KEY TO INSTALLEDAPPS TABLE
|
||||||
|
-- ============================================================================
|
||||||
|
ALTER TABLE installedapps
|
||||||
|
ADD COLUMN installedappid INT AUTO_INCREMENT PRIMARY KEY FIRST;
|
||||||
|
|
||||||
|
SELECT 'Added PK to installedapps' AS status;
|
||||||
|
|
||||||
|
-- ============================================================================
|
||||||
|
-- 2. MIGRATE MACHINES FROM PC-SPECIFIC TYPES TO GENERIC PC (33) + PCTYPEID
|
||||||
|
-- ============================================================================
|
||||||
|
|
||||||
|
-- PC - Standard (36) → machinetypeid=33, pctypeid=1 (Standard)
|
||||||
|
UPDATE machines
|
||||||
|
SET machinetypeid = 33, pctypeid = 1
|
||||||
|
WHERE machinetypeid = 36;
|
||||||
|
|
||||||
|
SELECT CONCAT('Migrated ', ROW_COUNT(), ' PC-Standard machines') AS status;
|
||||||
|
|
||||||
|
-- PC - CMM (41) → machinetypeid=33, pctypeid=5 (CMM)
|
||||||
|
UPDATE machines
|
||||||
|
SET machinetypeid = 33, pctypeid = 5
|
||||||
|
WHERE machinetypeid = 41;
|
||||||
|
|
||||||
|
SELECT CONCAT('Migrated ', ROW_COUNT(), ' PC-CMM machines') AS status;
|
||||||
|
|
||||||
|
-- Handle any other PC types that might exist in production
|
||||||
|
-- PC - Shopfloor (37) → machinetypeid=33, pctypeid=3 (Shopfloor)
|
||||||
|
UPDATE machines
|
||||||
|
SET machinetypeid = 33, pctypeid = 3
|
||||||
|
WHERE machinetypeid = 37 AND pctypeid IS NULL;
|
||||||
|
|
||||||
|
-- PC - Engineer (38) → machinetypeid=33, pctypeid=2 (Engineer)
|
||||||
|
UPDATE machines
|
||||||
|
SET machinetypeid = 33, pctypeid = 2
|
||||||
|
WHERE machinetypeid = 38 AND pctypeid IS NULL;
|
||||||
|
|
||||||
|
-- PC - Wax Trace (42) → machinetypeid=33, pctypeid=6 (Wax / Trace)
|
||||||
|
UPDATE machines
|
||||||
|
SET machinetypeid = 33, pctypeid = 6
|
||||||
|
WHERE machinetypeid = 42 AND pctypeid IS NULL;
|
||||||
|
|
||||||
|
-- Catch-all: Any remaining 34-46 → machinetypeid=33, pctypeid=4 (Uncategorized)
|
||||||
|
UPDATE machines
|
||||||
|
SET machinetypeid = 33, pctypeid = 4
|
||||||
|
WHERE machinetypeid BETWEEN 34 AND 46 AND pctypeid IS NULL;
|
||||||
|
|
||||||
|
SELECT CONCAT('Total machines now using machinetypeid 34-46: ',
|
||||||
|
(SELECT COUNT(*) FROM machines WHERE machinetypeid BETWEEN 34 AND 46)) AS status;
|
||||||
|
|
||||||
|
-- ============================================================================
|
||||||
|
-- 3. UPDATE MODELS TO USE GENERIC PC MACHINETYPE (33)
|
||||||
|
-- ============================================================================
|
||||||
|
UPDATE models
|
||||||
|
SET machinetypeid = 33
|
||||||
|
WHERE machinetypeid BETWEEN 34 AND 46;
|
||||||
|
|
||||||
|
SELECT CONCAT('Updated ', ROW_COUNT(), ' models to generic PC type') AS status;
|
||||||
|
|
||||||
|
-- ============================================================================
|
||||||
|
-- 4. DELETE REDUNDANT MACHINETYPES
|
||||||
|
-- ============================================================================
|
||||||
|
-- Keep 33 (PC) and 44 (USB Device), remove 34-43 and 45-46
|
||||||
|
|
||||||
|
DELETE FROM machinetypes WHERE machinetypeid BETWEEN 34 AND 43;
|
||||||
|
SELECT CONCAT('Deleted ', ROW_COUNT(), ' machinetypes (34-43)') AS status;
|
||||||
|
|
||||||
|
DELETE FROM machinetypes WHERE machinetypeid BETWEEN 45 AND 46;
|
||||||
|
SELECT CONCAT('Deleted ', ROW_COUNT(), ' machinetypes (45-46)') AS status;
|
||||||
|
|
||||||
|
-- ============================================================================
|
||||||
|
-- VERIFICATION
|
||||||
|
-- ============================================================================
|
||||||
|
SELECT 'VERIFICATION - Remaining machinetypes >= 33:' AS info;
|
||||||
|
SELECT machinetypeid, machinetype FROM machinetypes WHERE machinetypeid >= 33;
|
||||||
|
|
||||||
|
SELECT 'VERIFICATION - Machines by pctypeid:' AS info;
|
||||||
|
SELECT pt.typename, COUNT(*) as count
|
||||||
|
FROM machines m
|
||||||
|
JOIN pctype pt ON m.pctypeid = pt.pctypeid
|
||||||
|
WHERE m.pctypeid IS NOT NULL
|
||||||
|
GROUP BY m.pctypeid
|
||||||
|
ORDER BY count DESC;
|
||||||
|
|
||||||
|
-- ============================================================================
|
||||||
|
-- COMMIT (uncomment when ready to apply)
|
||||||
|
-- ============================================================================
|
||||||
|
COMMIT;
|
||||||
|
-- ROLLBACK; -- Use this instead if something looks wrong
|
||||||
|
|
||||||
|
SELECT 'Migration completed successfully!' AS status;
|
||||||
Reference in New Issue
Block a user