0% found this document useful (0 votes)
2 views

Button Functions.py

The document outlines a Python class, ButtonFunctions, which manages the saving of WIR (Work Inspection Report) logs to a CSV file using a GUI. It includes methods for validating input data, checking for duplicates, and inserting new entries into the CSV file while handling various exceptions. Additionally, it integrates with a WordHandler to update bookmarks in a Word document based on the WIR data entered by the user.

Uploaded by

HQHome
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as TXT, PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
2 views

Button Functions.py

The document outlines a Python class, ButtonFunctions, which manages the saving of WIR (Work Inspection Report) logs to a CSV file using a GUI. It includes methods for validating input data, checking for duplicates, and inserting new entries into the CSV file while handling various exceptions. Additionally, it integrates with a WordHandler to update bookmarks in a Word document based on the WIR data entered by the user.

Uploaded by

HQHome
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as TXT, PDF, TXT or read online on Scribd
You are on page 1/ 4

import csv

import datetime
from pathlib import Path
from PyQt5.QtWidgets import QMessageBox
from Logger import setup_logger
from Word import WordHandler
from constants import WIRLogFilePath, WordFilePath

class ButtonFunctions:
def __init__(self, main_window, ui):
self.main_window = main_window
self.ui = ui
self.logger = setup_logger()
self.file_path = Path(WIRLogFilePath)
self.headers = [
'WIR No', 'Revision', 'Activity', 'Sub Activity',
'Description', 'Villa No', 'Level', 'Part',
'Created Date', 'Inspection Date', 'Status'
]
# Ensure CSV file exists with headers
if not self.file_path.exists():
with open(self.file_path, 'w', newline='') as f:
writer = csv.writer(f)
writer.writerow(self.headers)

def save_to_WIRLog(self):
try:
data = self._get_ui_data()
if not self._validate_inputs(data):
return

if self._is_duplicate(data):
self._show_dialog("Duplicate Entry", "This WIR Already exists!
Kindly make Revision",
QMessageBox.Warning)
return

# Prepare and insert new WIR log row


new_row = self._prepare_row(data)
self._insert_into_csv(new_row)
print(f"Formatted Date: {data['Inspection_Date'].strftime('%d %b
%Y')}")

# Fetch next WIR number and revision (assuming you track revisions)
next_wir_number = self._next_wir_number()-1
revision = 0 # Adjust this logic if revisions are tracked dynamically

word_handler = WordHandler(next_wir_number, revision)


word_handler.update_bookmarks(data)

self._clear_ui_fields()
self._show_dialog("Success", f"WIR #{new_row[0]} saved successfully!",
QMessageBox.Information)

except PermissionError:
self._show_dialog("Error", "Please close the CSV file before saving!",
QMessageBox.Critical)
except Exception as e:
self._show_dialog("Error", f"An unexpected error occurred: {str(e)}",
QMessageBox.Critical)

def _insert_into_csv(self, new_row):


# Read existing data
rows = []
with open(self.file_path, 'r', newline='') as f:
reader = csv.reader(f)
rows = list(reader)

# Insert new row after header


rows.insert(1, new_row)

# Write back to file


with open(self.file_path, 'w', newline='') as f:
writer = csv.writer(f)
writer.writerows(rows)

def _get_ui_data(self):
activity_index = self.ui.Activity_QCB1.currentIndex()
villa_text = self.ui.Villa_QCB1.currentText().strip()
return {
'activity': self.ui.Activity_QCB1.currentText().strip(),
'sub_activity': self.ui.Sub_Activity_QCB1.currentText().strip(),
'description': self.ui.Description_QTE1.toPlainText().strip(),
'villa' : f"Plot # {villa_text}" if activity_index < 5 else f"Villa #
{villa_text}",
'level': self.ui.Level_QCB1.currentText().strip(),
'part': self.ui.Part_QCB1.currentText().strip(),
'Inspection_Date':
self._parse_date(self.ui.Inspection_Date_QCB1.currentText().strip()),
}

def _parse_date(self, date_str):


try:
return datetime.datetime.strptime(date_str, "%d %b %Y").date()
except ValueError:
raise ValueError("Invalid date format. Please use DD MMM YYYY")

def _validate_inputs(self, data):


required = [
('activity', 'Activity'),
('sub_activity', 'Sub Activity'),
('villa', 'Villa No'),
('level', 'Level'),
('part', 'Part')
]
missing = [name for field, name in required if not data[field]]
if missing:
self._show_dialog("Missing Information", f"Required fields: {',
'.join(missing)}", QMessageBox.Warning)
return False

if not isinstance(data['Inspection_Date'], datetime.date):


self._show_dialog("Invalid Date", "Please enter a valid date in DD MMM
YYYY format", QMessageBox.Warning)
return False

return True
def _prepare_row(self, data):
return [
self._next_wir_number(),
0,
data['activity'],
data['sub_activity'],
data['description'],
data['villa'],
data['level'],
data['part'],
datetime.date.today().strftime('%d %b %Y'),
data['Inspection_Date'].strftime('%d %b %Y'),
"",
"Under Review",
]

def _next_wir_number(self):
try:
with open(self.file_path, 'r', newline='') as f:
reader = csv.reader(f)
next(reader) # Skip header
wir_numbers = [int(row[0]) for row in reader if row]
return max(wir_numbers) + 1 if wir_numbers else 1
except FileNotFoundError:
return 1

def _is_duplicate(self, data):


try:
with open(self.file_path, 'r', newline='') as f:
reader = csv.DictReader(f)
for row in reader:
existing = {
'Activity': row['Activity'].lower().strip(),
'Sub Activity': row['Sub Activity'].lower().strip(),
'Villa No': row['Villa No'].lower().strip(),
'Level': row['Level'].lower().strip(),
'Part': row['Part'].lower().strip()
}
new_data = {
'Activity': data['activity'].lower().strip(),
'Sub Activity': data['sub_activity'].lower().strip(),
'Villa No': data['villa'].lower().strip(),
'Level': data['level'].lower().strip(),
'Part': data['part'].lower().strip()
}
if existing == new_data:
return True

except FileNotFoundError:
pass
return False

def _clear_ui_fields(self):
for combo in [
self.ui.Activity_QCB1,
self.ui.Sub_Activity_QCB1,
self.ui.Villa_QCB1,
self.ui.Level_QCB1,
self.ui.Part_QCB1,
self.ui.Inspection_Date_QCB1
]:
combo.setCurrentIndex(-1)
self.ui.Description_QTE1.clear()

def _show_dialog(self, title, message, icon=QMessageBox.Warning):


msg = QMessageBox(self.main_window)
msg.setIcon(icon)
msg.setText(message)
msg.setWindowTitle(title)
msg.exec_()

You might also like