Search code examples
batch-filecmdpandocfile-conversion

Pandoc Windows batch file builds wrong path openBinary file does not exist


THE ISSUE

This may just stem from a lack of deep understanding of Windows batch file coding.

I am trying to write a simple one-line batch file that will process every file in a directory using pandoc to convert all doc or docx (MS Word) files to markdown (.md) files. When I run my batch file I get the following error:

pandoc: C:_ALL\_ALL\accomp\testing-accomp-2017.05\20170505.md: openBinaryFile: does not exist (No such file or directory)

I get one of these errors for each file in the directory (around 25, or so).

The directory I'm running my command in looks like this:

C:\_ALL\!accomp\testing-accomp-2017.05

As you can see, for some reason the _ALL is appearing twice. The path it is showing me isn't right for some reason and I'm not sure if it is a pandoc issue or a CMD batch file programming issue.

MY CODE

Here is the code for my batch file:

@echo OFF

:: [Not sure what this does, but have read that it is necessary]
setlocal enabledelayedexpansion

:: MAIN
FOR /r "." %%i IN (*.doc *.docx) DO pandoc -f rst -t markdown "%%~fi" -o "%%~dpni.md"

:: End with a pause so user can copy any text from screen.
ECHO. Done. Press any key to terminate program
PAUSE>NUL

Now, I'm not certain what all these lines of code do, and they may be entirely unnecessary for all I know. However, the main and most important code here is the one that starts with For ..., which is inspired by this Stack Overflow post:

WHAT I'VE TRIED ALREADY

Basically there are about four variations of the same answer in the above linked post and I've tried each of those variations.


Solution

  • The error is caused by delayed expansion and the exclamation mark ! in directory name !accomp.

    The command line to execute by FOR expands during execution with file 20170505.doc to:

    pandoc -f rst -t markdown "C:\_ALL\!accomp\testing-accomp-2017.05\20170505.doc" -o "C:\_ALL\!accomp\testing-accomp-2017.05\20170505.md"
    

    This command line is parsed by Windows command processor a second time before execution because of enabled delayed environment variable expansion, searching for !variable! reference and replacing them with value of referenced variables.

    The string !accomp\testing-accomp-2017.05\20170505.doc" -o "C:\_ALL\! is completely misinterpreted here because of the exclamation marks. So finally executed is:

    pandoc -f rst -t markdown "C:\_ALL\\_ALL\accomp\testing-accomp-2017.05\20170505.md"
    

    And the file C:\_ALL\\_ALL\accomp\testing-accomp-2017.05\20170505.md does not exist.

    The solution is removing setlocal enabledelayedexpansion as not needed here because of no environment variable used on FOR command line.

    @ECHO OFF
    
    FOR /r "." %%i IN (*.doc *.docx) DO pandoc.exe -f rst -t markdown "%%i" -o "%%~dpni.md"
    
    :: End with a pause so user can copy any text from screen.
    ECHO Done. Press any key to terminate program ...
    PAUSE>NUL
    

    The loop variable i holds here already the full qualified file name. Therefore "%%~fi" can be replaced by "%%i".

    And it is better to use ECHO/ instead of ECHO. although neither . nor / is needed here. See DosTips forum topic ECHO. FAILS to give text or blank line - Instead use ECHO/ for the reason.