有没有办法让Guice Grapher起作用?

9

在Guice图形化工具中存在一个bug,导致大多数或所有图形呈现出错。是否有解决方法或修复程序?

4个回答

16

我稍微修改了@wuppi的答案,以便隐藏类路径和长名称注释,使图表更加紧凑和易读。他的答案跟随着经过编辑的代码:

我觉得这个实用方法非常有用,对我来说从未打印出错误的图形。

关于style=invis的问题: Guice图形化插件生成一个dot文件,其将某些类设为不可见样式。下面发布的方法中的replaceAll()解决了这个问题。 其余代码与Guice示例几乎相同。

我已经合并了Scot对Guice 4.x的修复,其中还包括Tim的答案:

public class Grapher {
    public static void main(String[] args) throws Exception {
        Grapher.graph4("filename.dot", Guice.createInjector(new MyModule()));
    }
    public static void graph4(String filename, Injector inj) throws Exception {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        PrintWriter out = new PrintWriter(baos);

        Injector injector = Guice.createInjector(new GraphvizModule());
        GraphvizGrapher renderer = injector.getInstance(GraphvizGrapher.class);
        renderer.setOut(out);
        renderer.setRankdir("TB");
        renderer.graph(inj);    

        out = new PrintWriter(new File(filename), "UTF-8");
        String s = baos.toString("UTF-8");
        s = fixGrapherBug(s);
        s = hideClassPaths(s);
        out.write(s);
        out.close();
    }

    public static String hideClassPaths(String s) {
        s = s.replaceAll("\\w[a-z\\d_\\.]+\\.([A-Z][A-Za-z\\d_\\$]*)", "$1");
        s = s.replaceAll("value=[\\w-]+", "random");
        return s;
    }

    public static String fixGrapherBug(String s) {
        s = s.replaceAll("style=invis", "style=solid");
        s = s.replaceAll("margin=(\\S+), ", " margin=\"$1\", ");
        return s;
    }
}

当然你可以自由生成任何其他的文件名 :)


Jeff,我不知道你是否看到了@Tim的回答,但它对于最新版本的graphviz和Guice 3.0是必需的。我还没有尝试过4.0 beta。 - durron597

5

Guice 4.x的示例,包括Jeff和Tim的解决方案:

public class Grapher {
    public static void main(String[] args) throws Exception {
        Grapher.graph4("filename.dot", Guice.createInjector(new MyModule()));
    }
    public static void graph4(String filename, Injector inj) throws Exception {
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        PrintWriter out = new PrintWriter(baos);

        Injector injector = Guice.createInjector(new GraphvizModule());
        GraphvizGrapher renderer = injector.getInstance(GraphvizGrapher.class);
        renderer.setOut(out);
        renderer.setRankdir("TB");
        renderer.graph(inj);    

        out = new PrintWriter(new File(filename), "UTF-8");
        String s = baos.toString("UTF-8");
        s = fixGrapherBug(s);
        s = hideClassPaths(s);
        out.write(s);
        out.close();
    }

    public static String hideClassPaths(String s) {
        s = s.replaceAll("\\w[a-z\\d_\\.]+\\.([A-Z][A-Za-z\\d_]*)", "");
        s = s.replaceAll("value=[\\w-]+", "random");
        return s;
    }

    public static String fixGrapherBug(String s) {
        s = s.replaceAll("style=invis", "style=solid");
        s = s.replaceAll("margin=(\\S+), ", " margin=\"$1\", ");
        return s;
    }
}

1
小bug修复--在我使用的当前guice-grapher版本(4.0-beta)中,“margin”关键字前面没有空格,因此替换行应为:s = s.replaceAll("margin=(\S+), ", " margin="$1", "); 另外,非常感谢您提供的示例。 - chooks

2
使用最新版本的GraphViz时,我发现以下替换方法也有帮助(否则GraphViz会拒绝打开文件):
s.replaceAll(" margin=(\\S+), ", " margin=\"$1\", ")

-1
上面 hideClassPaths() 方法中的第一个 replaceAll 过于热心了 -- 它除了包名还会把类名也一起移除。应该改为:
s = s.replaceAll("\\w[a-z\\d_\\.]+\\.([A-Z][A-Za-z\\d_\\$]*)", "$1");

请注意添加美元符号,以便内部类名也能正常工作。

1
谢谢!请删除这个回答,然后在错误的回答上进行评论或编辑。 - Jeff Axelrod

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接