Lazy loaded image
Technologies
Build a Command-Line App with Python in 7 Easy Steps - KDnuggets
00 min
Jul 2, 2024
Oct 13, 2024
type
status
date
summary
tags
category
URL
password
slug
icon
notion image
Building simple projects is a great way to learn Python and any programming language in general. You can learn the syntax to write for loops, use built-in functions, read files, and much more. But it’s only when you start building something that you actually “learn”.
Following the “learning by building” approach, let’s code a simple TO-DO list app that we can run at the command line. Along the way we’ll explore concepts like parsing command-line arguments and working with files and file paths. We’ll as well revisit basics like defining custom functions.
So let’s get started!

What You’ll Build

By coding along to this tutorial, you’ll be able to build a TO-DO list app you can run at the command line. Okay, so what would you like the app to do?
Like TO-DO lists on paper, you need to be able to add tasks, look up all tasks, and remove tasks (yeah, strikethrough or mark them done on paper) after you’ve completed them, yes? So we’ll build an app that lets us do the following.
Add tasks to the list:
Get a list of all tasks on the list:
And also remove a task (using its index) after you’ve finished it:
Now let’s start coding!

Step 1: Get Started

First, create a directory for your project. And inside the project directory, create a Python script file. This will be the main file for our to-do list app. Let's call it todo.py.
You don't need any third-party libraries for this project. So only make sure you’re using a recent version of Python. This tutorial uses Python 3.11.

Step 2: Import Necessary Modules

In the todo.py file, start by importing the required modules. For our simple to-do list app, we'll need the following:
  • argparse for command-line argument parsing
  • os for file operations
So let’s import them both:

Step 3: Set Up the Argument Parser

Recall that we’ll use command-line flags to add, list, and remove tasks. We can use both short and long options for each argument. For our app, let’s use the following:
  • a or -add to add tasks
  • l or -list to list all tasks
  • r or -remove to remove tasks using index
Here’s where we’ll use the argparse module to parse the arguments provided at the command line. We define the create_parser() function that does the following:
  • Initializes an ArgumentParser object (let’s call it parser).
  • Adds arguments for adding, listing, and removing tasks by calling the add_argument() method on the parser object.
When adding arguments we add both the short and long options as well as the corresponding help message. So here’s the create_parser() function:

Step 4: Add Task Management Functions

We now need to define functions to perform the following task management operations:
  • Adding a task
  • Listing all tasks
  • Removing a task by its index
The following function add_task interacts with a simple text file to manage items on the TO-DO list. It opens the file in the ‘append’ mode and adds the task to the end of the list:
Notice how we’ve used the with statement to manage the file. Doing so ensures that the file is closed after the operation—even if there’s an error—minimizing resource leaks.
To learn more, read the section on context managers for efficient resource handling in this tutorial on writing efficient Python code.
The list_tasks function lists all the tasks by checking if the file exists. The file is created only when you add the first task. We first check if the file exists and then read and print out the tasks. If there are currently no tasks, we get a helpful message. :
We also implement a remove_task function to remove tasks by index. Opening the file in the ‘write’ mode overwrites the existing file. So we remove the task corresponding to the index and write the updated TO-DO list to the file:

Step 5: Parse Command-Line Arguments

We’ve set up the parser to parse command-line arguments. And we’ve also defined the functions to perform the tasks of adding, listing, and removing tasks. So what’s next?
You probably guessed it. We only need to call the correct function based on the command-line argument received. Let’s define a main() function to parse the command-line arguments using the ArgumentParser object we’ve created in step 3.
Based on the provided arguments, call the appropriate task management functions. This can be done using a simple if-elif-else ladder like so:

Step 6: Run the App

You can now run the TO-DO list app from the command line. Use the short option h or the long option help to get information on the usage:
Initially, there are no tasks in the list, so using --list to list all tasks print out “No tasks found.”:
Now we add an item to the TO-DO list like so:
When you list the items now, you should be able to see the task added:
Because we’ve added the first item the tasks.txt file has been created (Refer to the definition of the list_tasks function in step 4):
Let's add another task to the list:
And another:
And now let’s get the list of all tasks:
Now let's remove a task by its index. Say we’re done with evening coffee (and hopefully for the day), so we remove it as shown:
The modified TO-DO list is as follows:

Step 7: Test, Improve, and Repeat

Okay, the simplest version of our app is ready. So how do we take this further? Here are a few things you can try:
  • What happens when you use an invalid command-line option (say w or -wrong)? The default behavior (if you recall from the if-elif-else ladder) is to print out the help message but there’ll be an exception, too. Try implementing error handling using try-except blocks.
  • Test your app by defining test cases that include edge cases. To start, you can use the built-in unittest module.
  • Improve the existing version by adding an option to specify the priority for each task. Also try to sort and retrieve tasks by priority.

Wrapping Up

In this tutorial, we built a simple command-line TO-DO list app. In doing so, we learned how to use the built-in argparse module to parse command-line arguments. We also used the command-line inputs to perform corresponding operations on a simple text file under the hood.
So where do we go next? Well, Python libraries like Typer make building command-line apps a breeze. And we’ll build one using Typer in an upcoming Python tutorial. Until then, keep coding!
Bala Priya C is a developer and technical writer from India. She likes working at the intersection of math, programming, data science, and content creation. Her areas of interest and expertise include DevOps, data science, and natural language processing. She enjoys reading, writing, coding, and coffee! Currently, she's working on learning and sharing her knowledge with the developer community by authoring tutorials, how-to guides, opinion pieces, and more. Bala also creates engaging resource overviews and coding tutorials.
上一篇
4 tabletop exercises every security team should run | CSO Online
下一篇
Containerize Python Apps with Docker in 5 Easy Steps - KDnuggets