From d7ef52820687787471b89a1cae418a2f4f4a470b Mon Sep 17 00:00:00 2001 From: Chuck Smith Date: Tue, 26 May 2026 19:42:43 -0400 Subject: [PATCH 1/2] feat: SolidStackWeb.mount_path helper MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Returns the path at which the engine is mounted in the host app, derived automatically from Rails routes — no configuration required. Host apps can use `link_to "Dashboard", SolidStackWeb.mount_path` instead of hardcoding the mount path. Documented in the install generator template. Closes #45. Co-Authored-By: Claude Sonnet 4.6 --- CHANGELOG.md | 1 + ROADMAP.md | 1 - .../install/templates/initializer.rb | 7 +++++++ lib/solid_stack_web.rb | 13 +++++++++++++ spec/solid_stack_web_spec.rb | 10 ++++++++++ 5 files changed, 31 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 2a3ffa0..1dc1b4b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Added - Install generator — `rails generate solid_stack_web:install` creates `config/initializers/solid_stack_web.rb` with every config option documented inline and injects the mount line into `config/routes.rb` +- `SolidStackWeb.mount_path` — returns the path at which the engine is mounted in the host app, derived automatically from routes; use `link_to "Dashboard", SolidStackWeb.mount_path` to link to the dashboard without hardcoding the path ## [0.8.0] - 2026-05-26 diff --git a/ROADMAP.md b/ROADMAP.md index ac48350..375ad20 100644 --- a/ROADMAP.md +++ b/ROADMAP.md @@ -11,7 +11,6 @@ The path to v1.0.0 is staged: first achieve feature parity with `solid_queue_das > _Make it easy to adopt and easy to contribute to._ ### Remaining -- **Configurable mount path helper** — engine-aware path helpers that respect whatever `at:` the host app chose - **Accessibility pass** — keyboard navigation, ARIA labels on interactive elements, sufficient colour contrast in both themes - **Query optimisation** — eliminate N+1 queries across all list views; add covering indexes to the dummy app schema - **Error pages** — engine-scoped 404/500 views so errors stay within the dashboard chrome diff --git a/lib/generators/solid_stack_web/install/templates/initializer.rb b/lib/generators/solid_stack_web/install/templates/initializer.rb index 1618001..6554ed0 100644 --- a/lib/generators/solid_stack_web/install/templates/initializer.rb +++ b/lib/generators/solid_stack_web/install/templates/initializer.rb @@ -31,6 +31,13 @@ # Disable for stores that contain sensitive data. # config.allow_value_preview = false + # Link to the dashboard from anywhere in your app without hardcoding the path: + # + # link_to "Queue Dashboard", SolidStackWeb.mount_path + # + # SolidStackWeb.mount_path is derived automatically from your routes — no + # configuration needed. + # Alert webhook — POST to this URL when a threshold is breached. # Delivery failures are silently swallowed; configure a cooldown to avoid storms. # diff --git a/lib/solid_stack_web.rb b/lib/solid_stack_web.rb index e8980d6..562e529 100644 --- a/lib/solid_stack_web.rb +++ b/lib/solid_stack_web.rb @@ -53,6 +53,19 @@ def allow_value_preview @allow_value_preview || false end + # Returns the path at which the engine is mounted in the host application, + # derived automatically from the host's routes. Host apps can use this to + # build links to the dashboard without hardcoding the mount path. + # + # link_to "Dashboard", SolidStackWeb.mount_path + # + def mount_path + route = Rails.application.routes.routes.find do |r| + r.app.respond_to?(:app) && r.app.app == SolidStackWeb::Engine + end + route&.path&.spec&.to_s&.sub(%r{\(.*\)\z}, "") || "/" + end + def configure yield self end diff --git a/spec/solid_stack_web_spec.rb b/spec/solid_stack_web_spec.rb index b8ccfa1..4d07615 100644 --- a/spec/solid_stack_web_spec.rb +++ b/spec/solid_stack_web_spec.rb @@ -13,6 +13,16 @@ end end + describe ".mount_path" do + it "returns the path at which the engine is mounted in the dummy app" do + expect(SolidStackWeb.mount_path).to eq("/solid_stack") + end + + it "returns a string with no trailing format suffix" do + expect(SolidStackWeb.mount_path).not_to include("(") + end + end + describe ".search_results_limit" do it "defaults to 25" do expect(SolidStackWeb.search_results_limit).to eq(25) From ce68197c09754d796d18186efca126c686a14543 Mon Sep 17 00:00:00 2001 From: Chuck Smith Date: Tue, 26 May 2026 19:43:35 -0400 Subject: [PATCH 2/2] docs: document mount_path helper and install generator in README Co-Authored-By: Claude Sonnet 4.6 --- README.md | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/README.md b/README.md index 8be7c21..cd18213 100644 --- a/README.md +++ b/README.md @@ -177,6 +177,24 @@ end The `authenticate` block is evaluated in the context of each request's controller instance, so any helper method available to controllers (e.g. `current_user` from Devise) works directly. If the block returns `false` or `nil`, the engine falls back to HTTP Basic authentication. If no `authenticate` block is configured, the dashboard is open. +### Linking to the dashboard + +`SolidStackWeb.mount_path` returns the path at which the engine is mounted, derived automatically from your routes. Use it to link to the dashboard from your application layout without hardcoding the path: + +```ruby +link_to "Queue Dashboard", SolidStackWeb.mount_path +``` + +### Install generator + +Run the install generator to create a documented initializer and wire up the mount point in one step: + +```bash +rails generate solid_stack_web:install +``` + +This creates `config/initializers/solid_stack_web.rb` with every configuration option commented inline, and injects `mount SolidStackWeb::Engine, at: "/solid_stack"` into `config/routes.rb`. + --- ## Requirements