I have the following script in my /etc/cron.d:

19 15 * * * root /opt/scripts/clean-nexus-release-repo.sh

The clean-nexus-release-repo.sh script looks like this:

find /opt/sonatype-work/nexus/storage/releases/se/company* -regextype posix-extended -depth -regex '.*/r?[0-9]{5,7}[a-Z0-9_.-]*\.[0-9]{1,3}' -mtime +60 -type d -print -exec rm -r {} \;
find /opt/sonatype-work/nexus/storage/releases/nu/company -regextype posix-extended -depth -regex '.*/r?[0-9]{5,7}[a-Z0-9_.-]*\.[0-9]{1,3}' -mtime +60 -type d -print -exec rm -r {} \;

When I run the clean-nexus-release-repo.sh script from my shell everything works fine. When it is run through cron I get the following output:

find: Invalid range end
find: Invalid range end

This is the same error I get when I move the hyphen in the [a-Z0-9_.-] regular expression to an invalid position. I have tried the following but I still get the same error:

  • Specifying an absolute path to the find command
  • Escaping the hyphen with a backslash
  • Removing that hyphen

find --version gives:

find (GNU findutils) 4.4.2

Running on Linux devtools01 2.6.32-71.el6.x86_64 (CentOS Linux release 6.0)

  • afaik, range expressions are locale dependent, maybe you have a different locale environment in cron? does [a-zA-Z...] instead of [a-Z.....] work? – Gryphius Jan 8 '13 at 15:24
  • Indeed a-zA-Z works! Why would a-Z not work in other locales? Thank you! Please provide this as an answer and I will upvote and accept. – K Erlandsson Jan 8 '13 at 15:29
  • added as an answer – Gryphius Jan 8 '13 at 15:38

I'm not sure I can give the perfect technical explanation here. maybe someone else can improve the answer.

basically I remember range expressions being locale dependent, so [a-Z] does not necessarily mean the same thing as [a-zA-Z]

I think the relevant documentation is:


Within a bracket expression, a range expression consists of two characters separated by a hyphen. It matches any single character that sorts between the two characters, inclusive, using the locale's collating sequence and character set. For example, in the default C locale, ‘[a-d]’ is equivalent to ‘[abcd]’. Many locales sort characters in dictionary order, and in these locales ‘[a-d]’ is typically not equivalent to ‘[abcd]’; it might be equivalent to ‘[aBbCcDd]’, for example. To obtain the traditional interpretation of bracket expressions, you can use the ‘C’ locale by setting the LC_ALL environment variable to the value ‘C’.


[a-Z] works as intended with locale fr_FR.UTF-8, and probably with all UTF8 locales, but not with "C" locale, as previously answered.

A script run from cron inherits no locale, whereas the same script tested from command line inherits user locale (xx_XX.UTF-8). This explains the different behaviour.

  • 1
    You can put LANG=fr_FR.UTF-8 on a line near the top of your crontab file if you wanted to set a locale (for all entries in that crontab). – Cameron Kerr May 7 '15 at 14:19

Ok I think the problem is found with the way ranges are defined. a-Z means from ascii value of "a" (97) to ascii value "Z" (90) meaning that the range ends before it starts.

Why it works in the shell I'm not sure, but changing the regex from

-regex '.*/r?[0-9]{5,7}[a-Z0-9_.-]*\.[0-9]{1,3}'


-regex '.*/r?[0-9]{5,7}[a-zA-Z0-9_.-]*\.[0-9]{1,3}'

works for me.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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