Skip to content
Snippets Groups Projects
Commit 2ebbfb8f authored by Andreas Kraft's avatar Andreas Kraft
Browse files

Added --outfile command line argument. Improved ToC insertion

parent 4f256c8d
No related branches found
No related tags found
No related merge requests found
# Generate TOC for Markdown files # Generate TOC for Markdown files
The script will generate a TOC for a Markdown file, based on the headers in the file. The script will generate a Table of Contents for a Markdown file, based on the headers in the file.
It generates and prints the TOC to the console, and optionally also inserts it into the original file. It generates and prints the TOC to the console, and optionally also inserts it into the original file.
For the latter, it will first create a backup copy of the file and then replace any section named "# Contents" with the new table of contents **in the original input document**. For the latter, it will first create a backup copy of the file and then replace any section named "# Contents" with the new table of contents **in the original input document**. To keep the original document intact, it may be a good idea to first create a backup copy of the document and work on that copy.
Alternatively, one can specify an output file name with the `--outfile` option. The script will then create a new file.
### Support for Table-of-Content Tags ### Support for Table-of-Content Tags
Some renderers support special tags in the Markdown document to automatically insert a TOC. This script supports the following tags: Various markdown renderers support special tags in the Markdown document to automatically insert a TOC. This script supports the following tags:
- `<!--TOC-->` - `<!--TOC-->`
- `[TOC]` - `[TOC]`
- `[CONTENT]` - `[CONTENT]`
If the `--toctags` and `--add-content` options are specified, the script will replace these tags with the generated TOC in the original input document. To keep the original document intact, it may be a good idea to first create a backup copy of the document and work on that copy. If the `--toctags` and `--add-content` options are specified, the script will replace these tags with the generated TOC in the original input document.
## Prerequisites ## Prerequisites
- Python 3.8 or higher - Python 3.10 or higher
## Usage ## Usage
...@@ -46,5 +48,8 @@ options: ...@@ -46,5 +48,8 @@ options:
indent spaces for each level (default: 4) indent spaces for each level (default: 4)
--level LEVELS, -l LEVELS --level LEVELS, -l LEVELS
limit the TOC levels; 0 means no limit (default: 0) limit the TOC levels; 0 means no limit (default: 0)
--outfile OUTFILE, -o OUTFILE
set the output file name; if not set, the input file will be
overwritten (default: None)
--toc-tags, -t replace special TOC tokens in the document (default: False) --toc-tags, -t replace special TOC tokens in the document (default: False)
``` ```
\ No newline at end of file
...@@ -13,7 +13,7 @@ import argparse, os, re ...@@ -13,7 +13,7 @@ import argparse, os, re
from rich import print from rich import print
tocTags:[str] = ['[TOC]', '[CONTENT]', '<!--TOC-->'] tocTags:list[str] = ['[TOC]', '[CONTENT]', '<!--TOC-->']
""" TOC tags to replace in the document with the TOC. """ """ TOC tags to replace in the document with the TOC. """
def backupFile(filename:str) -> None: def backupFile(filename:str) -> None:
...@@ -78,32 +78,38 @@ def processDocument(args:argparse.Namespace) -> None: ...@@ -78,32 +78,38 @@ def processDocument(args:argparse.Namespace) -> None:
headers.append((headline, level)) headers.append((headline, level))
# Prepare and Print the table of contents # Prepare and Print the table of contents
to = '# Contents\n\n' toc = '# Contents\n\n'
for h in headers: for h in headers:
to += '&nbsp;' * (h[1] * args.indent) + f'[{h[0]}](#{prepareTOClink(h[0])}) \n' toc += '&nbsp;' * (h[1] * args.indent) + f'[{h[0]}](#{prepareTOClink(h[0])}) \n'
to = re.sub('<[^<]+?>', '', to) toc = re.sub('<[^<]+?>', '', toc)
# Write the TOC to the console # Write the TOC to the console
print(to) print(toc)
# Add the TOC to the document # Add the TOC to the document
# The TOC replaces the old TOC if it exists in the section "# Contents" # The TOC replaces the old TOC if it exists in the section "# Contents"
if args.addContent: # An outfile explicitly enables the TOC to be added to the document
backupFile(args.document) if args.addContent or args.outfile:
outDocument = args.document if not args.outfile else args.outfile
backupFile(outDocument)
tocDone = False
# Add the TOC to the document # Add the TOC to the document
with open(args.document, 'w') as f: with open(outDocument, 'w') as f:
inToc = False inToc = False
for line in document: for line in document:
# Skip the old TOC when writing # Skip the old TOC when writing
if inToc: if inToc:
if not line.strip().startswith('#'): if not line.strip().startswith('#'):
continue continue
f.write('\n') # Add a newline
inToc = False inToc = False
tocDone = True
# Write the new TOC in the right place # Write the new TOC in the right place
if not tocDone:
if (args.tocTags and line.strip() in tocTags) or line.strip() == '# Contents': if (args.tocTags and line.strip() in tocTags) or line.strip() == '# Contents':
inToc = True inToc = True
f.write(to) f.write(toc)
continue continue
# Write the rest # Write the rest
...@@ -136,6 +142,7 @@ if __name__ == '__main__': ...@@ -136,6 +142,7 @@ if __name__ == '__main__':
parser.add_argument('--contents', '-c', action='store_true', dest='contents', default = False, help = 'add link to "Contents" section in the generated TOC') parser.add_argument('--contents', '-c', action='store_true', dest='contents', default = False, help = 'add link to "Contents" section in the generated TOC')
parser.add_argument('--indent', '-i', action='store', dest='indent', type = nonNegativeInt, default = 4, metavar = '<indent>', help = 'indent spaces for each level') parser.add_argument('--indent', '-i', action='store', dest='indent', type = nonNegativeInt, default = 4, metavar = '<indent>', help = 'indent spaces for each level')
parser.add_argument('--level', '-l', action='store', dest='levels', type = nonNegativeInt, default = 0, help = 'limit the TOC levels; 0 means no limit') parser.add_argument('--level', '-l', action='store', dest='levels', type = nonNegativeInt, default = 0, help = 'limit the TOC levels; 0 means no limit')
parser.add_argument('--outfile', '-o', action='store', dest='outfile', help = 'set the output file name; if not set, the input file will be overwritten')
parser.add_argument('--toc-tags', '-t', action='store_true', dest='tocTags', default = False, help = 'replace special TOC tokens in the document') parser.add_argument('--toc-tags', '-t', action='store_true', dest='tocTags', default = False, help = 'replace special TOC tokens in the document')
parser.add_argument('document', help = 'document to parse') parser.add_argument('document', help = 'document to parse')
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment