Skip to content
Merged
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
3 changes: 2 additions & 1 deletion apps/web/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,12 +22,13 @@
"@corbits/error-sink": "workspace:*",
"@corbits/mcp": "github:corbitsdev/corbits-mcp#9df1ab81d2f50d798bca2d2f44eb4759c92fac0e",
"@corbits/myra": "workspace:*",
"@corbits/react-ui": "github:corbitsdev/react-ui#3b122812a307ccb35be31386f7696020c5a84635",
"@corbits/react-ui": "0.3.0",
"@corbits/url-path": "workspace:*",
"@corbits/workflows": "workspace:*",
"@intx/types": "workspace:*",
"@isomorphic-git/lightning-fs": "4.7.0",
"@radix-ui/react-dialog": "^1.1.15",
"@radix-ui/react-dropdown-menu": "^2.1.16",
"@radix-ui/react-slot": "^1.2.3",
"@tanstack/react-query": "catalog:",
"arktype": "catalog:",
Expand Down
67 changes: 0 additions & 67 deletions apps/web/src/app.css
Original file line number Diff line number Diff line change
Expand Up @@ -800,74 +800,7 @@ select:disabled,
font-weight: 650;
}

.wb-av {
position: relative;
display: inline-flex;
flex: 0 0 auto;
}

.wb-av-st {
position: absolute;
right: -3px;
bottom: -3px;
width: 10px;
height: 10px;
border-radius: 50%;
border: 2px solid var(--background);
background: var(--muted-foreground);
}

.wb-av-st--ready {
background: var(--success);
}

.wb-av-st--idle {
background: color-mix(in srgb, var(--muted-foreground) 50%, transparent);
}

/* The arc travels a ring concentric with the mark. The conic angle is what
animates, so the masked shape itself never rotates. */
@property --orbit-a {
syntax: "<angle>";
inherits: false;
initial-value: 0deg;
}

.wb-av-orbit {
position: absolute;
inset: -3.5px;
padding: 1.5px;
pointer-events: none;
border-radius: calc(var(--av-r) + 3.5px);
background: conic-gradient(
from var(--orbit-a),
transparent 0deg,
color-mix(in srgb, var(--primary) 20%, transparent) 20deg,
var(--primary) 130deg,
transparent 131deg 360deg
);
-webkit-mask:
linear-gradient(#000 0 0) content-box,
linear-gradient(#000 0 0);
-webkit-mask-composite: xor;
mask-composite: exclude;
animation: wb-av-orbit 1.4s linear infinite;
}

.wb-av[data-kind="person"] .wb-av-orbit {
border-radius: 50%;
}

@keyframes wb-av-orbit {
to {
--orbit-a: 360deg;
}
}

@media (prefers-reduced-motion: reduce) {
.wb-av-orbit {
animation: none;
}
.shell-ch-row {
transition: none;
}
Expand Down
3 changes: 1 addition & 2 deletions apps/web/src/auth-screen.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,7 @@
// seeds a default dev account, and hosted deployments already have accounts —
// with creating an account one click away in the form's footer.

import { Button } from "@corbits/react-ui";
import { LoginForm } from "@corbits/react-ui/blocks/login/login-form";
import { Button, LoginForm } from "@corbits/react-ui";
import { useState } from "react";

import { AuthLayout } from "./auth/auth-layout";
Expand Down
3 changes: 2 additions & 1 deletion apps/web/src/bench/grants-tab.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { ConfirmButton, toast } from "@corbits/react-ui";
import { ConfirmButton } from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import type { GrantEffect } from "@intx/types";
import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";

Expand Down
3 changes: 2 additions & 1 deletion apps/web/src/bench/information-tab.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { Button, Skeleton, formatRelativeTime, toast } from "@corbits/react-ui";
import { Button, Skeleton, formatRelativeTime } from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import { useQuery } from "@tanstack/react-query";
import { useState } from "react";

Expand Down
3 changes: 2 additions & 1 deletion apps/web/src/chat/approval-row.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,8 @@
// workbench workbench's info column and the chat transcript, so a person can
// answer an agent's ask wherever they are looking when it lands.

import { Button, formatRelativeTime, toast } from "@corbits/react-ui";
import { Button, formatRelativeTime } from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import { useMutation, useQueryClient } from "@tanstack/react-query";

import { approveApproval, rejectApproval } from "../api";
Expand Down
54 changes: 20 additions & 34 deletions apps/web/src/chat/avatar.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,11 @@
import { Avatar, AvatarStack, type AvatarStackItem, type AvatarTone } from "@corbits/react-ui";
import {
Avatar,
AvatarStack,
type AvatarSize,
type AvatarStackItem,
type AvatarStatus,
type AvatarTone,
} from "@corbits/react-ui";

import { agentInitials } from "@/chat/threads-api";

Expand Down Expand Up @@ -61,18 +68,8 @@ export function resolveAvatarFill(
return { kind: "generated", className: avatarClassForPrincipal(principalId) };
}

export type CorbitAvatarSize = "xs" | "sm" | "md" | "lg" | "xl" | number;
export type AvatarStatus = "working" | "ready" | "idle";

// react-ui ships sm/md/lg only; the wrapper sizes xs/xl/numeric and the
// mark fills it.
const SIZE_PX = { xs: 16, sm: 24, md: 32, lg: 40, xl: 80 } as const;

function baseSize(px: number): "sm" | "md" | "lg" {
if (px <= 24) return "sm";
if (px <= 32) return "md";
return "lg";
}
export type CorbitAvatarSize = AvatarSize;
export type { AvatarStatus };

export interface WorkbenchAvatarProps {
/** Workers are rounded squares, people circles. */
Expand All @@ -92,28 +89,17 @@ export function WorkbenchAvatar({
status,
className,
}: WorkbenchAvatarProps) {
const px = typeof size === "number" ? size : SIZE_PX[size];
const radius = kind === "person" ? "50%" : `${Math.round(px * 0.28)}px`;
const working = kind === "worker" && status === "working";
return (
<span
className={["wb-av", className].filter(Boolean).join(" ")}
data-kind={kind}
{...(status === undefined ? {} : { "data-status": status })}
style={{ width: px, height: px, ["--av-r" as string]: radius }}
>
<Avatar
initials={agentInitials(name)}
label={name}
tone={tone}
size={baseSize(px)}
className="size-full! rounded-(--av-r)"
/>
{working ? <span className="wb-av-orbit" aria-hidden="true" /> : null}
{status === undefined || working ? null : (
<span className={`wb-av-st wb-av-st--${status}`} aria-hidden="true" />
)}
</span>
<Avatar
initials={agentInitials(name)}
label={name}
tone={tone}
size={size}
shape={kind === "person" ? "circle" : "square"}
orbit={kind === "worker" && status === "working"}
{...(status === undefined ? {} : { status })}
{...(className === undefined ? {} : { className })}
/>
);
}

Expand Down
8 changes: 6 additions & 2 deletions apps/web/src/command-palette-provider.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
import { artifactKindLabel, CommandPalette, useCommandShortcut } from "@corbits/react-ui";
import type { CommandPaletteGroup } from "@corbits/react-ui";
import { artifactKindLabel } from "@corbits/react-ui";
import {
CommandPalette,
useCommandShortcut,
type CommandPaletteGroup,
} from "@corbits/react-ui/ui/command-palette";
import { listWorkbenches } from "@/chat/workbench-tenants";
import { libraryArtifactPath } from "@/library";
import { reportError } from "@corbits/error-sink";
Expand Down
2 changes: 1 addition & 1 deletion apps/web/src/global-routines.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
// Scheduled workflow definitions across every bench the signed-in account
// belongs to — the aggregation both Workflows surfaces read from: the
// roster at `/workflows` and the detail page at `/workflows/<definitionId>`.
import { toast } from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import { reportError } from "@corbits/error-sink";
import { useMemo } from "react";
import { useQueries, useQueryClient } from "@tanstack/react-query";
Expand Down
23 changes: 14 additions & 9 deletions apps/web/src/onboarding/provider-connect-step.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
// Connects one provider credential through the stock catalog routes and
// derives the single offering it mints; a tenant that already resolves an
// offering skips this step (see `resolveExistingOffering`).
import { Button, Input, RadioGroup, RadioOption, Select } from "@corbits/react-ui";
import { Button, Input, Select } from "@corbits/react-ui";
import { Cpu, Key, LinkSimple } from "@/lib/icons";
import {
cancelProviderLogin,
Expand Down Expand Up @@ -456,12 +456,9 @@ export function ProviderConnectStep({

return (
<form className="onboarding-credential-form" onSubmit={(event) => void handleSubmit(event)}>
<RadioGroup
name="provider"
label="Inference provider"
value={selected ?? ""}
onValueChange={selectOption}
>
{/* Native radios until react-ui ships its RadioGroup again. */}
<fieldset role="radiogroup" className="onboarding-provider-group">
<legend>Inference provider</legend>
{PROVIDER_OPTIONS.map((candidate) => {
const rowId = `provider-${candidate.id}`;
const RowIcon = candidate.local
Expand All @@ -471,7 +468,15 @@ export function ProviderConnectStep({
: Key;
return (
<div key={candidate.id} className="onboarding-provider-row">
<RadioOption value={candidate.id} id={rowId} describedBy={`${rowId}-desc`} />
<input
type="radio"
name="provider"
id={rowId}
value={candidate.id}
checked={selected === candidate.id}
onChange={() => selectOption(candidate.id)}
aria-describedby={`${rowId}-desc`}
/>
<span className="onboarding-provider-icon" aria-hidden="true">
<RowIcon size={16} />
</span>
Expand All @@ -484,7 +489,7 @@ export function ProviderConnectStep({
</div>
);
})}
</RadioGroup>
</fieldset>
{option === undefined ? null : oauthProvider !== undefined ? (
<>
{modelPicker}
Expand Down
17 changes: 17 additions & 0 deletions apps/web/src/onboarding/provider-rows.css
Original file line number Diff line number Diff line change
Expand Up @@ -32,3 +32,20 @@
font-size: 0.75rem;
color: var(--muted-foreground);
}

.onboarding-provider-group {
margin: 0;
padding: 0;
border: 0;
}

.onboarding-provider-group legend {
padding: 0;
font-size: 0.875rem;
font-weight: 500;
}

.onboarding-provider-row input[type="radio"] {
flex: none;
accent-color: var(--primary);
}
7 changes: 2 additions & 5 deletions apps/web/src/pages/create-agent-panel.tsx
Original file line number Diff line number Diff line change
@@ -1,19 +1,16 @@
// No drafting assist or per-agent model/skills pin: the routes that backed
// those were removed from the hub.

import { Button, IntakeForm, SelectionCheckbox, Textarea } from "@corbits/react-ui";
import {
Button,
Dialog,
DialogBody,
DialogContent,
DialogDescription,
DialogFooter,
DialogHeader,
DialogTitle,
IntakeForm,
SelectionCheckbox,
Textarea,
} from "@corbits/react-ui";
} from "@corbits/react-ui/ui/dialog";
import type { IntakeField } from "@corbits/react-ui";
import { useState } from "react";

Expand Down
6 changes: 2 additions & 4 deletions apps/web/src/pages/create-skill-dialog.tsx
Original file line number Diff line number Diff line change
@@ -1,18 +1,16 @@
// Scoped down to naming the asset only: the stock asset routes accept a
// bare `{ kind, name, displayName }`, with no stock route yet to write a
// skill's SKILL.md content in the same call.
import { Button, IntakeForm, intakeFieldsComplete } from "@corbits/react-ui";
import {
Button,
Dialog,
DialogBody,
DialogContent,
DialogDescription,
DialogFooter,
DialogHeader,
DialogTitle,
IntakeForm,
intakeFieldsComplete,
} from "@corbits/react-ui";
} from "@corbits/react-ui/ui/dialog";
import type { IntakeField } from "@corbits/react-ui";
import { useState } from "react";

Expand Down
7 changes: 2 additions & 5 deletions apps/web/src/pages/library-page.tsx
Original file line number Diff line number Diff line change
@@ -1,10 +1,6 @@
import {
BulkActionBar,
Button,
Menu,
MenuContent,
MenuItem,
MenuTrigger,
RichEmptyState,
SelectionCheckbox,
Skeleton,
Expand All @@ -16,9 +12,10 @@ import {
TableRow,
artifactKindLabel,
formatRelativeTime,
toast,
useListSelection,
} from "@corbits/react-ui";
import { Menu, MenuContent, MenuItem, MenuTrigger } from "@corbits/react-ui/ui/menu";
import { toast } from "@corbits/react-ui/ui/toast";
import type { SelectionCheckboxState, UseListSelectionResult } from "@corbits/react-ui";
import {
ArtifactRenderer,
Expand Down
3 changes: 2 additions & 1 deletion apps/web/src/pages/new-workbench-picker.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
// A new workbench starts from one message: creating it deploys its agent and
// posts the message so the worker starts.

import { Button, toast } from "@corbits/react-ui";
import { Button } from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import { WorkbenchLoadingState } from "@/chat";
import { useState } from "react";
import { useMutation, useQueryClient } from "@tanstack/react-query";
Expand Down
2 changes: 1 addition & 1 deletion apps/web/src/pages/skill-detail-page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,8 @@ import {
Section,
Textarea,
formatRelativeTime,
toast,
} from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import { Lightning } from "@/lib/icons";
import { WorkbenchLoadingState } from "@/chat";
import { ApiQueryError, describeApiError } from "@/lib/api-query";
Expand Down
2 changes: 1 addition & 1 deletion apps/web/src/pages/tools-page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,8 @@ import {
TableHead,
TableHeader,
TableRow,
toast,
} from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import { QueryView } from "@/lib/api-query";
import { Plugs } from "@/lib/icons";

Expand Down
3 changes: 2 additions & 1 deletion apps/web/src/pages/workbench-page.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
// See docs/chat-mail-threading.md. The bench pill opens a drawer that pushes
// the thread left; the drawer's Information tab carries the bench overview.

import { Button, EmptyState, PageShell, Skeleton, toast } from "@corbits/react-ui";
import { Button, EmptyState, PageShell, Skeleton } from "@corbits/react-ui";
import { toast } from "@corbits/react-ui/ui/toast";
import { WarningCircle } from "@/lib/icons";
import { useMutation, useQuery, useQueryClient } from "@tanstack/react-query";
import { useCallback, useEffect, useRef, useState } from "react";
Expand Down
Loading
Loading