Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 27 additions & 7 deletions graph-visualization/README.md
Original file line number Diff line number Diff line change
@@ -1,17 +1,37 @@
# Render Graph Visualizations

This [node.js](https://nodejs.org/de) project provides the script [renderVisualizations.js](./renderVisualizations.js) to save all graph visualizations as image files.
This [node.js](https://nodejs.org/de) project provides the script [renderVisualizations.js](./renderVisualizations.js) to render all graph visualizations as image files.

## Prerequisites

- Run `npm ci` in this directory to download all necessary dependencies.

## How it works

[renderVisualizations.js](./renderVisualizations.js) uses these three steps:

- opens every HTML file with [Puppeteer](https://pptr.dev) in a headless browser
- takes screenshots of all contained [HTML5 Canvas elements](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/canvas?retiredLocale=de)
- saves them as [PNG](https://en.wikipedia.org/wiki/PNG) files in the current directory
- Opens every HTML file in this directory and its subdirectories with [Puppeteer](https://pptr.dev) in a headless browser
- Takes screenshots of all contained [HTML5 Canvas elements](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/canvas?retiredLocale=de)
- Creates a directory with the name of the HTML converted to snake case in the current directory
- Saves all screenshots as [PNG](https://en.wikipedia.org/wiki/PNG) files into that newly created directory

## Example
## How to run it in the CLI

If the current working directory is e.g. `temp/projectname/reports/graph-visualizations` within this repository,
then the command would look like this:
Under the assumption that your current working directory is `temp/projectname/reports/graph-visualizations` in the root directory of this repository, then the command would look like this:

```shell
node ./../../../../graph-visualization/renderVisualizations
```

## How to open it in the browser

- Open one of the HTML files in the Browser using `file://` prefix followed by the full path or using a Live Server.
- Enter the password for the local Neo4j database `neo4j` that you have chosen as initial password.
- Wait until the orange frames turn green and use drag'n'drop or scrolling to see the part of the Graph you're interested in.
- Currently, the frames are intentionally very large to get a practicable resolution for saving the images. This might get refined in future.

## Scripts

- [renderVisualizations.js](./renderVisualizations.js) is the main Node.js script that renders the Graph Visualizations using a Command Line Interface (CLI)
- [vis-configuration-presets.js](./vis-configuration-presets.js) contains functions that return predefined visualization configurations. Currently (May 2024), there is only one configuration for visualizing hierarchical, topology sorted Graphs.
- [visualization-pagination.js](./visualization-pagination.js) provides pagination for visualizing large Graphs by splitting them up into smaller Subgraphs all in separate images.

This file was deleted.

5 changes: 5 additions & 0 deletions graph-visualization/index.css
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,11 @@ div {
height: 100vh;
}

div.vis-tooltip {
font-size: 4px;
overflow-y: auto;
}

.indexedVisualization {
margin-top: 10px;
margin-left: 10px;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,13 +6,14 @@
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">

<title>Graph Visualization with neovis.js</title>
<title>Java Artifact Dependencies Graph Visualization with neovis.js</title>

<link rel="stylesheet" href="./../index.css">
<script src="./../node_modules/neovis.js/dist/neovis.js"></script>
<script type="text/javascript" src="./../vis-configuration-presets.js"></script>
<script type="text/javascript" src="./../visualization-pagination.js"></script>
<script type="text/javascript" src="artifactDependenciesGraph.js"></script>
<script type="text/javascript" src="graphVisualizationJavaArtifactDependencies.js"></script>

<link rel="stylesheet" href="./../index.css">
</head>

<body">
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
function getNeo4jCredentials() {
return {
serverUrl: "bolt://localhost:7687",
serverUser: "neo4j",
serverPassword: document.getElementById("neo4j-server-password").value,
};
}

function getConfiguration(credentials, visConfiguration, containerId = "visualizations") {
return {
containerId: containerId,
neo4j: credentials,
visConfig: visConfiguration,
// Note: "defaultLabelConfig" is used instead of named label configs: { NameOfTheLabel: {...}, ...}
// The reason for that is that neovis.js takes the first label that is returned by Neo4j.
// If there are multiple Labels this is not stable to use.
// Since we only expect one type of labels here (homogenous graph) we can simply use the default label config.
// Reference: https://github.com/neo4j-contrib/neovis.js/blob/cef0aa16d647ffe0fd9ca457bcffa6e0cb7c55c8/src/neovis.ts#L524
defaultLabelConfig: {
[NeoVis.NEOVIS_ADVANCED_CONFIG]: {
function: {
// Print all properties for the title (when nodes are clicked)
title: NeoVis.objectToTitleHtml,
// Use "fileName" as label. Remove leading slash, trailing ".jar", version number and a trailing word like "Final".
label: (node) =>
node.properties.fileName
.replace("/", "")
.replace(".jar", "")
.replace(/[\d\.\-\_v]+\w+$/gm, "") +
"(" +
node.properties.maxDistanceFromSource +
")",
},
},
},
relationships: {
DEPENDS_ON: {
label: false,
value: "weight",
[NeoVis.NEOVIS_ADVANCED_CONFIG]: {
function: {
title: NeoVis.objectToTitleHtml,
},
},
},
},
initialCypher:
"MATCH (artifact:Artifact)-[dependency:DEPENDS_ON*0..1]->(dependent:Artifact) WHERE artifact.topologicalSortIndex >= 0 AND dependent.topologicalSortIndex >= 0 AND artifact <> dependent RETURN artifact,dependency,dependent ORDER BY dependent.topologicalSortIndex, artifact.topologicalSortIndex SKIP toInteger($startIndex) LIMIT toInteger($blockSize)",
};
}

function draw() {
const config = getConfiguration(getNeo4jCredentials(), hierarchicalHexagons());
paginatedGraphVisualization({ containerElementId: "visualizations", neoVizConfiguration: config });
}
Loading