Python Programming

تسلط بر اتوماسیون پایتون: از اسکریپت‌های ساده تا زمان‌بندی وظایف پیچیده

در منظره توسعه نرم‌افزار مدرن، کارایی تنها یک لوکس نیست، بلکه یک ضرورت است. چه مهندس DevOps باشید که زیرساخت را مدیریت می‌کند و چه دانشمند داده‌ای که مجموعه‌داده‌های بزرگ را پردازش می‌کند، توانایی خودکارسازی وظایف تکراری یک مهارت حیاتی است. در حالی که پایتون به خاطر خوانایی و انعطاف‌پذیری خود شهرت دارد، بهره‌برداری از قدرت آن برای خودکارسازی سیستم‌ها نیازمند درک دقیقی از اصول پایه‌ای اسکریپت‌نویسی و مکانیسم‌های پیشرفته زمان‌بندی است.

این مقاله گذار از اسکریپت‌های خودکارسازی پایه به سیستم‌های زمان‌بندی وظایف پیچیده را با استفاده از پایتون بررسی می‌کند. ما همه چیز را از بهره‌گیری از زمان‌بندهای بومی سیستم‌عامل تا پیاده‌سازی زمان‌بندهای درون‌پردازشی مانند APScheduler و صف‌های وظیفه توزیع‌شده مانند Celery پوشش خواهیم داد.

پایه‌های خودکارسازی پایتون

قبل از غرق شدن در چارچوب‌های پیچیده، درک اصول اولیه نوشتن اسکریپت‌های تمیز و قابل اجرا ضروری است. یک اسکریپت خودکارسازی قوی باید ماژولار، دارای مدیریت خطا و در صورت امکان، ایدمپوتنت (تکرارپذیر بدون اثرات جانبی) باشد. کتابخانه استاندارد پایتون ابزارهای عالی برای این منظور فراهم می‌کند، به‌ویژه ماژول‌های subprocess و os.

برای مثال، سناریوی ساده‌ای را در نظر بگیرید که نیاز به پاک‌سازی فایل‌های لاگ قدیمی به صورت روزانه دارید. به جای SSH دستی به سرورها، می‌توانید یک اسکریپت پایتون برای انجام این کار بنویسید:

import os
import glob
from datetime import datetime, timedelta

def cleanup_logs(directory, days_old=30):
    """حذف فایل‌های لاگ قدیمی‌تر از تعداد مشخصی روز."""
    cutoff_date = datetime.now() - timedelta(days=days_old)
    
    # یافتن تمام فایل‌های .log در دایرکتوری
    log_files = glob.glob(os.path.join(directory, '*.log'))
    
    for file_path in log_files:
        file_mod_time = datetime.fromtimestamp(os.path.getmtime(file_path))
        if file_mod_time < cutoff_date:
            try:
                os.remove(file_path)
                print(f"حذف لاگ قدیمی: {file_path}")
            except PermissionError:
                print(f"دسترسی برای {file_path} رد شد")

if __name__ == "__main__":
    cleanup_logs("/var/log/myapp", days_old=30)

این اسکریپت اهمیت مدیریت خطا را نشان می‌دهد. در یک محیط تولید، شما باید ثبت وقایع (logging)، تجزیه آرگومان‌ها و شاید یک حالت آزمایشی (dry-run) را اضافه کنید تا از از دست دادن تصادفی داده‌ها جلوگیری شود.

زمان‌بندی در سطح سیستم: Cron و Crontab

برای وظایف ساده و تکراری، قابل‌اعتمادترین روش اغلب زمان‌بنده داخلی سیستم‌عامل است. در لینوکس و macOS، این ابزار crontab است و در ویندوز، Task Scheduler می‌باشد. اسکریپت‌های پایتون کاندیدای عالی برای وظایف cron هستند زیرا می‌توان آن‌ها را دقیقاً مانند هر اسکریپت قابل اجرای shell فراخوانی کرد.

برای زمان‌بندی اسکریپت بالا برای اجرا هر روز ساعت 2:00 صبح، باید خط زیر را به crontab خود اضافه کنید:

0 2 * * * /usr/bin/python3 /path/to/cleanup_logs.py

بهترین روش: همیشه از مسیرهای مطلق برای مفسر پایتون و اسکریپت استفاده کنید. وظایف cron متغیرهای محیطی یا PATH کاربر شما را به ارث نمی‌برند که می‌تواند منجر به خطاهای "command not found" شود اگر به محیط‌های مجازی یا کتابخانه‌های خاصی که در site-packages سراسری نیستند تکیه کنید.

زمان‌بندی درون‌پردازشی با APScheduler

گاهی اوقات اجرای فرآیندهای خارجی از طریق cron بیش از حد پیچیده یا غیرعملی است. برای مثال، اگر وظیفه شما نیاز به پردازش داده‌های حالت‌دار (stateful) دارد یا باید با یک برنامه وب در حال اجرا تعامل داشته باشد، ممکن است بخواهید وظایف را از داخل برنامه پایتون خود زمان‌بندی کنید. اینجاست که APScheduler درخشش می‌کند.

APScheduler به شما امکان می‌دهد وظایف را به صورت پویا در حالی که برنامه در حال اجراست زمان‌بندی کنید. این کتابخانه از سه نوع تریگر پشتیبانی می‌کند: cron (بر اساس زمان)، interval (دوره‌های ثابت) و date (یک‌بار مصرف). در اینجا نحوه تنظیم یک زمان‌بنده در یک برنامه پایتون آورده شده است:

from apscheduler.schedulers.blocking import BlockingScheduler
import logging

logging.basicConfig()

def my_job():
    print("وظیفه اجرا شد!")

scheduler = BlockingScheduler()

# اجرا هر روز ساعت 10:30 صبح
scheduler.add_job(my_job, 'cron', hour=10, minute=30)

try:
    scheduler.start()
except KeyboardInterrupt:
    scheduler.shutdown()

این رویکرد به‌ویژه برای دیمون‌های طولانی‌مدت، کارگران پس‌زمینه یا ابزارهای داخلی مفید است که می‌خواهید چرخه عمر زمان‌بنده را در کنار خود برنامه مدیریت کنید.

صف‌های وظیفه توزیع‌شده: ورود Celery

با رشد نیازهای خودکارسازی شما—که نیاز به اجرای موازی، منطق تلاش مجدد (retry logic) یا توزیع وظایف در چندین ماشین دارد—زمان‌بندهای ساده ناکافی می‌شوند. این حوزه صف‌های وظیفه توزیع‌شده مانند Celery است. Celery به شما امکان می‌دهد وظایفی را تعریف کنید که به کارگران ارسال می‌شوند و می‌توانند روی سرورهای مختلف اجرا شوند، بارهای سنگین، فراخوانی‌های API یا تبدیل داده‌ها را در پس‌زمینه انجام دهند.

اگرچه Celery منحنی یادگیری شیب‌داری دارد، اما ویژگی‌های درجه تولید مانند بک‌اند‌های نتیجه، نظارت (از طریق Flower) و تحویل تضمین‌شده وظایف را ارائه می‌دهد. یکپارچه‌سازی Celery با یک واسط مانند Redis یا RabbitMQ تضمین می‌کند که وظایف شما به طور قابل اعتماد پردازش شوند، حتی اگر یک کارگر دچار کرش شود.

نتیجه‌گیری

انتخاب ابزار مناسب برای خودکارسازی پایتون به پیچیدگی و مقیاس نیازهای شما بستگی دارد. برای وظایف ساده دستکاری فایل یا پاک‌سازی، یک اسکریپت خوب نوشته شده همراه با crontab قابل‌نگهدارترین راه‌حل است. برای برنامه‌هایی که به زمان‌بندی پویا نیاز دارند، APScheduler یک راه‌حل انعطاف‌پذیر و درون‌پردازشی ارائه می‌دهد. با این حال، هنگام کار با سیستم‌های توزیع‌شده با بار کاری بالا، Celery همچنان استاندارد صنعتی باقی می‌ماند.

با تسلط بر این ابزارها، نه تنها زمان صرفه‌جویی می‌کنید، بلکه خطر خطای انسانی را نیز کاهش می‌دهید و به شما امکان می‌دهید بر ساخت ویژگی‌های ارزش‌افزوده تمرکز کنید تا مدیریت وظایف عملیاتی پیش‌پاافتاده.

Share: