Skip to content

Commit

Permalink
Merge pull request #8 from aa9863/MainScripts
Browse files Browse the repository at this point in the history
Main scripts
  • Loading branch information
aa9863 committed Jul 3, 2020
2 parents 3100178 + be9b7c4 commit fe3e9d0
Show file tree
Hide file tree
Showing 11 changed files with 319 additions and 5 deletions.
12 changes: 12 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# 0.2

- Command line scripts added

# 0.1.1

- Allow both stock and user supplied templates
- Template inheritance

# 0.1

- Rendering from templates via python functions
93 changes: 93 additions & 0 deletions MarkdownMark/controller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,93 @@
"""
Use Markdown to generate various uni documents

Controller code to get the workflows working.

Two use cases at the moment:

1. Called with all parts specifid
- Template
- Input File
1. Called with just an input file. Which contains the template.

I would then plumb this to a command line script.

```
markdownmark <input> -t [template] [output]
```


Exceptions to check for

- jinja2.exceptions.TemplateNotFound


Things to think about:

1. Batch conversion, point him at a directory
1. PDF conversion, use something (QT?) to render the HTML to PDF.
"""

import logging

import os
import pathlib

import MarkdownMark.markdownParser as parser
import MarkdownMark.renderer as renderer


class RenderError(Exception):
"""Exception raised for errors in the input.


@message: explanation of the error
"""

def __init__(self, message):
self.message = message



def convertFile(inputFile, templateFile = None, templateDir=None, outputFile = None):
"""
Given a set of options convert a file from markdown
to a nicely rendered output.

The template file can be specified as part of the function, or in the header file.
NOTE: options specified to the function will overwrite anything in the template.

@param inputFile: The Markdown File we want to render
@param templateFile: Template file to use to render.
@param templateDir: Optional Local Template directory
@param outputFile: Output file, defaults to <input>.hmtl
"""

log = logging.getLogger("[CONTROLER]")
log.debug(" Dealing with Input file {0}".format(inputFile))

#Create a parser for this input file
theParser = parser.markdownParser(inputFile)
theParser.parseFile()
#Check for Header
if theParser.header:
#Check for either template dir or template file in the header
if templateFile is None:
templateFile = theParser.header.get("template")

if templateDir is None:
templateDir = theParser.header.get("templatedir")

if templateFile is None:
raise RenderError("No Template has been specified")
#Feed this to the Renderer
theRenderer = renderer.HTMLRenderer(templateFile, templateDir)

#We also need to know where to output the thing.
if outputFile is None:
log.debug("No Output file specified")

outputFile = "{0}.html".format(pathlib.Path(inputFile).stem)
log.debug("Output File is now {0}".format(outputFile))

theRenderer.toFile(theParser, outputFile)
Empty file.
41 changes: 41 additions & 0 deletions MarkdownMark/scripts/runDMC.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
import optparse


import MarkdownMark.controller as controller


def main():
usage = "%prog inputfile.md [options]"
description = "TODO: Longer Desc here"
parser = optparse.OptionParser(usage=usage,
description = description,
version="2.0")
parser.add_option("-t","--template",
dest="template",
help="Template file to use for rendering"
)
parser.add_option("-d","--templatedir",
dest="templatedir",
help="Local template directory",
),

parser.add_option("-o","--output",
dest="output",
help="Name of output file"
)


(options, args) = parser.parse_args()
if len(args) < 1:
parser.print_usage()
return -1


#Otherwise
controller.convertFile(args[0],
templateFile = options.template,
templateDir = options.templatedir,
outputFile = options.output)

if __name__ == "__main__":
main()
4 changes: 4 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -31,3 +31,7 @@ Or to stop and capture outputs
```
pytest -x -s
```

Or Nicer HTML output

pytest --html=report.html
12 changes: 9 additions & 3 deletions setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,20 @@
name="MarkdownMark",
author="Dan Goldsmith",
author_email="djgoldsmith@googlemail.com",
version="0.1.1",
version="0.2.0",
#Dependencies
install_requires=requires,
tests_require=testRequires,
#Load the Library
packages=find_packages(),
package_data = {"MarkdownMark": ["templates/"]}
#package_data = {"" : ["templates/"]}
package_data = {"MarkdownMark": ["templates/"]},

#And scripts
entry_points = {
"console_scripts":[
"runDMC = MarkdownMark.scripts.runDMC:main"
]
}
)


8 changes: 8 additions & 0 deletions test/inputs/inputController.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
---
template: controller.jinja2
templatedir: test/templates
---

# TheInput

Some Input from a markdown file
3 changes: 3 additions & 0 deletions test/inputs/inputControllerNoHead.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# TheInput

Some Input from a markdown file
4 changes: 4 additions & 0 deletions test/templates/controller.jinja2
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
<h1>Template Output</h1>
<h2>Markdown Input</h2>

{{ TheInput.markdown() }}
121 changes: 121 additions & 0 deletions test/test_controller.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
"""
Testing for the Main Methods and Script Functions
"""

import unittest
import os
import jinja2

import MarkdownMark.controller as controller

class controllerTest(unittest.TestCase):
"""
Tests for the controller.

The controller should allow us to bring all the parts togeter.
Meaning we can call controller.render(params) to get an sensible output.

```convertFile(inputFile, templateFile = None, templateDir=None, outputFile = None):```
"""

def tearDown(self):
"""
Called before all tests, make sure the tmp directory is clean
"""
if os.path.exists("/tmp/render.html"):
os.remove("/tmp/render.html")

#And if we dont sepcify a file
if os.path.exists("inputController.html"):
os.remove("inputController.html")

def testConvertAll(self):
""" Convert with all parameters supplied """

controller.convertFile("test/inputs/inputController.md",
"controller.jinja2",
"test/templates",
outputFile = "/tmp/render.html")
self._checkOutput()


def testConvertHeaderTemplate(self):
"""
Convert using template specified in the header.

If we don't specify a template when calling the function,
we look in the file header for a ```template:``` and use that
"""

controller.convertFile("test/inputs/inputController.md",
templateFile = None,
templateDir = "test/templates",
outputFile = "/tmp/render.html")
self._checkOutput()

def testNoOutput(self):
"""
If no output file is specified, we render as <input>.html
"""

controller.convertFile("test/inputs/inputController.md",
)

self._checkOutput("inputController.html")


def testInputOnly(self):
"""
Run the command with only the input file supplied

This should take the template and template dir from the header
Filemane defaults to the file inputs
"""


controller.convertFile("test/inputs/inputController.md"
)

self._checkOutput("inputController.html")

def testHeaderException(self):
"""
Throw an Exception if there is no template supplied

If no template is supplied we need to throw and exeption
"""

with self.assertRaises(controller.RenderError):
out = controller.convertFile("test/inputs/inputControllerNoHead.md")

#Can I unit test the exception message?


def testMissingTemplate(self):
"""
Throw an Exception if we cannot find the template

If the template doesn't exist, we also throw an exception
"""

with self.assertRaises(jinja2.exceptions.TemplateNotFound):
out = controller.convertFile("test/inputs/inputController.md", templateFile = "missing.jinja")


def _checkOutput(self, outFile = "/tmp/render.html"):
"""
Helper function to check the output

We are going for very simple templating here
"""

expected = """<h1>Template Output</h1>
<h2>Markdown Input</h2>

<p>Some Input from a markdown file</p>"""

fd = open(outFile, "r")
out = fd.read()
fd.close()

self.assertEqual(out, expected)
26 changes: 24 additions & 2 deletions test/test_render.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import MarkdownMark.markdownParser as parser
import MarkdownMark.renderer as renderer
import jinja2

"""
God I hate testing web output.
Expand Down Expand Up @@ -272,7 +273,6 @@ def testTemplateInheritance(self):
"""
theRenderer = renderer.HTMLRenderer("testInherit.jinja2", "test/templates")
out = theRenderer.render(self.theParser)
print (out)
expected = """<h1>Inherit From Templates</h1>

<h2>Introduction</h2>
Expand Down Expand Up @@ -308,7 +308,6 @@ def testTemplateBaseInheritance(self):
"""
theRenderer = renderer.HTMLRenderer("testBaseInherit.jinja2", "test/templates")
out = theRenderer.render(self.theParser)
print (out)
expected = """<h1>Inherit From Base</h1>

<h2>Introduction</h2>
Expand All @@ -335,3 +334,26 @@ def testTemplateBaseInheritance(self):
"""

self.assertEqual(out, expected)


def testRenderException(self):
"""
Throw an exception if we cannot find the template
"""

with self.assertRaises(jinja2.exceptions.TemplateNotFound):
theRenderer = renderer.HTMLRenderer("missing.jinja2")


def testRenderExceptionLocal(self):
"""
Throw an exception if we cannot find the template locally
"""

with self.assertRaises(jinja2.exceptions.TemplateNotFound):
theRenderer = renderer.HTMLRenderer("missing.jinja2", "test/templates")





0 comments on commit fe3e9d0

Please sign in to comment.