98

I have a SSL CRT file in PEM format. Is there a way that I can extract the common name (CN) from the certificate from the command line?

Braiam
  • 35,991
Naftuli Kay
  • 39,676

7 Answers7

136

If you have openssl installed you can run:

openssl x509 -noout -subject -in server.pem
Anthon
  • 79,293
Jeff Smith
  • 1,561
  • 11
    You can extract the CN out of the subject with: openssl x509 -noout -subject -in server.pem | sed -n '/^subject/s/^.*CN=//p' – Matthew Buckett Dec 04 '14 at 12:09
  • 1
    I modified what @MatthewBuckett said and used sed -e 's/^subject.*CN=\([a-zA-Z0-9\.\-]*\).*$/\1/' to get just the domain as I had additional details after the CN. Its not super strict matching for a valid CN but in most cases it works, you could be more slack and replace [a-zA-Z0-9\.\-] with [^/] but I am not certain that would always work. – flungo Jun 04 '15 at 16:11
  • 1
    Add \* to what @flungo used to support wildcard domains: sed -e 's/^subject.*CN=\([a-zA-Z0-9\.\-\*]*\).*$/\1/' ([^/] works in my case, though) – bryn Sep 12 '15 at 23:18
  • 1
    The sed commands suggested above won't work if the cert has Relative Distinguished Names (RDNs) specified after the Common Name (CN), for example OU (OrganizationalUnit) or C (Country). One way to cater for such cases would be an additional sed: openssl x509 -noout -subject -in server.pem | sed 's/^.*CN=//' | sed sed 's/\/.*$//'. – Ohad Schneider Jan 12 '17 at 15:45
  • 21
    Easier way to separate CN from other RDN/ATVs in Subject name: openssl x509 -noout -subject -nameopt multiline | grep commonName or for the value only | sed -n 's/ *commonName *= //p' – dave_thompson_085 Mar 22 '17 at 17:03
  • Hmm, I had to use my .crt, not my .pem but otherwise it worked. Not sure if something's set up differently (MacOS, OpenSSL 0.9.8zh 14 Jan 2016) – dwanderson Jul 24 '19 at 17:21
  • Simpler alternative to @dave_thompson_085 sed for getting the value after grep commonName is | awk '{print $3}' – fero Jun 14 '23 at 08:58
13
certtool -i < whatever.pem | egrep "^\s+Subject:"

Notice that's directing the file to standard input via <, not using it as argument. Sans egrep this will print the whole certificate out, but the CN is in the Subject: field near the top (beware there's also a CN value in the Issuer: field).

X.509 Certificate Information:
    Version: 3
    Serial Number (hex): 01
    Issuer: [...] CN=unixandlinux.ex  <- Not this one.
    Validity: ...
    Subject: CN=goldilocks

certtool is part of gnutls, if it is not installed just search for that. GnuTLS is a little nicer than OpenSSL, IMO.

goldilocks
  • 87,661
  • 30
  • 204
  • 262
3

I found the above answer, and found it to be very useful, but I also found that the certtool command syntax (on Ubuntu Linux, today) was noticeably different than described by goldilocks, as was the output. So, I thought it best to update that excellent answer with what might be "today's version."

The "i" option (now?) stands for "import," according to man certtool, so the proper command appears to be "d", "display." So, this command:

certtool d myfoo.crt

(The file-extension in my case just happens to be .crt not .pem ... this is not relevant.)

... produces output that, in relevant part, looks like this:

Common Name     : Foobar

Unquestionably, goldilocks was right: certtool output is much easier easier to work with than openssl in this case.

  • 2
    I suspect we are talking about completely different pieces of software. I have never seen a version of certtool that took options sans the usual operators (- or --), and man certtool for v. 3.5.8 (debian), 3.5.16 (fedora, the only version after that in the upstream stable branch is 3.5.17 from a month ago), GnuTLS's online documentation and, indeed, the online man page for Ubuntu 17.10 (same version as current debian) all refer to: – goldilocks Jan 17 '18 at 12:30
  • 1
    "-i, --certificate-info: Print information on the given certificate," whereas "-d" is "--debug". Very strange. O_o? – goldilocks Jan 17 '18 at 12:31
2

Using openssl and awk

  • openssl
    • -subject extracts only the subject, -multiline splits it to lines
  • awk
    • -F' = ' - Separate the fields by <space>=<space>
    • /commonName/ for only the lines that match commonName
    • {print $2} - print the second field
❯ openssl x509 -noout -subject -in cert.crt -nameopt multiline    
subject=
    countryName               = AU
    stateOrProvinceName       = NSW
    localityName              = Sydney
    organizationName          = Some Acme Company Pty Ltd
    organizationalUnitName    = Engineering
    commonName                = CommonName 123
    emailAddress              = engineering-support@acme.com.au

❯ openssl x509 -noout -subject -in cert.crt -nameopt multiline | awk -F' = ' '/commonName/ {print $2}' CommonName 123

Ramon
  • 131
1

I ended using:

openssl x509 -inform DER -noout -subject -nameopt oneline,-esc_msb -in test.pem | sed 's/.*CN = //' | sed 's/, OU =.*$//' | sed 's/\"//g' 

Notice the -nameopt oneline,-esc_msb which allows a valid output when the CN (common name) has special characters like accents for example.

sed 's/.*CN = //' removes the first part up to CN =

sed 's/, OU =.*$//' removes the last part from , OU =

sed 's/\"//g' Removes the quotes if any, noticed that sometimes CN comes with quotes and sometimes not.

Pretty sure there nicer and shorter ways to do it, but this one did the trick to me.

1

Old question, but I have found that some certs have values that are displayed by openssl on the same line as the commonName, separated by +.

I think this is dependent on how the subject common name is formed -- it seems to be possible to make the CN value a sequence of multiple subvalues.

An example of this is emailAddress, which can come out as commonName=Joe Bloggs + emailAddress=joe@example.org, even when using -nameopt multiline.

To get around this, my alternative is to use openssl asn1parse instead:

openssl asn1parse -in '/pathto/thecert.crt' |\
  awk -v FS=':' -v OFS='' '
    BEGIN          {e=0} 
    e==2           {$1="";$2="";$3="";print;exit} 
    /:commonName$/ {e++}
  '
  • 1
    I'm sure the output format of openssl asn1parse will never change and it will never come back to bite me... /s – jimbobmcgee Jan 27 '24 at 01:53
0

I used: openssl x509 -noout -subject -in mycert.crt | awk -F= '{print $NF}' add | sed -e 's/^[ \t]*//' If you can't live with the white space

djieno
  • 11