Comments (7)
other possibilities are to render to .svg, and basically wrap/ call graphviz cli
love your work on moon 💖
from moon.
RFC: moon graph
I took some time to research how we can tackle this and I am writing it down here.
Some notes
- When I say dep graph, I mean the graph of dependencies installed via package manager (npm, pnpm, yarn etc).
astro
,next
etc will be part of the dep graph. - When I say project graph, I mean the relationships between different repositories that are present in the workspace. The browser package, vue-vite-app etc will be part of the project graph*.
*In the context of the example repo.
Graphing libraries
Some popular graphing libraries that can be used to render the graph on the frontend.
- Cytoscope: Used by NX
- Sigma.js: Promising because it can render a lot of nodes which might be needed by the dep graph
- React Flow: Looks good
- Webcola: The Edgedb UI is built with this and it looks pretty good
other possibilities are to render to .svg, and basically wrap/ call graphviz cli
I am against this because it would be difficult to make the graph interactive, or allow us to extend behavior or add custom styling/interactions.
Problems with using rust
There is also the possibility of using a rust only solution by leveraging solutions such as yew charts. However, they are very immature and will likely result in a lot of developer pain since we might have to implement a graphing library in rust from scratch.
Serving the graph
There could be many possible solutions:
-
A separate SPA that will be bundled with the Moon CLI.
When we run
moon graph
, we start up an axum/rocket/warp server that will serve these bundled files. The server will have rest endpoints/graphql resolvers from where data can be fetched and displayed (usingon mount
if we choose svelte for the SPA). A--watch
option (like the one NX has) can be easily added by making the frontend establish a websocket connection with the backend and subscribe to changes. The backend can set up a file watcher to detect changes to the dependency graph on the fly. This will come at the cost of not being SEO friendly (but is that really a problem in this context?) -
A yew app that will be bundled with the Moon CLI.
This will have the same problems as described above.
-
A separate process is started.
We can have the
moon graph
command start a next-js/remix/nuxt-js server that can handle all the calculation/rendering of the graph. This will have some problems:- We will have to interop between rust and js code, or have to rewrite parts of graph calculation in js.
- Spawning a long running process (such as a server) within rust is non-trivial
Conclusion
I have left the minute details out of this RFC because we can refine/iterate on them later. That being said, I would love to get some feedback on the above.
from moon.
@IgnisDa Great writeup. There's another piece to this that is not mentioned, and that's the VS Code extension (and future editor extensions). The graph visualizer will also be present in the extension as its own view, so this means we need to be able to share the code between the CLI and the extension.
The biggest question like you said, is how to serve it. The graph will be built in JS of course, but once we support non-JS languages, we can't assume everyone will be using Node.js, so possibly serving with Rust is the best course?
from moon.
@milesj I am not sure how vscode extension packaging works, but lets say we write the graph visualizer in svelte (I have heard it has great integration with vscode extensions). We could simply build the SPA with svelte and then bundle it within the CLI. And we can also import svelte components into the vscode project and use them to render in a webview environment.
so possibly serving with Rust is the best course?
Agreed.
from moon.
Ok my thoughts.
The visualizer would need to work from both the CLI and from the VS Code extension. Code must be shared between the two.
Writing the JS
While svelte is great, I feel like this can simply be built in vanilla JS. Most of the interactivity will be in the graph itself, which will be abstracted away from us based on the lib we choose. Anything else would be simple DOM updates.
Serving the HTML/JS
For the extension, it relies on web views (https://code.visualstudio.com/api/extension-guides/webview) where raw HTML is simply rendered. The visualizer JS will most likely be included via a script
tag (not bundled or anything), something like:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Graph visualizer</title>
<script src="https://unpkg.com/@moonrepo/graph-visualizer@latest"></script>
</head>
<body>
<script>window.GRAPH_DATA = {}</script>
<div id="graph" />
</body>
</html>
For the script src
, we can use a CDN system like https://unpkg.com that points directly to the visualizer JS code. This allows us to:
- Not bundle the JS code in
@monorepo/cli
or the VS Code extension. - We can continually publish updates to the visualizer without having to also update downstream consumers. Just use
@latest
for the version. - Can be built in isolation.
For the Rust code, we can probably use the same exact approach. moon project-graph
would spin up a local HTTP server and serve the same HTML above. That's it. Doesn't need to get more complicated than that.
Visualizer requirements
All of those graphing libs you listed above are great, but I want to also include more information and functionality besides the graphs. For example:
Project graph
- When clicking on a project (node in the graph), it will also display all relevant information from the project's
moon.yml
. Primarilytasks
andproject
metadata. - Graph would need advanced filtering, like, "only show applications", "only show javascript projects", so on and so forth.
- Being able to only focus a project and see its dependencies and dependents.
- Maybe some kind of grouping like: https://ialab.it.monash.edu/webcola/examples/smallgroups.html
Dependency graph
- When clicking on a target (a node), it displays information on the task and owning project.
- Filters also?
from moon.
The CDN route sounds really good! But for functionalities like filtering, serching and grouping, i think it would be best to use some kind of UI framework. That would also ensure that we are able to add more advanced features later down the line without any major overhaul.
from moon.
Closing this since the initial work is done. Thanks a lot for it!
from moon.
Related Issues (20)
- [bug] Rust not listed as supported tool in the docs HOT 2
- [bug] `MOON_LOG=off moon bin pnpm` outputs tool instalation logs HOT 2
- Bun toolchain does not support inferTasksFromScripts HOT 3
- [bug] docs would be better with more in context `@group(…)` examples
- [bug] moon crashes when there's a environment variable entry HOT 3
- [bug] docs: TypeScript not listed as a tool HOT 1
- SIGINT (CTRL + C) immediately yields controls of the shell without waiting for the task to complete HOT 6
- [bug] tsconfig.json is not parsed as JSON5(?) HOT 3
- [feature] affectedFiles should pass in all input files when there are no affected files instead of `.` HOT 4
- [bug] `moon run ___` inside a project directory panicks HOT 3
- [bug] commit-msg hook fails on Windows 11 HOT 2
- [bug] Moon docker prune command using bun install also the dev dependencies HOT 4
- [bug] segfault following unknown project id HOT 2
- [feature] Allow applications dependent on other applications HOT 10
- All files from `inputs` are passed to a task's command HOT 1
- [bug] proto-plugin.toml {libc} placeholder fails to work. HOT 10
- [feature] Support .yaml extension for configuration files HOT 14
- [feature] ability to inherit or merge fileGroup(s) HOT 1
- [feature] Support Defining Common Tasks for different stack types HOT 2
- [bug] vscode extension: element with id is already registered in the tags panel HOT 1
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from moon.