I have a folder with subfolders in it and many libreoffice documents (.odt).

I need to find in which one there's a particular phrase.

I tried grep -ir "search phrase here" . but it only found the search phrase in an xml file.

Is there a way to search in documents that are not plain text files?

  • 1
    Have a look at Recoll. Jun 22, 2013 at 4:30
  • Is there a command line alternative?
    – To Do
    Jun 22, 2013 at 10:09
  • Recoll does have a poweful CLI interface. Jun 23, 2013 at 1:15
  • 1
    @Glutanimate, here's a thread specific to .odt files: ubuntuforums.org/showthread.php?t=899179. Recoll wants to pull in lot of qt dependencies.
    – user25656
    Jan 22, 2014 at 6:48

2 Answers 2


Finally, I resolved to using Recoll. It does a good job at finding information in files. Indexing is however slow and takes a lot of resources. This is not a problem if you do not run Recoll as a daemon, but only update the index manually when you're not using the computer.

To install it:

sudo apt install recoll
  • 1
    The "refresh index" option seems to be smart - building index on some 1250 files took a few dozen seconds, but after adding only 1 new file the refresh was instantaneous. It helps to just index your ~/Documents (or wherever you keep what you want to search), instead of the home directory (hidden configs?), or even the whole filesystem etc. Jul 16, 2017 at 21:08

I have the similar problem with OpenDocument (ODT document, OTT template) and Microsoft Word (DOC and DOCX documents, DOT and DOTX templates) files.

Currently, I'm happy with the following Bash script for recursive search:

if [ "$#" -ne 1 ]; then
    echo $"Usage: $(basename "$0") search_pattern"
    echo "You should have installed the following packages: odt2txt, docx2txt and libreoffice-writer"
    exit 1

printf "Looking for: $search_pattern\n"

find . -name '*.odt' -o -name '*.ott' -o \
  -name '*.docx' -o -name '*.dotx' -o \
     -name '*.doc' -o -name '*.dot' \
     -type f | while read -r doc; do

    doc_fullfilename=$(basename -- "$doc")

    case $doc_filetype in
        'odt' | 'ott')
        (odt2txt "$doc" 2>/dev/null | grep -i "$search_pattern") && echo "^ found in ODT/OTT: $doc" && echo
        'docx' | 'dotx')
        (docx2txt "$doc" - 2>/dev/null | grep -i "$search_pattern") && echo "^ found in DOCX/DOTX: $doc" && echo
        'doc'| 'dot')
        lowriter --headless --convert-to txt:Text "$doc" --outdir "$out_dir" 2>&1 > /dev/null
        grep -i "$search_pattern" "$out_dir/$doc_filename.txt" && echo "^ found in DOC/DOT: $doc" && echo
: ; done

It shows search results and file-names.


  1. the script uses three external programs - odt2txt (for ODT/OTT), docx2txt (for DOCX/DOTX), libreoffice-writer (for DOC/DOT).
  2. theoretically, all these programs may be changed to only one - LibreOffice Writer, but it significantly slower for ODT/OTT and DOCX/DOTX.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

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