import sqlite3 import hashlib from datetime import datetime class UserManager(object): permission = "NONE" allowBorrowBook = [] allowReturnBook = [] bookLocationInfo = [[]] bookInfos =[[]] recordInfo = [[]] database = None user_id = None @staticmethod def getAllowBorrowBook(): if len(UserManager.allowBorrowBook) <= 0: return ['暂无可借阅书籍'] else: return UserManager.allowBorrowBook @staticmethod def getAllowReturnBook(): if len(UserManager.allowReturnBook) <= 0: return ['暂无可归还书籍'] else: return UserManager.allowReturnBook @staticmethod def init(): UserManager.database = sqlite3.connect('database.db') cur = UserManager.database.cursor() tables = [ ("Account", ''' CREATE TABLE Account( userID TEXT PRIMARY KEY, passwordHash TEXT, permission TEXT CHECK(permission IN ('Admin', 'User', 'Ban')) ) '''), ("BookInfo", ''' CREATE TABLE BookInfo( ISBN TEXT PRIMARY KEY, author TEXT, name TEXT, category TEXT ) '''), ("MainBook", ''' CREATE TABLE MainBook( bookID INTEGER PRIMARY KEY, ISBN TEXT, borrowStatus TEXT CHECK(borrowStatus IN ('borrowed', 'available')), FOREIGN KEY (ISBN) REFERENCES BookInfo ) '''), ("BookLocation", ''' CREATE TABLE BookLocation( bookID INTEGER PRIMARY KEY, location TEXT, FOREIGN KEY (bookID) REFERENCES MainBook ) '''), ("BorrowRecord", ''' CREATE TABLE BorrowRecord( bookID INTEGER, borrowTime TEXT, actualReturnTime TEXT, borrowingUser TEXT, FOREIGN KEY (bookID) REFERENCES MainBook, FOREIGN KEY (borrowingUser) REFERENCES Account ) ''') ] for table_name, table_query in tables: cur.execute(f"SELECT name FROM sqlite_master WHERE type='table' AND name='{table_name}'") if not cur.fetchone(): cur.execute(table_query) cur.execute("SELECT COUNT(*) FROM Account") rows = cur.fetchone()[0] if rows == 0: default_password = "admin" passwordHash = hashlib.sha256(default_password.encode()).hexdigest() cur.execute('INSERT INTO Account(userID, passwordHash, permission) VALUES(?, ?, ?)', ("admin", passwordHash, "Admin")) UserManager.database.commit() cur.close() @staticmethod def login(user_name, password): cur = UserManager.database.cursor() passwordHash = hashlib.sha256(password.encode()).hexdigest() cur.execute('SELECT * FROM Account WHERE userID=? AND passwordHash=?', (user_name, passwordHash)) user = cur.fetchone() if user: UserManager.permission = user[2] UserManager.user_id = user[0] return True else: return False @staticmethod def addBookInfo(isbn, name, author, category): cur = UserManager.database.cursor() cur.execute('''INSERT INTO BookInfo(isbn, author, name, category) VALUES (?, ?, ?, ?)''', (isbn, author, name, category)) UserManager.database.commit() @staticmethod def addBookInstance(isbn, location): cur = UserManager.database.cursor() cur.execute(f"SELECT COUNT(*) FROM BookInfo WHERE ISBN=?", (isbn,)) result = cur.fetchone() if result[0] > 0: cur.execute('''SELECT bookID FROM MainBook ORDER BY bookID DESC''') last = cur.fetchone() last = last[0] last += 1 cur.execute('''INSERT INTO MainBook(bookID, ISBN, borrowStatus) VALUES (?, ?, 'available')''', (last, isbn)) cur.execute('''INSERT INTO BookLocation(bookID, location) VALUES (?,?)''', (last, location)) UserManager.database.commit() return True else: return False @staticmethod def addUser(name, password, permission): cur = UserManager.database.cursor() passwordHash = hashlib.sha256(password.encode()).hexdigest() cur.execute('''INSERT INTO Account(userID, passwordHash, permission) VALUES (?, ?, ?)''', (name, passwordHash, permission)) UserManager.database.commit() @staticmethod def modifierUserPerm(name, permission): cur = UserManager.database.cursor() cur.execute('''UPDATE Account SET permission=? WHERE userID=?''', (permission, name)) UserManager.database.commit() @staticmethod def removeBook(book_id): c = UserManager.database.cursor() c.execute("DELETE FROM BorrowRecord WHERE bookID=?", (book_id,)) c.execute("DELETE FROM BookLocation WHERE bookID=?", (book_id,)) c.execute("DELETE FROM MainBook WHERE bookID=?", (book_id,)) UserManager.database.commit() @staticmethod def getAllCanBorrowBook(): c = UserManager.database.cursor() c.execute(""" SELECT BookInfo.name FROM MainBook JOIN BookInfo ON MainBook.ISBN = BookInfo.ISBN WHERE MainBook.borrowStatus = 'available' """) results = c.fetchall() UserManager.allowBorrowBook = list(dict.fromkeys(result[0] for result in results)) @staticmethod def getAllNeedReturnBook(user_id): c = UserManager.database.cursor() c.execute(""" SELECT BookInfo.name FROM BorrowRecord JOIN MainBook ON BorrowRecord.bookID = MainBook.bookID JOIN BookInfo ON MainBook.ISBN = BookInfo.ISBN WHERE BorrowRecord.borrowingUser = ? AND BorrowRecord.actualReturnTime = '未归还' """, (user_id,)) results = c.fetchall() UserManager.allowReturnBook = [result[0] for result in results] @staticmethod def getAllBookIndexByNameThatCanBorrow(book_name): c = UserManager.database.cursor() c.execute(""" SELECT MainBook.bookID FROM MainBook JOIN BookInfo ON MainBook.ISBN = BookInfo.ISBN WHERE BookInfo.name = ? ORDER BY MainBook.bookID """, (book_name,)) # Fetch all results results = c.fetchall() # Extract book IDs book_ids = [result[0] for result in results] return book_ids @staticmethod def borrow_book(book_id): c = UserManager.database.cursor() borrow_time = datetime.now().strftime('%Y-%m-%d') c.execute(""" UPDATE MainBook SET borrowStatus = 'borrowed' WHERE bookID = ? """, (book_id,)) c.execute(""" INSERT INTO BorrowRecord (bookID, borrowTime,actualReturnTime, borrowingUser) VALUES (?, ?, ?, ?) """, (book_id, borrow_time, '未归还', UserManager.user_id)) UserManager.database.commit() @staticmethod def return_book(book_id): c = UserManager.database.cursor() actual_return_time = datetime.now().strftime('%Y-%m-%d') c.execute(""" UPDATE MainBook SET borrowStatus = 'available' WHERE bookID = ? """, (book_id,)) c.execute(""" UPDATE BorrowRecord SET actualReturnTime = ? WHERE bookID = ? AND borrowingUser = ? AND actualReturnTime = '未归还' """, (actual_return_time, book_id, UserManager.user_id)) UserManager.database.commit() @staticmethod def get_books_location_data(): c = UserManager.database.cursor() c.execute(""" SELECT MainBook.bookID, BookInfo.name, MainBook.ISBN, BookLocation.location FROM MainBook JOIN BookInfo ON MainBook.ISBN = BookInfo.ISBN JOIN BookLocation ON MainBook.bookID = BookLocation.bookID """) results = c.fetchall() UserManager.bookLocationInfo = [[str(value) for value in result] for result in results] @staticmethod def get_books_info_data(): c = UserManager.database.cursor() # Execute the query c.execute(""" SELECT BookInfo.name, BookInfo.author, BookInfo.ISBN, BookInfo.category, COUNT(MainBook.ISBN) FROM BookInfo LEFT JOIN MainBook ON BookInfo.ISBN = MainBook.ISBN GROUP BY BookInfo.ISBN """) # Fetch all results results = c.fetchall() UserManager.bookInfos = [[str(value) for value in result] for result in results] @staticmethod def get_user_borrow_records(): c = UserManager.database.cursor() # Execute the query c.execute(""" SELECT BorrowRecord.borrowingUser, BorrowRecord.bookID, BookInfo.name, MainBook.ISBN, BorrowRecord.borrowTime, BorrowRecord.actualReturnTime FROM BorrowRecord JOIN MainBook ON BorrowRecord.bookID = MainBook.bookID JOIN BookInfo ON MainBook.ISBN = BookInfo.ISBN """) # Fetch all results results = c.fetchall() # Convert numeric values to strings UserManager.recordInfo = [[str(value) if isinstance(value, (int, float)) else value for value in result] for result in results]