feat(portal): one-click "View client portal" preview from the project page
Adds a "View client portal" button on the project detail page that opens the
client portal scoped to that project — no CLI. GET /projects/{id}/portal-preview
auto-provisions a client + access token for the project (provision_preview_session)
and seals a portal session cookie, then redirects to /portal.
- Reuses the project's linked client if it has one; otherwise creates/reuses a
per-project 'preview-<id>' client. Only sets project.client_id when unset, so it
never clobbers a real client link. Idempotent — repeat clicks reuse the same
client/token.
- Lives under /projects (not /portal), so a future public proxy exposing only
/portal/* won't expose this operator shortcut.
Verified: provisioning (unlinked creates+links, idempotent, linked-no-clobber) 7/7.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -4,7 +4,7 @@
|
||||
|
||||
{% block content %}
|
||||
<!-- Breadcrumb Navigation -->
|
||||
<div class="mb-6">
|
||||
<div class="mb-6 flex items-center justify-between gap-3">
|
||||
<nav class="flex items-center space-x-2 text-sm">
|
||||
<a href="/projects" class="text-seismo-orange hover:text-seismo-navy flex items-center">
|
||||
<svg class="w-4 h-4 mr-1" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||
@@ -17,6 +17,17 @@
|
||||
</svg>
|
||||
<span class="text-gray-900 dark:text-white font-medium" id="project-name-breadcrumb">Project</span>
|
||||
</nav>
|
||||
|
||||
<!-- Preview the client portal for this project (opens scoped, read-only) -->
|
||||
<a href="/projects/{{ project_id }}/portal-preview" target="_blank" rel="noopener"
|
||||
class="shrink-0 inline-flex items-center gap-1.5 px-3 py-1.5 text-sm rounded-lg border border-seismo-orange/40 bg-seismo-orange/10 text-seismo-orange hover:bg-seismo-orange/20 transition-colors"
|
||||
title="Preview this project's client portal in a new tab">
|
||||
<svg class="w-4 h-4" fill="none" stroke="currentColor" viewBox="0 0 24 24">
|
||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M15 12a3 3 0 11-6 0 3 3 0 016 0z"></path>
|
||||
<path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M2.458 12C3.732 7.943 7.523 5 12 5c4.478 0 8.268 2.943 9.542 7-1.274 4.057-5.064 7-9.542 7-4.477 0-8.268-2.943-9.542-7z"></path>
|
||||
</svg>
|
||||
View client portal
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<!-- Header (loads dynamically) -->
|
||||
|
||||
Reference in New Issue
Block a user