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.

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

myid.id:

28fe2baadbe8da32ed0b99c69b11c01b2d141bc5b732b81e0960086de52fc891

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

4 Answers 4

up vote 5 down vote accepted

Try:

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

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 at 16:32
    
@1_CR well that's exactly my problem right now :D –  polym Jul 25 at 16:34
    
it doesn't work somehow. awk 'length==64 && /^[[:xdigit:]]*/ did work. Mind the *. –  polym Jul 25 at 16:40
    
@polym: You must use + instead of *. Try the fixed. I don't know why the first does not work? –  Gnouc Jul 25 at 16:42
    
nope still doesn't work, weird. echo 'df79b8640f3198bcd80937e8c089fe5c5fc5fc3cba56d129f3f7b7084362f258' | awk '{sub(/\r/,"")} length == 64 && /^[[:xdigit:]]+/' does produce nothing. –  polym Jul 25 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 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

 
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.