Skip to content

Commit

Permalink
docs: Add documentation for extending the map
Browse files Browse the repository at this point in the history
Signed-off-by: Oleksandr Dubenko <[email protected]>
  • Loading branch information
sniok committed Nov 27, 2024
1 parent 99d3fa4 commit 6d43fe4
Show file tree
Hide file tree
Showing 7 changed files with 151 additions and 10 deletions.
141 changes: 141 additions & 0 deletions docs/development/plugins/functionality/extending-the-map.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,141 @@
---
title: Extending the Map
sidebar_label: Extending the Map
---

Map view displays cluster resource on a graph. Plugins can extend this graph by adding nodes and edges.

## Nodes, edges and sources

**Node** represents a Kubernetes resource. **Edges** connect different **nodes**, for example ReplicaSet connects to Pods it owns.

<figure>

![Screenshot of a Map with one ReplicaSet node connected to three Pods it owns](./images/map-rs-and-pods.png)

<figcaption>1 ReplicaSet and 3 Pods it owns</figcaption>
</figure>

To add your own nodes and edges you need to define a **Source**

A graph **Source** represents a collection of Nodes and Edges along with name and icon. Source may contain other Sources.

<figure style="text-align: center">

![Screenshot of a Source picker containing various Kubernetes resource sources](./images/source-picker-workloads.png)

<figcaption>Example: "Pods" is a source that contains Nodes for all the Pods in the cluster, "Workloads" is also a source containing other Sources.</figcaption>
</figure>

## Creating and registering a Source

To define a Source create an object with the following structure:

```tsx
const mySource = {
id: "my-source", // ID of the source should be unique
label: "My Source", // label will be displayed in source picker
// you can provide an icon
icon: (
<img
src="https://headlamp.dev/img/favicon.png"
alt="My Source logo"
style={{ width: "100%", height: "100%" }}
/>
),
/**
* useData is a hook that will be called to load nodes and edges for your source
* You can use hooks here that Headlamp provides to load Kubernetes resources
* this hook should return an object with nodes and edges or `null` if it's loading
* it's important that return object is not recreated every time, so useMemo is required
*/
useData() {
return useMemo(() => {
// This would come from kubernetes API but it's hardcoded here as an example
const myResource = {
kind: "MyResourceKind",
metadata: {
uid: "1234",
name: "my-test-resource",
namespace: "test-namespace",
creationTimestamp: "1234",
},
};

const edges = []; // no edges in this source
const nodes = [
{
id: "1234", // ID should be unique
type: "kubeObject", // 'kubeObject' type represnets a kubernetes resource
data: {
// resource field is required and should contain KubeObject
resource: new KubeObject(myResource),
},
},
];

return { edges, nodes };
}, []);
},
};
```

Then to register it call `registerMapSource`

```tsx
registerMapSource(mySource);
```

You'll now see it in the Source picker and the Node on the Map:

<figure style="text-align: center">

![Screenshot of a source picker](./images/source-picker.png)

<figcaption>"My Source" is listed on the bottom. Enabled by default.</figcaption>
</figure>

<figure style="text-align: center">

![Screenshot of a node with a default icon](./images/node-without-an-icon.png)

<figcaption>MyCustomResource Node displayed with default Icon</figcaption>
</figure>

## Node Icons

To add an icon to the Node you need to call `registerKindIcon`.

Note: This is different from the Source icon. One Source may contain multiple different kinds of objects.

```tsx
registerKindIcon("MyCustomResource", {
// icon is a JSX element
icon: <img src="https://headlamp.dev/img/favicon.png" />,
});
```

<figure style="text-align: center">

![Screenshot of a node with a custom icon](./images/node-with-an-icon.png)

<figcaption>Node with a custom Icon</figcaption>
</figure>

## Details panel

When selecting a Node Map will display a details panel for the selected object.
To add a details Panel for your Nodes call function `registerKindDetailsPage`

```tsx
// You need to provide 'kind' of the resource and a React Component that will render details
// The props will contain name and a namespace of the Kubernetes Resource
// Details page usually loads the resource by name and namespace
registerKindDetailsPage("MyCustomResource", {
component: (props) => (
<div style={{ padding: "60px" }}>
Details {props.name} {props.namespace}
</div>
),
});
```
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ what we have so far:
Show a component in the app bar (in the top right) with
[registerAppBarAction](../api/plugin/registry/functions/registerappbaraction).

![screenshot of the header showing two actions](./images/podcounter_screenshot.png)
![screenshot of the header showing two actions](../images/podcounter_screenshot.png)

- Example plugin shows [How To Register an App Bar Action](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/pod-counter)
- API reference for [registerAppBarAction](../api/plugin/registry/functions/registerappbaraction)
Expand All @@ -69,7 +69,7 @@ Show a component in the app bar (in the top right) with
Change the logo (at the top left) with
[registerAppLogo](../api/plugin/registry/functions/registerapplogo).

![screenshot of the logo being changed](./images/change-logo.png)
![screenshot of the logo being changed](../images/change-logo.png)

- Example plugin shows [How To Change The Logo](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/change-logo)
- API reference for [registerAppLogo](../api/plugin/registry/functions/registerapplogo)
Expand All @@ -79,7 +79,7 @@ Change the logo (at the top left) with
Add menus when Headlamp is running as an app.
[Headlamp.setAppMenu](../api/plugin/lib/classes/Headlamp#setappmenu)

![screenshot of the logo being changed](./images/app-menus.png)
![screenshot of the logo being changed](../images/app-menus.png)

- Example plugin shows [How To Add App Menus](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/app-menus)
- API reference for [Headlamp.setAppMenu](../api/plugin/lib/classes/Headlamp#setappmenu)
Expand All @@ -89,7 +89,7 @@ Add menus when Headlamp is running as an app.
Change the Cluster Chooser button (in the middle top of the Headlamp app bar) with
[registerClusterChooser](../api/plugin/registry/functions/registerclusterchooser).

![screenshot of the cluster chooser button](./images/cluster-chooser.png)
![screenshot of the cluster chooser button](../images/cluster-chooser.png)

- Example plugin shows [How To Register Cluster Chooser button](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/clusterchooser)
- API reference for [registerClusterChooser](../api/plugin/registry/functions/registerclusterchooser)
Expand All @@ -100,7 +100,7 @@ Show a component to the top right area of a detail view
(in the area of the screenshot below that's highlighted as yellow)
[registerDetailsViewHeaderAction](../api/plugin/registry/functions/registerdetailsviewheaderaction).

![screenshot of the header showing two actions](./images/header_actions_screenshot.png)
![screenshot of the header showing two actions](../images/header_actions_screenshot.png)

- Example plugin shows [How To set a Details View Header Action](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/details-view)
- API reference for [registerDetailsViewHeaderAction](../api/plugin/registry/functions/registerdetailsviewheaderaction)
Expand All @@ -112,7 +112,7 @@ Change sections in cluster resources' details views with [registerDetailsViewSec
Or simply append a component at the bottom of different details views with
[registerDetailsViewSection](../api/plugin/registry/functions/registerdetailsviewsection).

![screenshot of the appended Details View Section](./images/details-view.jpeg)
![screenshot of the appended Details View Section](../images/details-view.jpeg)

- Example plugin shows [How To set a Details View Section](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/details-view)
- API reference for [registerDetailsViewSection](../api/plugin/registry/functions/registerdetailsviewsection)
Expand Down Expand Up @@ -140,7 +140,7 @@ Add sidebar items (menu on the left) with
[registerSidebarEntry](../api/plugin/registry/functions/registersidebarentry).
Remove sidebar items with [registerSidebarEntryFilter](../api/plugin/registry/functions/registersidebarentryfilter).

![screenshot of the sidebar being changed](./images/sidebar.png)
![screenshot of the sidebar being changed](../images/sidebar.png)

- Example plugin shows [How To add items to the sidebar](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/sidebar), and also how to remove sidebar items.
- API reference for [registerSidebarEntry](../api/plugin/registry/functions/registersidebarentry)
Expand All @@ -150,7 +150,7 @@ Remove sidebar items with [registerSidebarEntryFilter](../api/plugin/registry/fu

Change what tables across Headlamp show with [registerResourceTableColumnsProcessor](../api/plugin/registry/functions/registersidebarentry). This allows you to remove, add, update, or shuffle table columns.

![screenshot of the pods list with a context menu added by a plugin](./images/table-context-menu.png)
![screenshot of the pods list with a context menu added by a plugin](../images/table-context-menu.png)

- Example plugin shows [How to add a context menu to each row in the pods list table](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/tables).
- API reference for [registerResourceTableColumnsProcessor](../api/plugin/registry/functions/registerresourcetablecolumnsprocessor)
Expand All @@ -161,7 +161,7 @@ Headlamp has the concept of "Headlamp events". Those are fired when something re

React to Headlamp events with [registerHeadlampEventCallback](../api/plugin/registry/functions/registerheadlampeventcallback).

![screenshot of a snackbar notification when an event occurred](./images/event-snackbar.png)
![screenshot of a snackbar notification when an event occurred](../images/event-snackbar.png)

- Example plugin shows [How to show snackbars for Headlamp events](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/headlamp-events).
- API reference for [registerHeadlampEventCallback](../api/plugin/registry/functions/registerheadlampeventcallback)
Expand All @@ -172,4 +172,4 @@ The plugins can have user-configurable settings that can be used to change the b

- Example plugin shows [How to create plugin settings and use them](https://github.com/headlamp-k8s/headlamp/tree/main/plugins/examples/change-logo)

![screenshot of the plugin settings](./images/plugin-settings.png)
![screenshot of the plugin settings](../images/plugin-settings.png)

0 comments on commit 6d43fe4

Please sign in to comment.