Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings
6 changes: 6 additions & 0 deletions 6 .server-changes/admin-back-office-rate-limit.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
area: webapp
type: feature
---

Add a "Back office" tab to `/admin` and a per-organization detail page at `/admin/back-office/orgs/:orgId`. The first action available on that page is editing the org's API rate limit: admins can save a `tokenBucket` override (refill rate, interval, max tokens) and see a plain-English preview of the resulting sustained rate and burst allowance. Writes are audit-logged via the server logger.
17 changes: 13 additions & 4 deletions 17 apps/webapp/app/components/primitives/Tabs.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ export type TabsProps = {
tabs: {
label: string;
to: string;
end?: boolean;
}[];
className?: string;
layoutId: string;
Expand All @@ -21,7 +22,13 @@ export function Tabs({ tabs, className, layoutId, variant = "underline" }: TabsP
return (
<TabContainer className={className} variant={variant}>
{tabs.map((tab, index) => (
<TabLink key={index} to={tab.to} layoutId={layoutId} variant={variant}>
<TabLink
key={index}
to={tab.to}
layoutId={layoutId}
variant={variant}
end={tab.end ?? true}
>
{tab.label}
</TabLink>
))}
Expand Down Expand Up @@ -62,18 +69,20 @@ export function TabLink({
children,
layoutId,
variant = "underline",
end = true,
}: {
to: string;
children: ReactNode;
layoutId: string;
variant?: Variants;
end?: boolean;
}) {
if (variant === "segmented") {
return (
<NavLink
to={to}
className="group relative flex h-full grow items-center justify-center focus-custom"
end
end={end}
>
{({ isActive, isPending }) => {
const active = isActive || isPending;
Expand Down Expand Up @@ -110,7 +119,7 @@ export function TabLink({
<NavLink
to={to}
className="group flex flex-col items-center border-r border-charcoal-700 px-2 pt-1 focus-custom first:pl-0 last:border-none"
end
end={end}
>
{({ isActive, isPending }) => {
const active = isActive || isPending;
Expand All @@ -131,7 +140,7 @@ export function TabLink({

// underline variant (default)
return (
<NavLink to={to} className="group flex flex-col items-center pt-1 focus-custom" end>
<NavLink to={to} className="group flex flex-col items-center pt-1 focus-custom" end={end}>
{({ isActive, isPending }) => {
return (
<>
Expand Down
29 changes: 29 additions & 0 deletions 29 apps/webapp/app/routes/admin.back-office._index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
import type { LoaderFunctionArgs } from "@remix-run/server-runtime";
import { redirect, typedjson } from "remix-typedjson";
import { LinkButton } from "~/components/primitives/Buttons";
import { Header2 } from "~/components/primitives/Headers";
import { Paragraph } from "~/components/primitives/Paragraph";
import { requireUser } from "~/services/session.server";

export async function loader({ request }: LoaderFunctionArgs) {
const user = await requireUser(request);
if (!user.admin) {
return redirect("/");
}
return typedjson({});
}

export default function BackOfficeIndex() {
return (
<div className="flex flex-col items-start gap-3 py-6">
<Header2>Back office</Header2>
<Paragraph variant="base" className="max-w-prose">
Back-office actions are applied to a single organization. Pick an org from the
Organizations tab to open its detail page.
</Paragraph>
<LinkButton to="/admin/orgs" variant="primary/medium">
Pick an organization
</LinkButton>
</div>
);
}
Loading
Loading
Morty Proxy This is a proxified and sanitized view of the page, visit original site.