qjebbs / vscode-plantuml

Rich PlantUML support for Visual Studio Code.
MIT License
1.1k stars 161 forks source link

Inconsistent Include Behavior when embedded in Markdown document. #567

Open jmpicnic opened 11 months ago

jmpicnic commented 11 months ago

First, thank you for creating this very helpful, fantastic plugin. I am using it extensively across several projects and it is invaluable.

I have run into a couple of !include issues when embedding plantuml in markdown documents and trying to preview the result in the default VS-Code Markdown Preview. After poking around a bit, I think that the issues are because when rendering in combination with the markdown preview, the plugin seems to ignore the plantuml.render: Local setting and use server rendering anyway and the server rendering does not seem to understand !include paths.

I am using Local to be able to pass values to plantuml.include.path and making the setup match the mkdocs document compilation environment for publishing.

Any hints for how to solve or work around this problem would be greatly appreciated.

The problem I am having:

In the markdown preview, !include only works when:

  1. The including file provides the absolute path from the root of the filesystem.
  2. The value of the !include parameter is the literal file path and not one composed using Plantuml variables

These cases work fine for "naked" Plantuml preview.

There are a couple of additional quirks of the "naked" Plantuml Preview when using Local setting, found while trying to sort out what was going on:

  1. %dirpath() does not work.
  2. When getting the PWD environment variable, the plugin reports the working directory to be the root of the file system.

Environment

Machine

image

VS-Code

Version

image

Workspace settings

{
    "plantuml.includepaths": [
         "docs"
    ],
    "plantuml.render": "Local",
    "plantuml.jar": "/opt/homebrew/Cellar/plantuml/1.2023.13/libexec/plantuml.jar",
    "terminal.integrated.env.osx": {
        "PLANTUML_SECURITY_PROFILE": "UNSECURE",
        "PLANTUML_LIMIT_SIZE": "8192"
    },
    "markdown.preview.fontSize": 12,
    "plantuml.diagramsRoot": "docs/assets/plantuml",
    "plantuml.fileExtensions": ".wsd,.pu,.puml,.plantuml,.iuml,.ipuml,.cfg,.md",
    "plantuml.server": "https://plantuml.com/plantuml/",
    "plantuml.commandArgs": [
        "-DPLANTUML_SECURITY_PROFILE=UNSECURE",
        "-DPLANTUML_LIMIT_SIZE=8192"
    ],
    "plantuml.exportIncludeFolderHeirarchy": false,
    "plantuml.exportFormat": "png"
}

Structure of the VS-Code workspace

<workspace>
└── docs
    ├── sampleclass.puml
    ├── sampleclass2.puml
    └── test.md

Info to reproduce the problem

  1. Markdown file that embeds a plantuml diagram
  2. Two simple plantuml files that get included.

Markdown File with embedded Plantuml (test.md)

With a bunch of output in the title for diagnostics.

You can reproduce the problem by toggling the variables:

    # A Small Markdown File

    With a plantuml diagram

    ```plantuml
    @startuml (id=SAMPLE)
    skinparam defaultTextAlignment left
    !$include_path = %getenv("plantuml.include.path")
    title 
      = FINDING THE VALUES FOR THE ENVIRONMENT
      VERSION:\t\t\t [%version()]
      $PROFILE:\t\t [%getenv("PLANTUML_SECURITY_PROFILE")]
      $LIMIT_SIZE:\t\t [%getenv("PLANTUML_LIMIT_SIZE")]
      $HOME:\t\t\t [%getenv("HOME")]
      $PWD:\t\t\t [%getenv("PWD")]
      %dirpath:\t\t [%dirpath()]\t\t\t << Should be here.
      %filename:\t\t [%filename()]
      !if ($include_path != "")
      Include Path is __set__
      !else
      Include Path is __**NOT** set__
      !endif
    end title

    !$toggle_relative_path = 0
    !if ($toggle_relative_path == 1)
      !include sampleclass.puml
    !else
      !include /Users/jmp/Documents/obsidian-docs/docs/sampleclass.puml
    !endif

    !$should_be_dirpath = "/Users/jmp/Documents/obsidian-docs/docs"

    !$toggle_composite = 0
    !if ($toggle_composite == 1) 
      !include $should_be_dirpath/sampleclass2.puml
    !else
      !include /Users/jmp/Documents/obsidian-docs/docs/sampleclass2.puml

    @enduml
### Two minimal plantuml files to include

#### File sampleclass.puml

```plantuml
@startuml

class SampleClass

@enduml

File sampleclass2.puml

@startuml

class SampleClass2 #lightBlue

@enduml

Working Output (no relative include paths, no composition of !include arguments)

Note that there are some weird discrepancies in the rendering of tabs, but that is minor...

From the Plantuml Preview window

This is using Local rendering

image

From the Markdown Preview window

image

And for "golden" reference, the command line result

with this executed from the workspace root:

% java -version
openjdk version "21" 2023-09-19 LTS
OpenJDK Runtime Environment Corretto-21.0.0.35.1 (build 21+35-LTS)
OpenJDK 64-Bit Server VM Corretto-21.0.0.35.1 (build 21+35-LTS, mixed mode, sharing)
% java -DPLANTUML_SECURITY_PROFILE=UNSECURE -DPLANTUML_LIMIT_SIZE=8192 -Dplantuml.include.path="docs" -Djava.awt.headless=true -jar /opt/homebrew/Cellar/plantuml/1.2023.13/libexec/plantuml.jar docs/test
.md

image

Errors Found

With $toggle_composite == 1

image

With $toggle_relative_path == 1

image

jmpicnic commented 11 months ago

Update:

If the plantuml.includepaths setting includes the absolute path from the root of the filesystem to the directory where the files are located, the plugin works.

There is still the difference in that when rendering inside markdown, it does not recognize the local directory as an origin for include files.

This setting fixed the toggle_relative_path case:

{
<...>
    "plantuml.includepaths": [
         "/Users/jmp/Documents/obsidian-docs/docs"
    ],
<...>
}