Здравствуйте, уважаемые коллеги! Прошу не судить строго, так как это моя первая статья.
У нас появилась необходимость отслеживать изменения в doc и docx файлах с фиксацией имени пользователя, который внес эти изменения. Сами файлы находятся в расшаренной папке (да, да, общие папки это зло, но убедить у меня не получилось) и необходимо знать кто внес изменения. Подробнее под катом.
Сами изменения в файлах будем отслеживать при помощи watchdog (pip install watchdog).
Код для отслеживания всех изменений:
# Для отслеживания изменений import time from watchdog.observers import Observer from watchdog.events import FileSystemEventHandler # Отслеживаем изменения class Watcher: def __init__(self, path): self.observer = Observer() self.path = path def run(self): event_handler = Handler() self.observer.schedule(event_handler, self.path, recursive=True) self.observer.start() try: while True: time.sleep(1) except: self.observer.stop() print("Error") self.observer.join() class Handler(FileSystemEventHandler): @staticmethod def on_any_event(event): if event.is_directory: return None print( "[{}] noticed: [{}] on: [{}] ".format( time.asctime(), event.event_type, event.src_path ) ) if __name__ == "__main__": w = Watcher('C:\\Users\\user\\Desktop\\') w.run()
Такой код позволяет отслеживать изменения во всех файлах (не показывая кто изменил) на рабочем столе пользователя. Естественно, папку «C:\Users\user\Desktop\» эту указал для примера.
Пример вывода:
[Mon Dec 5 14:32:37 2022] noticed: [modified] on: [C:\Users\user\Desktop\Документ Microsoft Word.docx]
Тут нет информации о том, кто изменил файл. Эту информацию можно получить из самого docx файла.
Нам нужно отслеживать изменения именно в doc и docx файлах, поэтому переделаем код:
# -*- coding: utf-8 -*- # Для атрибутов файла import docx # Для отслеживания изменений import time from watchdog.observers import Observer from watchdog.events import FileSystemEventHandler # Отслеживаем изменения class Watcher: def __init__(self, path): self.observer = Observer() self.path = path def run(self): event_handler = Handler() self.observer.schedule(event_handler, self.path, recursive=True) self.observer.start() try: while True: time.sleep(1) except: self.observer.stop() print("Error") self.observer.join() class Handler(FileSystemEventHandler): @staticmethod def on_any_event(event): # if event.is_directory: # return None # print( # "[{}] noticed: [{}] on: [{}] ".format( # time.asctime(), event.event_type, event.src_path # ) # ) # Получаем атрибуты файла if '.tmp' in event.src_path: return None try: document = docx.Document(docx = event.src_path) core_properties = document.core_properties print(f'{core_properties.last_modified_by} в {core_properties.modified} модифицировал файл {event.src_path}') except: pass if __name__ == "__main__": w = Watcher('C:\\Users\\user\\Desktop\\') w.run()
В данном примере изменения просто печатаются в консоль при помощи строки:
print(f'{core_properties.last_modified_by} в {core_properties.modified} модифицировал файл {event.src_path}’)
Пример вывода:
Иванов Иван Иванович в 2022-12-05 07:35:00 модифицировал файл C:\Users\user\Desktop\Документ Microsoft Word.docx
Для журналирования можно использовать простейшую запись в файл:
f = open('change-doc.log','w') # открытие в режиме записи f.write(f'{core_properties.last_modified_by} в {core_properties.modified} модифицировал файл {event.src_path}\n') # запись в файл f.close() # закрытие файла
Или можно отправлять изменения на почту (если это востребовано):
import smtplib from email.mime.multipart import MIMEMultipart from email.mime.text import MIMEText fromaddr = "test@mail.ru" toaddr = "test2@mail.ru" mypass = "password" msg = MIMEMultipart() msg['From'] = fromaddr msg['To'] = toaddr msg['Subject'] = f'Модифицирован файл {event.src_path}' body = f'{core_properties.last_modified_by} в {core_properties.modified} модифицировал файл {event.src_path}' msg.attach(MIMEText(body, 'plain')) server = smtplib.SMTP_SSL('smtp.mail.ru', 465) server.login(fromaddr, mypass) text = msg.as_string() server.sendmail(fromaddr, toaddr, text) server.quit()
Также приведу полный список атрибутов docx файла, которые можно таким же образом получить:
file_name = 'C:\\Users\\user\\Desktop\\123.docx' document = docx.Document(docx = file_name) core_properties = document.core_properties print('author', core_properties.author) print('created', core_properties.created) print('last_modified_by', core_properties.last_modified_by) print('last_printed', core_properties.last_printed) print('modified', core_properties.modified) print('revision', core_properties.revision) print('title', core_properties.title) print('category', core_properties.category) print('comments', core_properties.comments) print('identifier', core_properties.identifier) print('keywords', core_properties.keywords) print('language', core_properties.language) print('subject', core_properties.subject) print('version', core_properties.version) print('keywords', core_properties.keywords) print('content_status', core_properties.content_status)
Спасибо за внимание!!!
ссылка на оригинал статьи https://habr.com/ru/post/720600/
Добавить комментарий