mikitex70 / plantuml-markdown

PlantUML plugin for Python-Markdown
BSD 2-Clause "Simplified" License
192 stars 55 forks source link

Guidance on how to use with mkdocs #52

Closed mdeliw closed 3 years ago

mdeliw commented 3 years ago

The plugin converts markdowns into html, so can't be used a preprocessor for mkdocs - which expects markdown as input.

mikitex70 commented 3 years ago

Can you give me an mkdocs example configuration which does not work so I can try to fix the plugin?

mdeliw commented 3 years ago

The approach I took may not be correct or ideal, and I appreciate your help.

I adjusted squidfunk's Dockerfile, mkdocs.yml, and requirements.txt to include the approach taken by https://github.com/amarraja/mkdocs-material-plantuml to create a revised image based on squidfunk to include your plugin and plantuml.jar, graphviz, jre ... etc. The image was created fine, but the build doesn't render plantuml.

Steps I took:

mikitex70 commented 3 years ago

I've made some test with your configuration and the only error I've found is that in the mkdocs.yml the plugin must be named plantuml_markdon instead of plantuml-markdown. Doing so the diagrams are rendered correctly using the notation ```plantuml.

The @staruml/@enduml block is ignored because is not a Markdown code block, and is treated as normal text.

Your screenshots shows what happens when the plugin plantuml_markdown is not installed.

The plugin is called whenever a code block with type plantuml or uml is found by the markdown command and so it contributes to produce the final html document. It is a plugin for markdown, not a pre-processor for taking in input markdown documents and producing markdown documents, that after can be translated in html with the markdown command. Check your configuration and the containers logs, it should report some error or warning during the startup.

mdeliw commented 3 years ago

Thank you. I made the changes as follows:

squidfunk/mkdocs-material-puml is my revised docker image. I could get plantuml.jar to run, but got a headlessexception. I changed the java command to include -Djava.awt.headless=true but that didn't resolve the issue. I don't know if openjdk8-jre is the issue or something else.

√ mkdocs.squidfunk > docker run --rm -t -v ${PWD}:/docs squidfunk/mkdocs-material-puml build
INFO    -  Cleaning site directory
INFO    -  Building documentation to directory: /docs/site
Error in "uml" directive: b'Mar 08, 2021 3:34:06 AM java.util.prefs.FileSystemPreferences$1 run\nINFO: Created user preferences directory.\nException in thread "main" java.awt.HeadlessException\n\tat java.awt.GraphicsEnvironment.checkHeadless(GraphicsEnvironment.java:204)\n\tat java.awt.Window.<init>(Window.java:536)\n\tat java.awt.Frame.<init>(Frame.java:420)\n\tat javax.swing.JFrame.<init>(JFrame.java:232)\n\tat net.sourceforge.plantuml.swing.MainWindow2.<init>(MainWindow2.java:159)\n\tat net.sourceforge.plantuml.Run.main(Run.java:174)\n'
Error in "uml" directive: b'Exception in thread "main" java.awt.HeadlessException\n\tat java.awt.GraphicsEnvironment.checkHeadless(GraphicsEnvironment.java:204)\n\tat java.awt.Window.<init>(Window.java:536)\n\tat java.awt.Frame.<init>(Frame.java:420)\n\tat javax.swing.JFrame.<init>(JFrame.java:232)\n\tat net.sourceforge.plantuml.swing.MainWindow2.<init>(MainWindow2.java:159)\n\tat net.sourceforge.plantuml.Run.main(Run.java:174)\n

The enhanced Dockerfile is as follows:

# Copyright (c) 2016-2021 Martin Donath <martin.donath@squidfunk.com>

# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to
# deal in the Software without restriction, including without limitation the
# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
# sell copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:

# The above copyright notice and this permission notice shall be included in
# all copies or substantial portions of the Software.

# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
# IN THE SOFTWARE.

FROM python:3.8.7-alpine3.12

# Build-time flags
ARG WITH_PLUGINS=true

# Environment variables
ENV PACKAGES=/usr/local/lib/python3.8/site-packages
ENV PYTHONDONTWRITEBYTECODE=1

# Set build directory
WORKDIR /tmp

# Copy files necessary for build
COPY material material
COPY MANIFEST.in MANIFEST.in
COPY package.json package.json
COPY README.md README.md
COPY requirements.txt requirements.txt
COPY setup.py setup.py

# Perform build and cleanup artifacts and caches
RUN \
  apk add --no-cache \
    git \
    git-fast-import \
    openssh \
    curl \
    openjdk8-jre \
    graphviz \
  && apk add --no-cache --virtual .build gcc musl-dev \
  && pip install --no-cache-dir . \
  && curl -L https://sourceforge.net/projects/plantuml/files/1.2021.1/plantuml.1.2021.1.jar/download > /opt/plantuml.jar \
  && printf "#!/bin/sh \
  \njava -Djava.awt.headless=true -jar /opt/plantuml.jar $@" > /usr/bin/plantuml \
  && chmod 755 /usr/bin/plantuml \
  && cat /usr/bin/plantuml \
  && \
    if [ "${WITH_PLUGINS}" = "true" ]; then \
      pip install --no-cache-dir \
        "mkdocs-minify-plugin>=0.3" \
        "mkdocs-redirects>=1.0"; \
    fi \
  && apk del .build gcc musl-dev \
  && \
    for theme in mkdocs readthedocs; do \
      rm -rf ${PACKAGES}/mkdocs/themes/$theme; \
      ln -s \
        ${PACKAGES}/material \
        ${PACKAGES}/mkdocs/themes/$theme; \
    done \
  && rm -rf /tmp/* /root/.cache \
  && \
    find ${PACKAGES} \
      -type f \
      -path "*/__pycache__/*" \
      -exec rm -f {} \;

# Set working directory
WORKDIR /docs

# Expose MkDocs development server port
EXPOSE 8000

# Start development server by default
ENTRYPOINT ["mkdocs"]
CMD ["serve", "--dev-addr=0.0.0.0:8000"]
mdeliw commented 3 years ago

I replaced -Djava.awt.headless=true to -headless, and now I get the following error:

√ mkdocs.squidfunk > docker run --rm -t -v ${PWD}:/docs squidfunk/mkdocs-material-puml build
INFO    -  Cleaning site directory
INFO    -  Building documentation to directory: /docs/site
Error in "uml" directive: b'No diagram found\n'
Error in "uml" directive: b'No diagram found\n'

A sample markdown is as follows:

Riskology Docs

```plantuml
  Goofy -> MickeyMouse: calls
  Goofy <-- MickeyMouse: responds
  Goofy ->  MickeyMouse: calls
  Goofy <-- MickeyMouse: responds
mdeliw commented 3 years ago

Its raising exception in this code:

@staticmethod
    def _render_local_uml_image(plantuml_code, img_format):
        plantuml_code = plantuml_code.encode('utf8')
        cmdline = ['plantuml', '-p', "-t" + img_format]

        try:
            # On Windows run batch files through a shell so the extension can be resolved
            p = Popen(cmdline, stdin=PIPE, stdout=PIPE, stderr=PIPE, shell=(os.name == 'nt'))
            out, err = p.communicate(input=plantuml_code)
        except Exception as exc:
            raise Exception('Failed to run plantuml: %s' % exc)
        else:
            if p.returncode != 0:
                # plantuml returns a nice image in case of syntax error so log but still return out
-->           print('Error in "uml" directive: %s' % err)

            return out
mdeliw commented 3 years ago
Screen Shot 2021-03-07 at 9 48 58 PM

Server option works, local doesn't

mikitex70 commented 3 years ago

I've made my test using a local plantumlinstallation and all is working fine. The problen is in the /usr/bin/plantuml shell script: the $@ argument is missing. Escape it or replace double quotes with single quotes in the printf command so the docker build will no try to replace that variable.

mdeliw commented 3 years ago

&& printf '#!/bin/sh\n\n java -jar /opt/plantuml.jar -headless ${@}' > /usr/bin/plantuml \. worked . Thanks.