Quality Control - [QC Entry]
Doubt
- In QC1 delete not given. From QC main how can I delete uploaded file since there will be different item grps. Should I delete using foreach? -
No we will delete using yearqcno as prefix - Grn lines without TrnId we will not take right even for manual? -
Yes - Need to add document Validation for uploaded certificate using AI. -
Next Round - GRN is only for Incoming. So other options for QC Stage should I hide for now? -
Yes - Download Certificate not working due to credential issue
- Ref Doc we will store GRN, Invoice, SCN like this? -
3 Characters. INV, GRN etc. - Checked By and Approved By should we do upper case and then insert? -
No - Report No it is generating as “R-000001-008” i.e “R-{qcno}-{itemgrpcode}” -
Ok - Mix & manual we will remove, everything should be done through test plan. Upload/Download Certificate we will keep -
Next Round
Objective
- The QC module manages quality inspections for business documents like:
- Goods Receipt (Incoming QC)
- Production (In-Process QC)
- Invoice (Outgoing QC)
- It supports:
- Manual QC (certificate-based)
- System QC (parameter-based validation)
- Mix QC (Combination of System + Manual based on item groups)
Data Model Overview
QC_Main (Header)
↓
QC_Line (Item Group Level)
↓
QC_Parameter (Parameter Level – only for system/mix mode)Quality Control (QC) Process Flow
flowchart TD
Start([Start])
Start --> QC["QC (Header)
Stores QC Stage, Reference GRN, Mode & Overall Status"]
QC --> Fetch["Fetch Distinct Item Groups
from Reference GRN"]
Fetch --> QC1["QC1 (Item Groups)
Stores Item Group, Test Plan,
Report Details & Item Status"]
QC1 --> Decision{"Test Plan Available?"}
Decision -- No --> Manual["Manual QC
Upload Certificate
Enter Report Details
Select Pass / Fail"]
Decision -- Yes --> QC2["QC2 (Inspection Parameters)
Parameter Records Autofetched and Inserted"]
QC2 --> Bulk Update["Bulk Update Inspection Values"]
Bulk Update --> Evaluate["Evaluate Parameter Results"]
Manual --> UpdateQC1["Automatically Update QC1 Item Status"]
Evaluate --> UpdateQC1
UpdateQC1 --> UpdateQC["Automatically Update Overall QC Status"]
UpdateQC --> End([End])Tables
CREATE TABLE QualityControl
(
Id INT IDENTITY(1,1) PRIMARY KEY,
qcno NVARCHAR(6),
qcDate DATETIME,
yearqcno NVARCHAR(12),
qcStage NVARCHAR(3), -- IQC (Incoming), PQC (In process), FQC (Final)
refDoc NVARCHAR(20), -- GRN (Currently restricted)
refNo NVARCHAR(6),
refDate DATETIME,
mode NVARCHAR(1), -- S (System), M (Manual), X (Mix)
qcStatus NVARCHAR(1), -- O (Open), C (Closed), P (Partial)
checkedBy NVARCHAR(25),
approvedBy NVARCHAR(25)
);
CREATE TABLE QualityControl1
(
Id INT IDENTITY(1,1) PRIMARY KEY,
qcno NVARCHAR(6),
yearqcno NVARCHAR(12),
itemgrpid NVARCHAR(3),
testplancode NVARCHAR(6), -- (0 for Manual)
reportNo NVARCHAR(20),
reportDate DATETIME,
itemQcStatus NVARCHAR(1), -- Pending (N), P (Pass), F (Fail)
remarks NVARCHAR(150)
);
CREATE TABLE QualityControl2
(
Id INT IDENTITY(1,1) PRIMARY KEY,
qcno NVARCHAR(6),
yearqcno NVARCHAR(12),
itemgrpid NVARCHAR(3),
parameterCode NVARCHAR(6),
actualValue DECIMAL(7,3),
result NVARCHAR(1) -- Pending (N), P (Pass), F (Fail)
);QC Main Level
QC Index
Fields
| Column | Property |
|---|---|
| QC No | QcNo |
| QC Date | QcDate |
| QC Stage | QcStageName |
| Ref Doc | RefDoc |
| Mode | QcModeName |
| Status | QcStatusName |
Buttons
- Create
QC Details
Fields
| Column | Property |
|---|---|
| QC No | QcNo |
| QC Date | QcDate |
| QC Stage | QcStageName |
| Ref Doc | RefDoc |
| Ref No | RefNo |
| Ref Date | RefDate |
| QC Mode | QcModeName |
| Status | QcStatusName |
| Approved By | ApprovedBy |
| Approve QC | Link Show if QCState is Closed and approvedby is empty |
Buttons
- Create
- Delete
- Back
Delete Validation
| Message | Condition |
|---|---|
| QC is Approved. You may not delete it. | If approved by is not empty |
QC Create
Fields
| Column | Property | Model Class Validation |
|---|---|---|
| QC Date | QcDate | |
QC Stage HardCoded Combo |
QcStageCode | QC Stage needs to be selected |
Ref Doc HardCoded Combo |
RefDoc | Ref Doc needs to be selected |
| Ref No | RefNo | 1. Ref No needs to be filled 2. Ref No can be upto 6 digits only |
| Ref Date | RefDate | |
QC Mode HardCoded Combo |
QcMode | QC Mode needs to be selected |
Hard Coded combo values
QC Stage
- IQC (Incoming)
- PQC (In-Process)
- FQC (Final)
Ref Doc (Currently restricted)
- GRN
Mode
- S (System)
- M (Manual)
- X (Mix)
Validations
| Message | Condition |
|---|---|
| Invalid Ref No / Ref Date | If not found in GRN |
| No lines found with QR generated. | If GRN has no items with qr generated |
| Duplicate QC Entry | If QC exists for same RefNo |
| Test plan available for all item groups. Mode should be system. | If manual or mixed is selected when test plan is available for all item groups. |
| Test plan missing for all item groups. Mode should be manual. | If system or mixed is selected when test plan not found for any item group. |
| Test plan is available for some item groups and missing for some. Mode should be mixed. | If manual or system is selected when partial test plans are available. |
| One or more item groups are linked to Test Plans that do not contain any test parameters. Please update. | If not manual and there exists test plan for correspomding item groups where test parameters are not added. |
Validation Queries
public int GetRefDocExistCnt(string refNo, DateTime? refDate, string dbname)
{
var query = @"SELECT COUNT(*) FROM Grn
WHERE grnNo = @refNo AND CONVERT(DATE, dated) = @refDate";
using var connection = _DapperContext.SetClientConnection(dbname);
var count = connection.QuerySingleOrDefault<int>(query, new { refNo, refDate = refDate?.Date });
return count;
}
public int GetDuplicateQcCount(string refNo, DateTime? refDate, string refDoc, int id, string dbname)
{
var query = @"SELECT COUNT(*) FROM QualityControl
WHERE refNo = @refNo AND CONVERT(DATE, refdate) = @refDate
AND refDoc = @refDoc AND Id != @id";
using var connection = _DapperContext.SetClientConnection(dbname);
var count = connection.QuerySingleOrDefault<int>(query, new { refNo, refDate = refDate?.Date, refDoc, id });
return count;
}
public int GetRefDocLineCount(string refNo, DateTime? refDate, string dbname)
{
var query = @"SELECT COUNT(*) FROM Grn1 G1
LEFT JOIN Grn G ON G1.yeargrnno = G.yeargrnno
WHERE G.grnno = @refNo AND CONVERT(DATE, dated) = @refDate
AND COALESCE(trnid, '') != ''";
using var connection = _DapperContext.SetClientConnection(dbname);
var count = connection.QuerySingleOrDefault<int>(query, new { refNo, refDate = refDate?.Date });
return count;
}
public string GetItemGroupsPlanStatus(string refNo, DateTime? refDate, string qcStageCode, string dbname)
{
var query = @"WITH A (itemgroupcode, hastestplancnt, recordcnt) AS
(
SELECT DISTINCT I.itemgroupid AS ItemGroupCode, IIF(TP.testPlanCode IS NULL, 0, 1) AS hastestplancnt, 1 AS recordcnt
FROM Grn1 G1
LEFT JOIN Grn G ON G1.yeargrnno = G.yeargrnno
LEFT JOIN inventorymst I ON G1.itemid = I.itemid
LEFT JOIN TestPlanMst TP ON I.itemgroupid = TP.itemgroupid AND TP.qcStage = @qcStageCode AND TP.isactive = 'Y'
WHERE G.grnno = @refNo AND CONVERT(DATE, dated) = @refDate
AND COALESCE(trnid, '') != ''
),
B (hastestplancnt, recordcnt) AS
(
SELECT SUM(hastestplancnt) AS hastestplancnt,
SUM(recordcnt) AS recordcnt FROM A
)
SELECT IIF(hastestplancnt = 0, 'M',
IIF(hastestplancnt = recordcnt, 'S', 'X')) AS ind FROM B";
using var connection = _DapperContext.SetClientConnection(dbname);
var data = connection.QuerySingleOrDefault<string>(query, new { refNo, refDate = refDate?.Date, qcStageCode });
return data;
}
public int GetTestPlanLineCount(string refNo, DateTime? refDate, string qcStageCode, string dbname)
{
var query = @"WITH A (itemgroupid, lineCnt, recordcnt) AS
(
SELECT DISTINCT
I.itemgroupid,
IIF
(
EXISTS
(
SELECT 1
FROM TestPlanMst1 TP1
WHERE TP1.testPlanCode = TP.testPlanCode
),
1,
0
) AS lineCnt,
1 AS recordcnt
FROM Grn1 G1
LEFT JOIN Grn G ON G1.yeargrnno = G.yeargrnno
LEFT JOIN inventorymst I ON G1.itemid = I.itemid
LEFT JOIN TestPlanMst TP ON I.itemgroupid = TP.itemgroupid AND TP.qcStage = @qcStageCode AND TP.isactive = 'Y'
WHERE G.grnno = @refNo AND CONVERT(DATE, dated) = @refDate
AND COALESCE(trnid, '') != ''
AND TP.testplancode IS NOT NULL
),
B (lineCnt, recordcnt) AS
(
SELECT SUM(lineCnt) AS lineCnt,
SUM(recordcnt) AS recordcnt FROM A
)
SELECT IIF(lineCnt < recordCnt, 0, 1) AS cnt FROM B";
using var connection = _DapperContext.SetClientConnection(dbname);
var data = connection.QuerySingleOrDefault<int>(query, new { refNo, refDate = refDate?.Date, qcStageCode });
return data;
}
public List<QualityControl1> GetRefDocItemGroups(string refNo, DateTime? refDate, string qcStageCode, string dbname)
{
var query = @"SELECT DISTINCT I.itemgroupid AS ItemGroupCode,
COALESCE(TP.testPlanCode, '0') AS testPlanCode
FROM Grn1 G1
LEFT JOIN Grn G ON G1.yeargrnno = G.yeargrnno
LEFT JOIN inventorymst I ON G1.itemid = I.itemid
LEFT JOIN TestPlanMst TP ON I.itemgroupid = TP.itemgroupid AND TP.qcStage = @qcStageCode AND TP.isactive = 'Y'
WHERE G.grnno = @refNo AND CONVERT(DATE, dated) = @refDate
AND COALESCE(trnid, '') != ''";
using var connection = _DapperContext.SetClientConnection(dbname);
var data = connection.Query<QualityControl1>(query, new { refNo, refDate = refDate?.Date, qcStageCode });
return data.ToList();
}Points
- QC No & YearQCNo → System generated
- Default Status → O (OPEN)
Mode Determination Logic
| Condition | Mode |
|---|---|
| All item groups have test plan | S |
| None have test plan | M |
| Partial availability | X |
Processing Logic
Manual Mode
- QC1 populated with item groups
- testplancode = 0
- User must:
- Upload certificate (per item group)
- Enter Report No & Date
- Select the QC Status for that item group
- QC2 → NOT used
System Mode
- QC1 populated with item groups
- testplancode assigned
- QC2 populated with parameters
- Report No → Auto generated
- Report Date →
DateTime.Now
Mix Mode
- Item groups with test plan → System
- Item groups without → Manual
Print Report PDF
Header
- QC No
LEFT ALIGN - QC Date
LEFT ALIGN - QC Mode
LEFT ALIGN - Overall Result
RIGHT ALIGN - QC Status
RIGHT ALIGN - Approval Status
RIGHT ALIGN
Reference Information
- Reference Document
LEFT ALIGN - Reference Number
LEFT ALIGN - Reference Date
LEFT ALIGN - Checked By
RIGHT ALIGN - Approved By
RIGHT ALIGN
Inspection Summary
- Sr No
- Item Group
- Report No
- Report Date
- Test Plan
- Result
- QA Remark
Detailed Inspection Results
Header
- Item Group
- Report No
- Report Date
Details
- Sr No
- Parameter Name
- Parameter Type
- Value
- Range
- Result
Certificate
- The inspected material(s) have been verified against the defined quality control requirements and found to conform to all applicable acceptance criteria.
- Material Status
Footer
- Checked By
- Approved By
- Generated By
QC Line Level 1
- Records will be autofetched and inserted from Reference Document.
- For System model Report Number and date will be generated by System.
- For Manaual mode Report Number and date will be given by user.
- User can also write remarks.
- Initially Item QC Status will be inserted as
Pending
QC 1 Index
Fields
| Column | Property |
|---|---|
| QC No | QcNo |
| Item Group | ItemGroupName |
| Test Plan Code | TestPlanCode |
| Item QC Status | ItemQcStatusName |
QC 1 Details
Main Fields
| Column | Property |
|---|---|
| QC No | QcNo |
| Item Group | ItemGroupName |
| Test Plan Code | TestPlanCode |
| Test Plan Name | TestPlanName Show if TestPlanCode != "0" |
| Report No | ReportNo |
| Report Date | ReportDate |
| Item QC Status | ItemQcStatusName |
| QA Remark | Remarks |
Sub Fields Show only if testplancode != "0"
| Column | Property |
|---|---|
| Parameter Code | ParameterCode |
| Parameter Name | ParameterName |
| Parameter Type | ParameterTypeName |
| Value | If Type User then ResultName else ActualValue |
| Result | ResultName |
Buttons
- Modify QA Remark
Dialog Box - Upload / Download Certificate
Show only if testplancode = "0" - Bulk Update
Show only if testplancode != "0"
QC 1 Upload
Fields
| Column | Property |
|---|---|
QC No Read only |
QcNo |
| Item Group | ItemGroupName |
| Report No | ReportNo |
| Report Date | ReportDate |
Item QC Status Hardcoded Combo (Pass/Fail) |
ItemQcStatusCode By default will be Pass |
Upload File |
Validations
- QC is Approved. You may not modify it.
- File needs to be selected.
- File size must be up to 1 MB
- Report Date needs to be selected.
If it is 01-Jan-01 only
QC Line Level 2
- Will be available only for System or Mix mode and test plan exists
- Initially result will be
Pending
QC 2 Bulk Update
- Bulk Update will not be allowed if QC is approved.
Download Model
-
Values will be prefilled and only actual Value column will be open
-
Fields
Column Property Id HiddenId Parameter Code ParameterCode Parameter Name ParameterCode Parameter Type Code HiddenParameterTypeCode Parameter Type Name ParameterTypeName Value Value -
Instruction Sheet
Column Validation Value For parameter type System fill numeric value and for Manual fill P(Pass)/F(Fail)
Reading XL Error code
| Column | Validation |
|---|---|
| Z1 | Value must be in proper number format If parameter type System |
| Z2 | Value must be between 0 to 9999.999 If parameter type System |
| Z3 | Value must be P - Pass, F - Fail If parameter type User |
Repository XL Sheet
| Column | Property |
|---|---|
| Company Name | companydata.CompanyName |
| Report Name | Quality Control Parameter Bulk Update |
| Report Date | DateTime.Now.Date.ToString(“dd-MMM-yy”) |
| QC No, Item Group | data.QcNo, data.ItemGroupName |
| Error Code | ErrorCode |
| Id | Id |
| Parameter Code | ParameterCode |
| Parameter Name | ParameterCode |
| Parameter Type Code | ParameterTypeCode |
| Parameter Type Name | ParameterTypeName |
| Value | Value |
| Actual Value | ActualValue |
| Result | ResultName |
Repository Error Code Message
| Validation |
|---|
| Model has been altered. Records are missing. Please re-download the model. Bulk update failed due to validation errors. |
| Model has been altered. Records are not matching. Please re-download the model. Bulk update failed due to validation errors. |
| Bulk uspdate Succeeded. |
Repository Query
public async Task<Tuple<List<QualityControl2>, string>> QualityControl2BulkUpdate(int qc1Id, List<QualityControl2> listData, string dbname, string yearLabel, string userName, string itemGroupCode)
{
var tempCreate = @"CREATE TABLE #temp
(
Id INT,
parametercode NVARCHAR(6) COLLATE DATABASE_DEFAULT,
parametername NVARCHAR(100) COLLATE DATABASE_DEFAULT,
parametertypecode NVARCHAR(1) COLLATE DATABASE_DEFAULT,
parametertypename NVARCHAR(10) COLLATE DATABASE_DEFAULT,
value NVARCHAR(10) COLLATE DATABASE_DEFAULT,
actualvalue NUMERIC(7,3),
result NVARCHAR(1) COLLATE DATABASE_DEFAULT
)";
var tempinsertion = @"INSERT INTO #temp (Id,parametercode,parametername,parametertypecode,parametertypename,value,actualvalue)
VALUES (@Id,@parametercode,@parametername,@parametertypecode,@parametertypename,@value,0)";
var errorCodeA = @"WITH A (LineCnt) AS
(
SELECT COUNT(*) AS LineCnt
FROM #temp
),
B (LineCnt) AS
(
SELECT COUNT(*) AS LineCnt
FROM QualityControl2 Q2
LEFT JOIN QualityControl1 Q1 ON Q2.yearqcno = Q1.yearqcno AND Q2.itemgrpid = Q1.itemgrpid
WHERE Q1.id = @qc1Id
),
C (LineCnt) AS
(
SELECT (LineCnt * -1) AS LineCnt FROM A
UNION ALL
SELECT LineCnt FROM B
)
SELECT SUM(LineCnt) FROM C";
var errorCodeB = @"WITH A (id) AS
(
SELECT Q2.id
FROM QualityControl2 Q2
LEFT JOIN QualityControl1 Q1 ON Q2.yearqcno = Q1.yearqcno AND Q2.itemgrpid = Q1.itemgrpid
WHERE Q1.id = @qc1Id
),
B (id) AS
(
SELECT id FROM A WHERE NOT EXISTS (SELECT id FROM #temp WHERE A.id = #temp.id)
)
SELECT COUNT(*) FROM B";
var updateQc2TempSystemStatus = @"WITH A (result, actualvalue, id) AS
(
SELECT IIF(Z.value BETWEEN Q.minvalue AND Q.maxvalue, 'P', 'F') AS Result,
Z.value AS actualvalue, Z.id
FROM #temp Z
LEFT JOIN QualityParameter Q ON Z.parametercode = Q.parametercode
WHERE Z.parametertypecode = 'S'
)
UPDATE #temp SET actualvalue = A.actualvalue, result = A.result
FROM A
WHERE #temp.id = A.id";
var updateQc2TempUserStatus = @"WITH A (result, id) AS
(
SELECT Z.value AS result, Z.id
FROM #temp Z
WHERE Z.parametertypecode = 'U'
)
UPDATE #temp SET result = A.result
FROM A
WHERE #temp.id = A.id";
var updateQc2Status = @"UPDATE QualityControl2 SET result = Z.result,
actualvalue = Z.actualvalue
FROM #temp Z
WHERE QualityControl2.id = Z.id";
var updateQc1Status = @"WITH A (itemqcstatus) AS
(
SELECT IIF(SUM(IIF(Q2.result != 'P', 1, 0)) = 0, 'P', 'F') AS itemqcstatus
FROM QualityControl2 Q2
LEFT JOIN QualityControl1 Q1 ON Q2.yearqcno = Q1.yearqcno AND Q2.itemgrpid = Q1.itemgrpid
WHERE Q1.id = @qc1Id
)
UPDATE QualityControl1 SET itemqcstatus = A.itemqcstatus
FROM A
WHERE QualityControl1.id = @qc1Id";
var updateQcStatus = @"WITH A (qcStatus) AS
(
SELECT IIF(SUM(IIF(Q1.itemqcstatus = 'N', 1, 0)) = 0, 'C', 'P') AS qcStatus
FROM QualityControl1 Q1
WHERE Q1.YearQcNo = @YearQcNo
)
UPDATE QualityControl SET qcStatus = A.qcStatus
FROM A
WHERE QualityControl.yearqcno = @YearQcNo";
var finalSelect = @"SELECT id, parametercode, parametername, parametertypecode, parametertypename, value,
actualvalue, IIF(result = 'P', 'Pass', 'Fail') AS resultname
FROM #temp
ORDER BY Id ASC";
using var connection = _DapperContext.SetClientConnection(dbname);
connection.Open();
connection.Execute(tempCreate);
connection.Execute(tempinsertion, listData.Select(item => new
{
item.Id,
item.ParameterCode,
item.ParameterName,
item.ParameterTypeCode,
item.ParameterTypeName,
item.Value
}));
var errorcodeACnt = connection.QuerySingleOrDefault<int>(errorCodeA, new { qc1Id });
var errorcodeBCnt = connection.QuerySingleOrDefault<int>(errorCodeB, new { qc1Id });
string msg;
string errorCodeMsg = string.Empty;
if (errorcodeACnt != 0)
{
errorCodeMsg = "Model has been altered. Records are missing. Please re-download the model.";
}
else if (errorcodeBCnt != 0)
{
errorCodeMsg = "Model has been altered. Records are not matching. Please re-download the model.";
}
if (errorcodeACnt == 0 && errorcodeBCnt == 0)
{
connection.Execute(updateQc2TempSystemStatus);
connection.Execute(updateQc2TempUserStatus);
connection.Execute(updateQc2Status);
connection.Execute(updateQc1Status, new { qc1Id });
var data = QualityControl1Details(qc1Id, dbname).Result;
connection.Execute(updateQcStatus, new { data.YearQcNo });
_IUtilityMethodsRepository.InsertMFGLog(dbname, userName, "", "QualityControl", "Bulk Update", yearLabel, $"Updated Parameters for Item Group : {itemGroupCode}");
msg = "Bulk update Succeeded.";
}
else
{
msg = $"{errorCodeMsg} Bulk update failed due to validation errors.";
}
var resultData = await connection.QueryAsync<QualityControl2>(finalSelect);
var resultList = resultData.ToList();
return new Tuple<List<QualityControl2>, string>(resultList, msg);
}Parameter Execution Logic
System Parameter
- Inititally status will be → Pending
- User fills actual values
- IF actualValue BETWEEN minValue AND maxValue → PASS ELSE → FAIL
Manual Parameter
- User selects: Pass / Fail
Status Logic
QC2 (Parameter)
- N → Pending
- P → Pass
- F → Fail
QC1 (Item Group)
IF Manual → user input
IF System:
IF any FAIL → F
ELSE IF all PASS → P
ELSE → NQC_Main
IF all QC1 = PASS → C
IF all QC1 = Pending → O
ELSE → PQC Locking
- If QC exists → Modify/Delete not allowed for linked refdoc
Edge Case Handling
Multiple Items in Item Group (Critical)
Problem:
- 3 items → 2 good, 1 bad
Solution
👉 Use Worst Case Logic
IF ANY sample fails → Item Group FAILInput Approach
- User must enter: Minimum observed value
Model Class
using System.ComponentModel.DataAnnotations;
namespace ErpCrystal_MFG.Models;
public class QualityControl
{
public int Id { get; set; }
public string QcNo { get; set; } = string.Empty;
public DateTime? QcDate { get; set; } = DateTime.Now;
public string YearQcNo { get; set; } = string.Empty;
[Required(ErrorMessage = "QC Stage needs to be selected")]
public string QcStageCode { get; set; } = string.Empty;
public string QcStageName { get; set; } = string.Empty;
[Required(ErrorMessage = "Ref Doc needs to be selected")]
public string RefDoc { get; set; } = string.Empty;
[Required(ErrorMessage = "Ref No needs to be filled")]
[StringLength(6, ErrorMessage = "Ref No can be upto 6 digits only")]
public string RefNo { get; set; } = string.Empty;
public DateTime? RefDate { get; set; } = DateTime.Now;
[Required(ErrorMessage = "QC Mode needs to be selected")]
public string QcModeCode { get; set; } = string.Empty;
public string QcModeName { get; set; } = string.Empty;
public string QcStatusCode { get; set; } = string.Empty;
public string QcStatusName { get; set; } = string.Empty;
public string CheckedBy { get; set; } = string.Empty;
public string ApprovedBy { get; set; } = string.Empty;
public string DeleteReason { get; set; } = string.Empty;
}
public class QualityControl1
{
public int Id { get; set; }
public string QcNo { get; set; } = string.Empty;
public string YearQcNo { get; set; } = string.Empty;
public string ItemGroupCode { get; set; } = string.Empty;
public string ItemGroupName { get; set; } = string.Empty;
public string TestPlanCode { get; set; } = string.Empty;
public string TestPlanName { get; set; } = string.Empty;
public int MainId { get; set; }
[Required(ErrorMessage = "Report No needs to be filled")]
[StringLength(20, ErrorMessage = "Report No can be upto 20 characters only")]
public string ReportNo { get; set; } = string.Empty;
public DateTime? ReportDate { get; set; } = DateTime.Now;
public string ItemQcStatusCode { get; set; } = string.Empty;
public string ItemQcStatusName { get; set; } = string.Empty;
[StringLength(150, ErrorMessage = "QA Remark can be upto 150 characters only")]
public string Remarks { get; set; } = string.Empty;
}
public class QualityControl2
{
public int Id { get; set; }
public string QcNo { get; set; } = string.Empty;
public string YearQcNo { get; set; } = string.Empty;
public string ItemGroupCode { get; set; } = string.Empty;
public string ItemGroupName { get; set; } = string.Empty;
public string ParameterCode { get; set; } = string.Empty;
public string ParameterName { get; set; } = string.Empty;
public string Value { get; set; } = string.Empty;
public decimal ActualValue { get; set; }
public string ResultCode { get; set; } = string.Empty;
public string ResultName { get; set; } = string.Empty;
public string ParameterTypeCode { get; set; } = string.Empty;
public string ParameterTypeName { get; set; } = string.Empty;
public string ErrorCode { get; set; } = string.Empty;
}
public class QualityControlPrint
{
public string YearQcNo { get; set; } = string.Empty;
public string QcNo { get; set; } = string.Empty;
public DateTime? QcDate { get; set; } = DateTime.Now;
public string QcStageName { get; set; } = string.Empty;
public string RefDoc { get; set; } = string.Empty;
public string RefNo { get; set; } = string.Empty;
public DateTime? RefDate { get; set; } = DateTime.Now;
public string QcModeName { get; set; } = string.Empty;
public string QcStatusName { get; set; } = string.Empty;
public string PdfFileName { get; set; } = string.Empty;
// QC 1
public string ItemGroupName { get; set; } = string.Empty;
public string TestPlanName { get; set; } = string.Empty;
public string ReportNo { get; set; } = string.Empty;
public DateTime? ReportDate { get; set; } = DateTime.Now;
public string ItemQcStatusName { get; set; } = string.Empty;
public string Remarks { get; set; } = string.Empty;
// QC 2
public string ParameterName { get; set; } = string.Empty;
public string ParameterTypeCode { get; set; } = string.Empty;
public string ParameterTypeName { get; set; } = string.Empty;
public string ActualValue { get; set; } = string.Empty;
public string ResultName { get; set; } = string.Empty;
public string CheckedBy { get; set; } = string.Empty;
public string ApprovedBy { get; set; } = string.Empty;
}File & Method Names
| File Name |
|---|
| Model Class - QualityControl |
| Service - IQualityControlService, QualityControlService |
| Controller - QualityControlController, QuestPDF_QualityControl |
| Repository - IQualityControlRepository, QualityControlRepository |
| Razor Pages - QualityControlIndex - QualityControlDetails - QualityControlCreate - QualityControl1Index - QualityControl1Details - QualityControl1Upload - QualityControl2BulkUpdate |
| Method Name - QualityControlIndex - QualityControlDetails - QualityControlValidateCreate - GetRefDocExistCnt - GetDuplicateQcCount - GetRefDocLineCount - GetItemGroupsPlanStatus - GetTestPlanLineCount - GetRefDocItemGroups - QualityControlCreate - GetMaxQcNo - QualityControlDelete - QualityControl1Index - QualityControl1Details - QualityControl1CreateLines - QualityControl1ModifyRemarks - QualityControl1ModifyUpload - QualityControl2Index - QualityControl2DownloadModel - QualityControl2BulkUpdate - QualityControlPrint - QualityControlPrintData - ApproveQC |
Role Name
| Role |
|---|
| QualityControlDetails QualityControlDelete ApproveQC QualityControlCreate QualityControlModify |