Skip to content

Instantly share code, notes, and snippets.

@ernstki
Last active September 3, 2023 21:03
Show Gist options
  • Save ernstki/d3094c51e92383ff5a607c61f50019c7 to your computer and use it in GitHub Desktop.
Save ernstki/d3094c51e92383ff5a607c61f50019c7 to your computer and use it in GitHub Desktop.
fc-json - print the output of `fc-cat` as JSON
#!/bin/sh
##
## fc-json - print output of 'fc-cat' as valid JSON
##
## Usage:
## $ fc-json | jq -SC .
##
## Author: Kevin Ernst <ernstki -at- mail.uc.edu>
## Date: 2 September 2023
## License: MIT
## Source: https://gist.githubusercontent.com/ernstki/d3094c51e92383ff5a607c61f50019c7
##
fc-cat | awk '
BEGIN {
FS = "[:\"]"
}
{
for (i=1; i<=NF; i++) {
if ($i ~ /=/) {
split($i, a, "=")
A[a[1]] = a[2]
}
if ("fullname" in A) {
for (k in A) {
B[A["fullname"]][k] = A[k]
}
}
}
}
END {
print "["
c = 0
for (fn in B) {
printf " {\n"
cc = 0
for (k in B[fn]) {
v = B[fn][k]
if (v == "True")
printf " \"%s\": true", k
else if (v == "False")
printf " \"%s\": false", k
else if (v ~ /^[0-9][.0-9]*$/)
printf " \"%s\": %s", k, v
else if (k ~ /(lang|style|charset)/) {
printf " \"%s\": [", k
split(v, a, k=="charset" ? " " : "[,|]")
for (i=1; i<length(a); i++) {
printf "\"%s\", ", a[i]
}
printf "\"%s\"", a[length(a)]
printf "]"
}
else
printf " \"%s\": \"%s\"", k, v
printf ++cc < length(B[fn]) ? ",\n" : "\n"
}
printf " }" (++c < length(B) ? ",\n" : "\n")
}
print "]"
}'
# vim: ft=awk
@ernstki
Copy link
Author

ernstki commented Sep 3, 2023

Renders the output of fc-cat as valid JSON. The fc-cat binary is likely already on your system, as part of the fontconfig package.

Maybe there are other/better tools that already do this, but I did it for the challenge. In particular, figuring out how to create valid JSON, since trailing commas aren't allowed.

Installation

GIST='https://gist.githubusercontent.com/ernstki/d3094c51e92383ff5a607c61f50019c7/raw/fc-json'
mkdir -p ~/bin
(curl $GIST || wget -O- $GIST) > ~/bin/fc-json 
chmod a+x ~/bin/fc-json

# make sure it works (if not, try logging out and back in)
fc-json | head

Most modern Unices will add ~/bin to your search path on login (if it exists), but if not, assuming the Bash shell:

dotprofile=~/.$([[ -f ~/.bash_profile ]] && echo bash_)profile
echo '
# add ~/bin/to my search path
export PATH="$HOME/bin:$PATH"' >> $dotprofile

Example usage

fc-json | jq -SC . | less -R

# list all fonts which do not include `en` language
fc-json | jq -r '.[] | select(.lang?|index("en")|not) | .fullname'

See also

  • Fontconfig Developers Reference, heading "FONT PROPERTIES" - freedesktop.org
  • ISO 639.2 "Codes for the Representation of Names of Languages" - loc.gov
    • can convert to JSON, CSV, or tab-delimited with this trick
      curl -sS https://www.loc.gov/standards/iso639-2/php/English_list.php \
        | pup 'table tbody tr td table tr json{}' \
        | jq -r 'map(.children | map(.text))[] | @tsv'

License

MIT.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment