Hone logo
Hone
Problems

Graceful Shutdown in Python

Many applications, especially those dealing with network connections, databases, or file operations, need to shut down cleanly. A graceful shutdown involves finishing ongoing tasks, releasing resources, and saving state before exiting, preventing data loss or corruption. This challenge asks you to implement a mechanism for gracefully shutting down a Python application, responding to signals like SIGTERM and SIGINT.

Problem Description

You are tasked with creating a Python script that gracefully handles shutdown signals (SIGTERM and SIGINT, typically triggered by Ctrl+C or a kill command). The script should simulate a long-running task (e.g., processing data, writing to a file) and ensure that this task is completed or properly stopped before the application exits.

Specifically, your script should:

  1. Register Signal Handlers: Implement signal handlers for SIGTERM and SIGINT.
  2. Simulate a Long-Running Task: Include a function that simulates a task that takes a few seconds to complete. This task should print progress updates periodically.
  3. Graceful Shutdown Logic: When a shutdown signal is received:
    • Set a flag indicating that shutdown is in progress.
    • Allow the long-running task to finish its current iteration (or a small portion of it) before exiting.
    • Print a message indicating that the application is shutting down gracefully.
    • Exit with a status code of 0 (success).
  4. Prevent Immediate Exit: The signal handler should not immediately exit the program upon receiving a signal. It should initiate the shutdown process.
  5. Clean Up (Optional): You can optionally include cleanup actions within the signal handler, such as closing files or releasing network connections. For this challenge, a simple print statement is sufficient.

Examples

Example 1:

Input:  The script is running, simulating a task.  The user presses Ctrl+C (SIGINT).
Output:
[00:00:01] Processing...
[00:00:02] Processing...
[00:00:03] Shutting down gracefully...

Explanation: The script receives SIGINT, sets the shutdown flag, allows the task to run for a few iterations, prints a shutdown message, and exits.

Example 2:

Input: The script is running, simulating a task. The user sends a SIGTERM signal (e.g., using `kill -15 <pid>`).
Output:
[00:00:01] Processing...
[00:00:02] Processing...
[00:00:03] Shutting down gracefully...

Explanation: Similar to Example 1, but triggered by SIGTERM.

Example 3: (Edge Case - Task already finished)

Input: The script is running, and the simulated task has already completed. The user presses Ctrl+C.
Output:
[00:00:00] Task completed.
[00:00:01] Shutting down gracefully...

Explanation: If the task finishes before the signal is received, the shutdown logic still executes, printing the graceful shutdown message.

Constraints

  • The simulated task should take at least 2-3 seconds to complete a single iteration.
  • The script should handle both SIGTERM (signal number 15) and SIGINT (signal number 2).
  • The script should exit with a status code of 0 upon graceful shutdown.
  • The script should not crash or raise unhandled exceptions.

Notes

  • Use the signal module to register signal handlers.
  • Consider using a global flag to indicate that shutdown is in progress. This flag can be checked within the long-running task to determine when to exit.
  • The goal is to demonstrate a graceful shutdown, not an immediate exit. Allow the task to make progress before terminating.
  • You don't need to implement a complex task; a simple loop with print statements is sufficient for demonstration purposes.
  • Think about how to avoid race conditions if multiple threads or processes are involved (although this challenge focuses on a single process).
Loading editor...
python