Setup
Step 1: Install Rafay frontend plugin¶
Install the Rafay Backstage frontend plugin package using the command below:
yarn --cwd packages/app add @rafaysystems/backstage-plugin-rafay
Step 2: Configure Rafay Org Account in Backstage¶
Using Backstage with the Rafay Org requires authentication using the Rafay Org API token. Update the Backstage app-config.yaml
file with the Rafay Org URL and your API key.
- In the Backstage environment, edit the
app-config.yaml
file. Example path:/my-backstage-app/app-config.yaml
. - Implement the changes outlined below:
app:
- title: Scaffolded Backstage App
+ title: Rafay Backstage Demo App
baseUrl: http://localhost:3000
organization:
@@ -50,6 +50,10 @@ proxy:
# '/test':
# target: 'https://example.com'
# changeOrigin: true
+ '/rs-plugin':
+ target: ${RAFAY_CONSOLE_URL}
+ headers:
+ X-RAFAY-API-KEYID: ${RAFAY_API_KEY}
Note
Following HTTP methods needs to be allowed: GET, POST, PUT, DELETE
- Enable Rafay page and verify if the credentials are active by navigating to http://localhost:3000/rafay. Project list should be visible
Edit the App.tsx
file at packages/app/src/
.
@@ -33,6 +33,7 @@ import { AppRouter, FlatRoutes } from '@backstage/core-app-api';
import { CatalogGraphPage } from '@backstage/plugin-catalog-graph';
import { RequirePermission } from '@backstage/plugin-permission-react';
import { catalogEntityCreatePermission } from '@backstage/plugin-catalog-
common/alpha';
+import { RafayPage } from '@rafaysystems/backstage-plugin-rafay';
const app = createApp({
apis,
@@ -93,6 +94,7 @@ const routes = (
</Route>
<Route path="/settings" element={<UserSettingsPage />} />
<Route path="/catalog-graph" element={<CatalogGraphPage />} />
+ <Route path="/rafay" element={<RafayPage />} />
</FlatRoutes>
);
Step 3: GitHub integration¶
Configure GitHub integration using the instructions outlined here.
Step 4: Install Rafay backend plugin¶
Install the Rafay Backstage backend plugin package using the command below:
yarn --cwd packages/backend add @rafaysystems/backstage-plugin-rafay-backend
Create a rafay.ts
file in the packages/backend/src/plugins
folder. Include the following content in the rafay.ts
file.
+import { createRouter } from '@rafaysystems/backstage-plugin-rafay-backend'; +import { Router } from 'express';
+import { PluginEnvironment } from '../types';
+
+export default async function createPlugin(
+ env: PluginEnvironment,
+): Promise<Router> {
+ return await createRouter({
+ logger: env.logger,
+ });
+}
Step 5: Register Rafay backend plugin¶
Edit the index.ts
file to register the backend plugin. The index.ts
file is located at packages/backend/src/
.
@@ -31,6 +31,7 @@ import search from './plugins/search';
import { PluginEnvironment } from './types';
import { ServerPermissionClient } from '@backstage/plugin-permission-node';
import { DefaultIdentityClient } from '@backstage/plugin-auth-node';
+import rafay from './plugins/rafay';
function makeCreateEnv(config: Config) {
const root = getRootLogger();
@@ -85,6 +86,7 @@ async function main() {
const techdocsEnv = useHotMemoize(module, () => createEnv('techdocs'));
const searchEnv = useHotMemoize(module, () => createEnv('search'));
const appEnv = useHotMemoize(module, () => createEnv('app'));
+ const rafayEnv = useHotMemoize(module, () => createEnv('rafay'));
const apiRouter = Router();
apiRouter.use('/catalog', await catalog(catalogEnv));
@@ -93,6 +95,7 @@ async function main() {
apiRouter.use('/techdocs', await techdocs(techdocsEnv));
apiRouter.use('/proxy', await proxy(proxyEnv));
apiRouter.use('/search', await search(searchEnv));
+ apiRouter.use('/rafay-backend', await rafay(rafayEnv));
Verify backend is registered by navigating to http://localhost:7007/api/rafay-backend/health. Response should be {"status":"ok"}.
Step 6: Add/Register templates¶
Some example templates have been provided for creating resources (environments/clusters/namespaces). These templates can be imported by adding a location to the catalog configuration in the app-config.yaml
file. Follow the instructions outlined below:
(a) Add templates
yarn --cwd ppackages/backend add @backstage/integration
(b) Add the template location to the app-config.yaml
file
@@ -96,6 +96,12 @@ catalog:
rules:
- allow: [User, Group]
+ # Rafay example templates
+ - type: file
+ target: ../../rafay-examples/templates/all.yaml
+ rules:
+ - allow: [Template]
+
## Uncomment these lines to add more example data
# - type: url
# target: https://github.com/backstage/backstage/blob/master/packages/catalog-model/examples/all.yaml
© Register the Rafay template actions in scaffolder.ts
@@ -3,6 +3,17 @@ import { createRouter } from '@backstage/plugin-scaffolder-backend';
import { Router } from 'express';
import type { PluginEnvironment } from '../types';
+import { ScmIntegrations } from '@backstage/integration';
+import { createBuiltinActions } from '@backstage/plugin-scaffolder-backend';
+import {
+ createNewEKSClusterAction,
+ createNewAKSClusterAction,
+ createNewGKEClusterAction,
+ createNewClusterFromTemplateAction,
+ createNewNamespaceAction,
+ createNewWorkloadAction,
+} from '@rafaysystems/backstage-plugin-rafay-backend';
+
export default async function createPlugin(
env: PluginEnvironment,
): Promise<Router> {
@@ -10,6 +21,28 @@ export default async function createPlugin(
discoveryApi: env.discovery,
});
+ const integrations = ScmIntegrations.fromConfig(env.config);
+
+ const builtInActions = createBuiltinActions({
+ integrations,
+ catalogClient,
+ reader: env.reader,
+ config: env.config,
+ });
+
+ const backendUrl = env.config.getString('backend.baseUrl');
+ const baseUrl = `${backendUrl}/api/proxy/rs-plugin`;
+
+ const actions = [
+ ...builtInActions,
+ createNewEKSClusterAction({ baseUrl }),
+ createNewAKSClusterAction({ baseUrl }),
+ createNewGKEClusterAction({ baseUrl }),
+ createNewClusterFromTemplateAction({ baseUrl }),
+ createNewNamespaceAction({ baseUrl }),
+ createNewWorkloadAction({ baseUrl }),
+ ];
+
return await createRouter({
logger: env.logger,
config: env.config,
@@ -18,5 +51,6 @@ export default async function createPlugin(
catalogClient,
identity: env.identity,
permissions: env.permissions,
+ actions,
}); }
Step 7: Add Entity cards¶
Edit the EntityPage.tsx
file to add the Rafay Org entity cards to the entity page layout. The EntityPage.tsx
file is located at packages/app/scr/components/catalog
.
@@ -58,6 +58,19 @@ import {
import { TechDocsAddons } from '@backstage/plugin-techdocs-react';
import { ReportIssue } from '@backstage/plugin-techdocs-module-addons-contrib';
+import {
+ EntityClusterInfo,
+ EntityClusterNamespaceList,
+ EntityClusterPodList,
+ EntityNamespaceInfo,
+ EntityNamespacePodList,
+ EntityWorkloadInfo,
+ EntityWorkloadPodList,
+ isRafayPluginEntityTypeWorkload,
+ isRafayPluginEntityTypeNamespace,
+ isRafayPluginEntityTypeCluster,
+} from '@rafaysystems/backstage-plugin-rafay';
+
const techdocsContent = (
<EntityTechdocsContent>
<TechDocsAddons>
@@ -121,13 +134,61 @@ const entityWarningContent = (
</> );
const overviewContent = (
<Grid container spacing={3} alignItems="stretch">
{entityWarningContent}
<Grid item md={6}>
<EntityAboutCard variant="gridItem" />
</Grid>
- <Grid item md={6} xs={12}>
+ <EntitySwitch>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
<EntitySwitch.Case if={isRafayPluginEntityTypeNamespace}>
<Grid item md={6} xs={12}>
<EntityNamespaceInfo />
</Grid>
<Grid item md={6} xs={12}>
<EntityNamespacePodList />
</Grid>
</EntitySwitch.Case>
<EntitySwitch.Case if={isRafayPluginEntityTypeWorkload}>
<Grid item md={6} xs={12}>
<EntityWorkloadInfo />
</Grid>
<Grid item md={6} xs={12}>
<EntityWorkloadPodList />
</Grid>
+ </EntitySwitch.Case>
+ <EntitySwitch.Case if={isRafayPluginEntityTypeCluster}>
+ <Grid item md={6} xs={12}>
+ <EntityClusterInfo />
+ </Grid>
+ <Grid item md={6} xs={12}>
+ <EntityClusterNamespaceList />
+ </Grid>
+ <Grid item md={6} xs={12}>
+ <EntityClusterPodList />
+ </Grid>
+ </EntitySwitch.Case>
+ </EntitySwitch>
+ {/* <Grid item md={6} xs={12}>
<EntityCatalogGraphCard variant="gridItem" height={400} />
</Grid>
@@ -136,7 +197,7 @@ const overviewContent = (
</Grid>
<Grid item md={8} xs={12}>
<EntityHasSubcomponentsCard variant="gridItem" />
- </Grid>
+ </Grid> */}
</Grid> );