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.

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

Let's say, I have files that contain only one docker id:



I want to check if the content of my.id is exactly 64 characters long and contains only characters in the range [0-9] and [a-z] (maybe [a-f]).

  • How can I do that?
  • If the file contains a newline 0x0a, how can I include/exclude it in this check?
share|improve this question
up vote 5 down vote accepted


$ echo 28fe2baadbe8da32ed0b99c69b11c01b2d141bc5b732b81e0960086de52fc891 | 
awk '{sub(/\r/,"")} length == 64 && /^[[:xdigit:]]+$/'

or use perl instead.

Include newline:

perl -ne 'print if length == 64 and /^[[:xdigit:]]+$/'

Exclude newline:

perl -nle 'print if length == 64 and /^[[:xdigit:]]+$/'
share|improve this answer
Thank you. Can you also answer the added second question that I just encountered? – polym Jul 25 '14 at 16:32
@1_CR well that's exactly my problem right now :D – polym Jul 25 '14 at 16:34
it doesn't work somehow. awk 'length==64 && /^[[:xdigit:]]*/ did work. Mind the *. – polym Jul 25 '14 at 16:40
@polym: You must use + instead of *. Try the fixed. I don't know why the first does not work? – cuonglm Jul 25 '14 at 16:42
nope still doesn't work, weird. echo 'df79b8640f3198bcd80937e8c089fe5c5fc5fc3cba56d129f3f7b7084362f258' | awk '{sub(/\r/,"")} length == 64 && /^[[:xdigit:]]+/' does produce nothing. – polym Jul 25 '14 at 16:45

How about a whole-line grep

grep -qxE '[[:xdigit:]]{64}' myid.id && echo "yes"

or (not sure about this one) bash-specific

IFS= read -r id < myid.id 
[[ ${#id} -eq 64 ]] && [[ $id =~ [[:xdigit:]]{64} ]] && echo "yes"
share|improve this answer
Or grep -qE '^[[:xdigit:]]{64}$' myid.id. – Scott Jul 25 '14 at 20:24
read s <./file
[ ${#s} -eq 64 ] &&
[ -n "${s##*[![:alnum:]]*}" ] && 
echo success\!

If you decide to restrict the test to a-f then change [:alnum:] to [:xdigit:]. Though it's worth mentioning that any application using the POSIX classes [:alnum:] and/or [:xdigit:] will match A-[ZF] as well - it's part of the spec... If that's a problem you might want to add one more test like:

...&& [ -n "${s##*[[:upper:]]*}" ] &&...
share|improve this answer

Try this out:

 echo 28fe2baadbe8da32ed0b99c69b11c01b2d141bc5b732b81e0960086de52fc891 | grep [:0-9a-z:] |  wc -c
share|improve this answer

Your Answer


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.