Skip to content
Open
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
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -53,3 +53,5 @@ install-state.gz
# Built binaries
/bin
pages/plugin.yaml
backend/static/index.html
backend/static/plugin.yaml
58 changes: 16 additions & 42 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -44,63 +44,37 @@ Available image tags are listed in the [container registry](https://github.com/f

- [Node.js](https://nodejs.org/en/) (v18+)
- [Yarn](https://yarnpkg.com) (v4)
- [Go](https://go.dev/dl/) (v1.24+)
- [Helm](https://helm.sh/docs/intro/install/)
- [oc](https://console.redhat.com/openshift/downloads) CLI
- [Docker](https://www.docker.com) or [podman 3.2.0+](https://podman.io)
- An [OpenShift cluster](https://console.redhat.com/openshift/create)
- Github [*Personal Access Token*](https://github.com/settings/personal-access-tokens) with *administration*, *content* and *workflow* write permissions in all repositories
- [inotify-tools](https://github.com/inotify-tools/inotify-tools) (optional, enables Go backend auto-recompile on file changes)

### Option 1: Local
### Setup

In one terminal window, run:
1. `oc login` to your OpenShift cluster
2. `yarn install`
3. `./init.sh`

1. `yarn install`
2. `yarn run start`
This builds the pages assets (plugin.yaml, landing page), compiles the Go backend, starts the webpack dev server, and launches the OpenShift console in a container. Navigate to <http://localhost:9000> to see the running plugin.

In another terminal window, run:
To stop the dev environment:

1. `oc login` (requires [oc](https://console.redhat.com/openshift/downloads) and an [OpenShift cluster](https://console.redhat.com/openshift/create))
2. `yarn run start-console` (requires [Docker](https://www.docker.com) or [podman 3.2.0+](https://podman.io))

This will run the OpenShift console in a container connected to the cluster
you've logged into. The plugin HTTP server runs on port 9001 with CORS enabled.
Navigate to <http://localhost:9000/example> to see the running plugin.

#### Running start-console with Apple silicon and podman

If you are using podman on a Mac with Apple silicon, `yarn run start-console`
might fail since it runs an amd64 image. You can workaround the problem with
[qemu-user-static](https://github.com/multiarch/qemu-user-static) by running
these commands:

```bash
podman machine ssh
sudo -i
rpm-ostree install qemu-user-static
systemctl reboot
```shell
./init.sh --stop
```

### Option 2: Docker + VSCode Remote Container
To use random ports (useful when defaults are already in use):

Make sure the
[Remote Containers](https://marketplace.visualstudio.com/items?itemName=ms-vscode-remote.remote-containers)
extension is installed. This method uses Docker Compose where one container is
the OpenShift console and the second container is the plugin. It requires that
you have access to an existing OpenShift cluster. After the initial build, the
cached containers will help you start developing in seconds.

1. Create a `dev.env` file inside the `.devcontainer` folder with the correct values for your cluster:

```bash
OC_PLUGIN_NAME=console-functions-plugin
OC_URL=https://api.example.com:6443
OC_USER=kubeadmin
OC_PASS=<password>
```shell
./init.sh --randomize-ports
```

2. `(Ctrl+Shift+P) => Remote Containers: Open Folder in Container...`
3. `yarn run start`
4. Navigate to <http://localhost:9000/example>
### Viewing GitHub Pages locally

The landing page served at [functions-dev.github.io/ocp-console-plugin](https://functions-dev.github.io/ocp-console-plugin/) is built from `pages/index.html` and the Helm chart. The `init.sh` script generates these assets into `backend/static/` automatically, so the running backend serves them at <http://localhost:8080>.

## Docker image

Expand Down
16 changes: 9 additions & 7 deletions docs/claude-progress.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,16 @@
# Newest entries first. Agents: append your entry at the top after the header.

---
## 2026-06-12 | Session: Fix clipboard copy error handling
Worked on: Add error state for copy-to-clipboard buttons on landing page
## 2026-06-16 | Session: PR #36 - GitHub Pages local dev + clipboard fix (SRVOCF-843)
Worked on: Local GitHub Pages dev support, clipboard copy error handling, PR review feedback
Completed:
- Added error handling for navigator.clipboard API unavailability (e.g. non-HTTPS contexts)
- Added .catch() handler for clipboard.writeText promise rejection
- Added error state styling (.copy-error class) with red color, X icon, and "Copy failed" hover label
- Applied error handling to both install command and YAML copy buttons
Left off: Branch pr/fix-catch ready for review.
- Added error handling for clipboard copy buttons: .catch() on writeText, error state styling (.copy-error class with red color, X icon, "Copy failed" label)
- GitHub Pages local dev: build_pages in init.sh, README simplification, CRC host mapping, .gitignore updates
- Extracted PLUGIN_NAME local variable in build_pages() to replace hardcoded strings
- Moved helm prerequisite check from check_prerequisites() into build_pages() (only needed there)
- Added features.json entry for SRVOCF-843, set "passes": true
- All 14 suites, 126 tests passing, webpack builds clean
Left off: Changes ready to commit and push for merge.
Blockers: None

---
Expand Down
11 changes: 11 additions & 0 deletions docs/features.json
Original file line number Diff line number Diff line change
Expand Up @@ -191,5 +191,16 @@
"Both copy buttons (install command and YAML) have error handling"
],
"passes": true
},
{
"category": "technical",
"description": "GitHub Pages local development: script to generate plugin.yaml and serve the pages site locally",
"steps": [
"Add a script (e.g. hack/pages-dev.sh) that runs helm template to generate plugin.yaml into pages/",
"Script starts a local HTTP server (e.g. python -m http.server) to serve pages/ so fetch('plugin.yaml') works",
"Add pages/plugin.yaml to .gitignore so the generated file is not committed",
"Document usage in README or script header"
],
"passes": true
}
]
17 changes: 17 additions & 0 deletions init.sh
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,23 @@ write_dev_env() {
EOF
}

build_pages() {
if ! command -v helm &>/dev/null; then
echo "Error: helm not found. Install from https://helm.sh/docs/intro/install/"
exit 1
fi

local plugin_name="console-functions-plugin"
echo "Building pages assets..."
helm template "$plugin_name" charts/openshift-console-plugin \
-n "$plugin_name" \
--set "plugin.image=ghcr.io/functions-dev/${plugin_name}:latest" \
> backend/static/plugin.yaml
cp pages/index.html backend/static/index.html
}

start_backend() {
build_pages
echo "Building Go backend..."
(cd backend && go build -buildvcs=false -o ../bin/backend .)
(cd backend && go build -buildvcs=false -o ../bin/errserver ./cmd/errserver)
Expand Down Expand Up @@ -176,6 +192,7 @@ check_prerequisites() {
echo "Error: not logged in to OpenShift. Run 'oc login' first."
exit 1
fi

}

install_dependencies() {
Expand Down
3 changes: 3 additions & 0 deletions start-console.sh
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,9 @@ else
PLUGIN_HOST="host.docker.internal"
fi
CONTAINER_NETWORK_OPTS="-p ${CONSOLE_PORT}:9000"
if [[ "$(uname -s)" == "Darwin" ]]; then
CONTAINER_NETWORK_OPTS="${CONTAINER_NETWORK_OPTS} --add-host api.crc.testing:host-gateway"
fi

BRIDGE_PLUGINS="${PLUGIN_NAME}=http://${PLUGIN_HOST}:${PLUGIN_PORT}"
BRIDGE_PLUGIN_PROXY='{"services":[{"consoleAPIPath":"/api/proxy/plugin/'"${PLUGIN_NAME}"'/backend/","endpoint":"http://'"${PLUGIN_HOST}"':'"${BACKEND_PORT}"'","authorize":false}]}'
Expand Down
Loading