import React from 'react'; import { MessageSquareText, Lock } from 'lucide-react'; import { Button } from '../../../../components/ui/button'; /** * What the Messages panels render when the thread list did not arrive.. * * THE DEFECT THIS REPLACES WAS TWO CONTRADICTORY SENTENCES IN ONE VIEWPORT. Measured as HR on the * staff Messages screen: the banner said *"You do not have access to this information"* - correct, and * permanent - while the panel underneath said **"Unable to load messages / Please try again later"** with * a **Retry** button. **The false one had the button**, so a reader takes the retryable characterisation * as the live status and hammers Retry against a door that is working exactly as designed. * * A correct authorization decision must never render as a retryable fault * is the same family from the other side: a * denial may not render as EMPTY DATA either, because that is a false claim that the user has no records. * Both halves are why this component exists rather than an early `return null`. * * ONE COMPONENT FOR BOTH PANELS, deliberately. The identical hard-coded block lived in the Colleagues * panel and the Patients panel - one defect with two faces, which is exactly the shape that gets half * fixed and reads as done. */ export interface MessagesLoadFailureProps { /** The sentence the loader produced. Already correct for the cause - `describeFetchFailure` owns it. */ message: string; /** * `false` for an authorization outcome, `true` for a fault a retry could clear. * * `undefined` renders as RETRYABLE. Failing open here is the deliberate direction: withholding * Retry from someone whose load failed on a network blip strands them, while offering it on a denial * is merely useless. The classification comes from the status code, so `undefined` means we genuinely * could not tell. */ retryable?: boolean; onRetry: () => void; /** Centred in the list pane it sits in, rather than standing a viewport tall. */ inPane?: boolean; } export const MessagesLoadFailure: React.FC = ({ message, retryable, onRetry, inPane }) => { const isDenial = retryable === false; return (
{/* ⛔ Not the destructive tone for a denial. Nothing is broken — the system is working and this role is not entitled — and a red failure treatment on an unbroken screen is what sent people looking for an outage that does not exist. */} {isDenial ? ( ) : ( )}

{isDenial ? 'Messages are not available to you' : 'Unable to load messages'}

{/* ⭐ The loader's own sentence, rather than a second one written here. The panel used to discard it and print "Please try again later" for every cause, which is how a 403 acquired retry copy the banner above it had already contradicted. */}

{message}

{/* 🚨 THE BUTTON IS THE WHOLE POINT OF THE DISTINCTION. A retry cannot change an authorization decision, and offering one asserts that it can. */} {!isDenial && ( )}
); }; export default MessagesLoadFailure;