Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems. It's 100% free, no registration required.

I want to write a script that reads my input (for example if my script is called "check", then I would type "check 9 4 1993" and that input would go through the cal command and will check through the calendar whether it is a valid date or not).

I've got the bulk of my idea but I'm not sure what approach to use in my syntax. (I'm fairly new to bash scripting so bear with me please).

My idea below is that if the input that goes through the cal command gives an error it will mean that it's not a valid date, and vice-versa if there's no error than the date is valid. I do realize there's something terribly wrong with this draft (I can't figure out how to make it so that my input will go through the cal command), but I will appreciate some suggestions. Here's the draft anyways:

#!/bin/bash

day=$1; month=$2; year=$3
day=$(echo "$day" | bc)
month=$(echo "$month" | bc)
year=$(echo "$year" | bc)

cal $day $ month $year 2> /dev/null
if [[$? -eq 0 ]]; then
   echo "This is a valid date"
else
   echo "This is an invalid date"
fi
share|improve this question
1  
    
What is the purpose behind day=$(echo "$day" | bc)? Input validation? Removal of leading zeros?. In either case you could also do day=$((10#$day)) which uses the shell's own arithmetic expansion instead of forking a bc process. –  Digital Trauma Oct 8 '14 at 16:28
1  
Almost exactly the same problem as in bash question about if and then; and very similar to how to write this if command? –  G-Man Oct 8 '14 at 16:33

3 Answers 3

There is a space between your dollar $ and your month variable:

cal $day $ month $year 2> /dev/null

It should be:

cal $day $month $year 2> /dev/null
share|improve this answer
    
Damn, what a rookie mistake by me, thanks for noticing :) The script works as intended now, i have the right output. –  grinke Oct 8 '14 at 17:16

In some Linux distros that I have checked (e,g, Ubuntu 14.04), the packaged cal comes from BSD and not GNU Coreutils. The BSD version does not seem to accept days as a parameter; only months and years. The Ubuntu version does have a -H YYYY-MM-DD option, but that doesn't seem to help.

Instead I would use the date utility. Assuming the GNU Coreutils under Linux I think I would rewrite your script something like:

#!/bin/bash

day=$((10#$1))
month=$((10#$2))
year=$((10#$3))

if date -d $year-$month-$day > /dev/null 2>&1; then
    # cal $month $year
    echo "This is a valid date"
else
    echo "This is an invalid date"
fi

Notes:

  • I am using the shell's own arithmetic expansion to validate input/remove leading zeros, instead of forking a new bc process for each parameter
  • I am using GNU date to parse the input date
  • The date command may be used directly as the if conditional expression. if works by checking process exit codes. Commonly the [ or [[ executables are used instead, but there is no reason other programs can be used if they exit with useful exit codes
  • I'm not sure if you actually wanted the cal output for correct dates or not. If you do, simply uncomment the cal line.
share|improve this answer

[[ is actually a command, and like other commands you need whitespace to separate its arguments:

if [[ $? -eq 0 ]]; then
# ...^
share|improve this answer
    
thanks, that makes sense now. –  grinke Oct 8 '14 at 17:11

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.