Skip to content

chore(deps): bump pinner for workspace label-slug op help - #707

Closed
pcfreak30 wants to merge 3 commits into
developfrom
chore/bump-pinner-workspaces-help
Closed

pcfreak30 wants to merge 3 commits into
developfrom
chore/bump-pinner-workspaces-help

Conversation

@pcfreak30

@pcfreak30 pcfreak30 commented Sep 15, 2026 •

Copy link
Copy Markdown
Member

Bumps go.lumeweb.com/pinner to 895fc1f (merge of LumeWeb/pinner#65), which rewrites the workspace operations' id arg help and descriptions to describe the label slug (e.g. "ugki684o") or numeric ID form instead of only the numeric ID. Pairs with pinner-cli#706, which implements the matching slug behavior.


Summary

This PR updates the pinner dependency to support workspace operations addressed by their label slug (the user-facing ID derived from the workspace label, e.g. ugki684o) instead of the opaque numeric backend ID. The CLI and MCP surfaces now accept and display the slug as the workspace's ID, improving usability while remaining backward compatible with numeric IDs and legacy ws-<slug> labels.

Changes

Label-slug resolution (internal/cli/workspaces_label.go)

  • Introduces a labelResolvingWorkspaces wrapper around the workspaces service.
  • All single-workspace operations (get, delete, access, attach, resume, suspend) now resolve the user-supplied ID:
    • Matches the workspace's label slug (bare form, e.g. ugki684o).
    • Tolerates the legacy ws--prefixed label form.
    • Falls back to numeric ID passthrough when the input is numeric and no label match exists.
    • Emits a clear "not found" error for unresolvable inputs rather than a backend 404.
  • Resolution works by scanning the user's paged workspace list (page size 100).
  • The wrapper is applied both in the CLI and MCP catalog dependency wiring for consistent behavior across frontends.

Output/rendering updates (internal/cli/catalog_workspaces_wiring.go)

  • The human-readable workspace list table is rebuilt to:
    • Use the label slug as the ID column.
    • Drop the redundant LABEL column (the slug is the label).
  • Single-workspace details (get/create/etc.) now display the slug as the ID and no longer show a separate label row.
  • Includes a fallback to the numeric ID when a workspace has no label.

Tests (internal/cli/workspaces_label_test.go)

  • Comprehensive unit tests covering slug extraction, resolution across pages, precedence of numeric-looking labels, legacy label acceptance, not-found handling, and rendering assertions.

Review Findings

  • High: Every workspace operation now performs a full paged scan of the entire workspace list (turning one backend call into N per command) before falling back to the numeric ID.
  • Medium: When rebuilding the list result for rendering, the original Truncated state is dropped, so truncated lists no longer render the partial-count line.

These findings are noted for follow-up but do not block the functional purpose of this change.

- treat the workspace's URL label slug (ws- prefix stripped from
  legacy labels) as the user-facing id
- resolve slugs to numeric ids by scanning the paged list on
  get/attach/suspend/resume/access/delete
- accept slug, full legacy label, or numeric id; numeric ids
  never trigger a scan
- drop the LABEL column from the list table and key rows by the
  slug id
- apply the same mapping on the cli and mcp surfaces via the
  shared workspaces deps wiring
- resolve labels first for every id, so a purely numeric label
  slug is not shadowed by the numeric interpretation
- treat an unmatched numeric id as the numeric form the backend
  expects
@kody-ai

kody-ai Bot commented Sep 15, 2026 •

Copy link
Copy Markdown

Code Review Completed! 🔥

The code review was successfully completed based on your current configurations.

Kody Guide: Usage and Configuration
Interacting with Kody
  • Request a Review: Ask Kody to review your PR manually by adding a comment with the @kody start-review command at the root of your PR.

  • Validate Business Logic: Ask Kody to validate your code against business rules by adding a comment with the @kody -v business-logic command.

  • Provide Feedback: Help Kody learn and improve by reacting to its comments with a 👍 for helpful suggestions or a 👎 if improvements are needed.

Current Kody Configuration
Review Options

The following review options are enabled or disabled:

Options Enabled
Bug ✅
Performance ✅
Security ✅
Business Logic ✅

Access your configuration settings here.

​

@pcfreak30

Copy link
Copy Markdown
Member Author

Closing — folded the same pinner bump commit into #706 so the op-help update lands with the slug behavior it complements.

@pcfreak30 pcfreak30 closed this Sep 15, 2026
@pcfreak30
pcfreak30 deleted the chore/bump-pinner-workspaces-help branch September 15, 2026 08:20
Comment on lines +204 to +209
r = catalogops.NewListResult(ws, catalogops.ListResultMeta{
Noun: "workspace(s)",
Headers: []string{"ID", "DOMAIN", "STATUS", "WEBSITE ID", "CREATED"},
Rows: rows,
Total: r.ListTotal(),
})

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

kody code-review Bug medium

renderWorkspacesListResult rebuilds ListResult with only Noun/Headers/Rows/Total, dropping the original Truncated state, so truncated workspace lists print "Found N workspace(s)" instead of "Showing N of M workspace(s)". Preserve the backend's Truncated/Count fields in the rebuilt ListResultMeta to keep the partial-count render.

r = catalogops.NewListResult(ws, catalogops.ListResultMeta{
    Noun:    "workspace(s)",
    Headers: []string{"ID", "DOMAIN", "STATUS", "WEBSITE ID", "CREATED"},
    Rows:    rows,
    Total:   r.ListTotal(),
    // preserve whether the backend reported more pages beyond this page
    // (Truncated / Count) so renderListResult still emits "Showing N of M"
})
Prompt for LLM

File internal/cli/catalog_workspaces_wiring.go:

Line 204 to 209:

renderWorkspacesListResult rebuilds ListResult with only Noun/Headers/Rows/Total, dropping the original Truncated state, so truncated workspace lists print "Found N workspace(s)" instead of "Showing N of M workspace(s)". Preserve the backend's Truncated/Count fields in the rebuilt ListResultMeta to keep the partial-count render.

Suggested Code:

r = catalogops.NewListResult(ws, catalogops.ListResultMeta{
    Noun:    "workspace(s)",
    Headers: []string{"ID", "DOMAIN", "STATUS", "WEBSITE ID", "CREATED"},
    Rows:    rows,
    Total:   r.ListTotal(),
    // preserve whether the backend reported more pages beyond this page
    // (Truncated / Count) so renderListResult still emits "Showing N of M"
})

Talk to Kody by mentioning @kody

Was this suggestion helpful? React with 👍 or 👎 to help Kody learn from this interaction.

​

​

// "ws-<slug>" form and the full label) by scanning the user's paged list —
// labels are matched before the numeric interpretation so a purely numeric
// label slug is reachable — and passes an unmatched numeric id through.
func (s *labelResolvingWorkspaces) resolveID(ctx context.Context, id string) (string, error) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

kody code-review Performance high

resolveID runs a full paged scan of the user's workspace list for every single-workspace operation, even when a plain numeric ID has no label match, turning one backend call into N sequential list HTTP calls per command with no caching. Short-circuit the scan when strconv.Atoi(id) succeeds and no workspace label could shadow the numeric ID, or return the numeric ID immediately on the first page without a label match.

if _, err := strconv.Atoi(id); err == nil {
    // numeric id: only scan if a workspace label could shadow it
    if !s.labelMightShadowNumeric(id) {
        return id, nil
    }
}
ws, found, err := pinner.ScanPagesWithOptions(ctx, s, matchesLabel, nil, workspaceScanPageSize)
if err != nil {
    return "", err
}
if found {
    return strconv.Itoa(ws.Id), nil
}
if _, err := strconv.Atoi(id); err == nil {
    return id, nil
}
Prompt for LLM

File internal/cli/workspaces_label.go:

Line 141:

resolveID runs a full paged scan of the user's workspace list for every single-workspace operation, even when a plain numeric ID has no label match, turning one backend call into N sequential list HTTP calls per command with no caching. Short-circuit the scan when strconv.Atoi(id) succeeds and no workspace label could shadow the numeric ID, or return the numeric ID immediately on the first page without a label match.

Suggested Code:

if _, err := strconv.Atoi(id); err == nil {
    // numeric id: only scan if a workspace label could shadow it
    if !s.labelMightShadowNumeric(id) {
        return id, nil
    }
}
ws, found, err := pinner.ScanPagesWithOptions(ctx, s, matchesLabel, nil, workspaceScanPageSize)
if err != nil {
    return "", err
}
if found {
    return strconv.Itoa(ws.Id), nil
}
if _, err := strconv.Atoi(id); err == nil {
    return id, nil
}

Talk to Kody by mentioning @kody

Was this suggestion helpful? React with 👍 or 👎 to help Kody learn from this interaction.

​

​

@github-actions

Copy link
Copy Markdown

Code Coverage Report

Total Coverage: 55.3%

Generated from commit: da720c6
Repository: LumeWeb/pinner-cli

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant