Code examples for extending PlantUML syntax is needed. Provided sample not working

0 votes
asked Mar 7 in Question / help by aibrahim (120 points)
edited Mar 7 by aibrahim

I have been trying for a quite time to see how can I extend PlantUML syntax using java or javascript.

as an example for what I want to have UML to support the following syntax

@startarchitecture
target_system My System -> external_system External System
@endarchitecture

This should generate a diagram with a connection between "My System"  which is drawn as oval and "External System" which is drawn as double lined border rectangle.

As a final trial to do so, I asked ChatGPT several questions to understand how to do implement that. I started with the following question

where can I find documentation for defining new plantuml syntax using java and javascript?

The answer was the following:

You can find the documentation for defining new PlantUML syntax using Java and JavaScript on the PlantUML website. The website provides detailed instructions on how to define new keywords, functions, and variables using both Java and JavaScript.

For Java, you can create a new plugin that extends the PlantUML syntax using the AbstractPuzzle class. The website provides a sample plugin that you can use as a starting point.

For JavaScript, you can create a new syntax highlighter that modifies the HTML generated by PlantUML. The website provides an example of a JavaScript-based syntax highlighter that adds a new keyword to the PlantUML syntax.

You can find more information on these topics, along with many examples and tutorials, on the PlantUML website.

But I didn't find any thing about the AbstractPuzzle class at any place !!!. So to validate the answer I asked the following question:

can you give me an example for a java file that extends the PlantUML syntax to include target_system as new keyword to be drawn as an oval?

And here was the answer from ChatGPT


Sure, here's an example Java file that extends the PlantUML syntax to add a new keyword called target_system that is drawn as an oval:

import net.sourceforge.plantuml.AbstractPuzzle;
import net.sourceforge.plantuml.Puzzle;
import net.sourceforge.plantuml.graphic.StringBounder;
import net.sourceforge.plantuml.graphic.SymbolContext;
import net.sourceforge.plantuml.graphic.TextBlock;
import net.sourceforge.plantuml.graphic.TextBlockOval;
import net.sourceforge.plantuml.graphic.UDrawable;
import net.sourceforge.plantuml.graphic.USymbol;
import net.sourceforge.plantuml.ugraphic.UShape;
import net.sourceforge.plantuml.ugraphic.UStroke;

public class TargetSystemPuzzle extends AbstractPuzzle {
    public TargetSystemPuzzle() {
        super("target_system");
    }

    @Override
    public Puzzle getNew() {
        return new TargetSystemPuzzle();
    }

    @Override
    public UDrawable getSymbol(StringBounder stringBounder, SymbolContext symbolContext, double x, double y,
                               double width, double height) {
        return new USymbol() {
            @Override
            public SkinParameter getSkinParameter() {
                return SkinParameter.ENTITY;
            }

            @Override
            public void drawU(UGraphic ug) {
                UShape oval = new TextBlockOval(width, height, UStroke.DEFAULT, symbolContext.getBackColor(),
                        symbolContext.getForeColor());
                oval.draw(ug.apply(new UTranslate(x, y)));
            }

            @Override
            public TextBlock asSmall(TextBlock name, TextBlock stereo, double scale) {
                return name;
            }
        };
    }

    @Override
    public boolean puzzle(String line, boolean isStart) {
        if (line.matches("^target_system\\s+.*")) {
            String text = line.replaceFirst("^target_system\\s+", "");
            TextBlock textBlock = getTextBlock(text);
            addField(textBlock, null, null, null, null, SkinParameter.ENTITY, false, null, null, null,
                    AbstractPuzzle.DEFAULT_LINE_COLOR, AbstractPuzzle.DEFAULT_STEREOTYPE_COLOR,
                    AbstractPuzzle.DEFAULT_LINE_STYLE, 0, 0, AbstractPuzzle.MAXX, AbstractPuzzle.MINY,
                    AbstractPuzzle.IMAL_WIDTH);
            return true;
        }
        return false;
    }
}

This code defines a new class TargetSystemPuzzle that extends the AbstractPuzzle class. The getSymbol method creates a new oval shape for the keyword target_system, and the puzzle method checks if the input line matches the pattern ^target_system.*. If so, it creates a new oval with the text following the keyword target_system.

To use this plugin, you need to compile the Java file and add the compiled class to the PlantUML classpath. You can then use the new keyword target_system in your PlantUML code, like this:

@startuml
target_system My System
@enduml

This will generate a diagram with an oval labeled "My System".


So it was clear that there is a dependency on this class to move forward to extend the syntax. But the problem is that I didn't find any thing regarding this class as well as no examples to do what I need to do.

So I asked it the following:

Can you give me URL links where I can find documentation for the AbstractPuzzle class and resources for more examples?

Its answer was the following:

Sure! Here are the links to the PlantUML documentation and examples:

  1. AbstractPuzzle class documentation: https://plantuml.com/en/abstractpuzzle

  2. PlantUML examples: https://plantuml.com/en/gallery

These resources should provide you with more information and examples to help you get started with extending the PlantUML syntax using Java.

And of course, these URL give me 404 - Not found error on the site.

My questions are:

  1. Where can I find documentation that can help me to develop what I need (using Java/JavaScript? 
  2. Why I can not find any thing related to AbstractPuzzle?
commented Mar 8 by aibrahim (120 points)
I got a feedback on slack overflow site, that questions based on ChatGPT code is forbidden as a lot of the code is not correct.

I am kind of start believing that, however I am still lost in the area of extending the syntax. So please don't address if the code is valid or not, as I understand that most probably it is invalid, but please guide me to an example or code that address my problem.

I appreciate your support.

Your answer

Your name to display (optional):
Privacy: Your email address will only be used for sending these notifications.
Anti-spam verification:

[Antispam2 Feature: please please wait 1 or 2 minutes (this message will disappear) before pressing the button otherwise it will fail](--------)
To avoid this verification in future, please log in or register.
...