Command line counter with plain text file database
Tags: beginners, programming, perl
Published: 2023-01-29 06:24:55

---
title: Command line counter with plain text file database
published: true
description: A very simple command-line counter to show a few basic features of the Perl programming language.
tags: beginners, programming, perl
# cover_image: https://direct_url_to_image.jpg
# Use a ratio of 100:42 for best results.
# published_at: 2023-01-29 06:18 +0000
canonical_url: https://code-maven.com/command-line-counter
series: counter
---

As part of the [big counter example project](https://code-maven.com/counter), this example runs on the command line and uses a plain text file as `back-end database`.
It is probably the most basic version of all the [counter examples](https://code-maven.com/counter), that provides a single counter.


## Front-end

The front end is the command line. We just run the script as `perl counter.pl`.

## Back-end

In this example the "database" is going to be a simple file called 'counter.txt' with only a number in it. The most recent value of the counter.

## Code

```perl
use strict;
use warnings;

my $file = 'counter.txt';
my $count = 0;

if (-e $file) {
    open my $fh, '<', $file or die "Could not open '$file' for reading. $!";
    $count = <$fh>;
    close $fh;
}

$count++;
print "$count\n";

open my $fh, '>', $file or die "Could not open '$file' for writing. $!";
print $fh $count;
close $fh;


```

After the initial statements to enable [strict and warnings](https://perlmaven.com/always-use-strict-and-use-warnings), we have declared a variable called `$file` that holds the name of the 'database' file we are going to use to store the latest value of the counter. This could be declared as a [constant or read-only variable](https://perlmaven.com/constants-and-read-only-variables-in-perl), but I did not bother.

During the execution of the script we will hold the value of the counter in the variable we cunningly called `$counter`. We declare it up-front and assign a default value of 0 to it.

Next we should be reading in the previous value of the counter. However, before we run the script for the first file, the file holding the number does not exist.  Hence we need to do two things.


1. When we declare `$counter` using the `my` keyword we also initialize it to the default value of 0. This way, even if the `counter.txt` file does not exist yet we can pretend that the previous value 0.
1. Then, before we attempt to open the `counter.txt` file for reading, we check if it already exists using the `-e` operator.

Because at the first run the file does not exist, let's skip this code now and let's go straight to the part after the closing curly brace (`}`).

```perl
$count++;
print "$count\n";

open my $fh, '>', $file or die "Could not open '$file' for writing. $!";
print $fh $count;
close $fh;
```

Using `++` the auto-increment operator of Perl, we increment the value of `$count` (which started out as 0 during the first execution). Then we print it out to the screen.

In the 3 lines after that, we open the 'counter.txt' file for [writing](https://perlmaven.com/writing-to-files-with-perl). In the first run this will create the file,
in subsequent runs this will clean up the file to have no content. Then we use the `print` statement to write the new content of `$count` into the now empty file.
Finally, just to be nice, we close the file handle using the `close` function.

On the second and later executions of the script, the 'counter.txt' file will already exist. Thus the `if (-e $file)` will return true, and we enter the block:

```perl
if (-e $file) {
    open my $fh, '<', $file or die "Could not open '$file' for reading. $!";
    $count = <$fh>;
    close $fh;
}

```

In this block we try to [open the file for reading](https://perlmaven.com/open-and-read-from-files) using the `open` function and [throw an exception](https://perlmaven.com/die) by calling the `die` function if we still cannot open the file. This should happen only in the most extreme situation and therefore it is ok to take drastic steps. If the `open` was successful, `$fh`, the newly declared variable will have the file handle in it. We can then use the `<$fh>` operator to read one line (the only one it has) from the file and finally we `close` the file.

## No need to initialize the counter


Actually when we declared the `$counter` variable it was not really necessary to also assign 0 to it. It looks better for people coming from other programming languages, but in Perl even if we left it [undef](https://perlmaven.com/undef-and-defined-in-perl) the script would work perfectly well.

That's because when using the ++ [auto increment](https://perlmaven.com/numerical-operators) operator on a variable that has `undef` in it, that `undef` will act as if it was actually 0. It is probably the simplest form of [autovivification](https://perlmaven.com/autovivification) in Perl. So we could have written

```perl
my $counter;
```