/* ===================================================================
   IMPORT CENTER (#167) — the ingest pipeline's UI.

   Built as a sibling of the Governance hub (yb-gov) and the Services dashboard (yb-svc): the same
   hero + card-grid construction, the same --yb-* tokens from ui-refinement.css, the same shared
   primitives (yb-dialog-btn, yb-seg, yb-field-error, yb-dialog-scroll). Nothing here invents a
   colour or a radius — dark mode therefore rides on the tokens with no per-component overrides.

   The one thing this surface says that no other does: a full load DELETES. That is where the design
   spends its emphasis — the mode is a pair of explicit cards rather than a dropdown item, and
   choosing the destructive one swaps in a red-railed panel that names exactly what it will sweep.
   =================================================================== */

.yb-imp {
    display: flex;
    flex-direction: column;
    gap: 1.25rem;
    /* The page shell centres its text; everything here is read left-to-right prose and forms. */
    text-align: left;
}

/* Dark-mode parity for the native Bootstrap controls on this page. Syncfusion editors theme
   themselves, so only the plain .form-control / <textarea> need this — left un-styled they keep a
   white fill on the dark surface. (Same gap #158 fixed inside .yb-dialog; this surface is outside
   one.) Light mode is Bootstrap's own and is already correct. */
[data-theme="dark"] .yb-imp .form-control {
    background-color: var(--yb-surface-2);
    color: var(--yb-text);
    border-color: var(--yb-border-strong);
}

[data-theme="dark"] .yb-imp .form-control::placeholder {
    color: var(--yb-text-soft);
    opacity: 1;
}

[data-theme="dark"] .yb-imp .form-control:focus {
    background-color: var(--yb-surface-2);
    color: var(--yb-text);
}

/* ERP-managed notice (#165). Sits on the roster screens and the roster record view, exactly where
   the Add/Edit affordances used to be, so nobody hunts for an edit button that no longer exists.
   Informational, not a warning — the roster being ERP-owned is the design, not a fault. */
.yb-erp-note {
    display: flex;
    align-items: flex-start;
    gap: 0.55rem;
    margin: 0.85rem 0;
    padding: 0.7rem 0.9rem;
    border: 1px solid var(--yb-border);
    border-left: 3px solid var(--yb-accent);
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface-2);
    font-size: 0.85rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
    text-align: left;
}

.yb-erp-note > i {
    color: var(--yb-accent);
    margin-top: 0.12rem;
    flex: none;
}

.yb-erp-note strong { color: var(--yb-text); }

/* No required asterisks on a read-only roster record (#165).
   The rule from #147 is that a marker means "the user must fill this in" — not "the API needs this
   column". On a view-only record there is nothing to fill in, so the asterisk is a promise of an
   input that does not exist. The fields keep their [Required] attributes (they still describe what
   the ERP must supply); only the marker, which speaks to a person filling a form, is dropped. */
.yb-form-page fieldset[disabled] .yb-required-marker {
    display: none;
}

/* ── Hero ─────────────────────────────────────────────────────────── */
.yb-imp-hero {
    display: flex;
    align-items: flex-start;
    gap: 1rem;
    padding: 1.1rem 1.25rem;
    border: 1px solid var(--yb-border);
    border-left: 3px solid var(--yb-accent);
    border-radius: var(--yb-radius);
    background: var(--yb-surface);
    box-shadow: var(--yb-shadow-xs);
}

.yb-imp-hero__icon {
    flex: none;
    width: 2.6rem;
    height: 2.6rem;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--yb-radius);
    background: rgba(var(--yb-accent-rgb), 0.12);
    color: var(--yb-accent);
    font-size: 1.2rem;
}

.yb-imp-hero__name {
    margin: 0;
    font-family: var(--yb-font-display);
    font-size: 1.1rem;
    font-weight: 600;
    color: var(--yb-text);
}

.yb-imp-hero__sub {
    display: block;
    margin-top: 0.2rem;
    font-size: 0.86rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-imp-hero__sub strong { color: var(--yb-text); font-weight: 600; }

/* ── Grouped domain cards ─────────────────────────────────────────── */
.yb-imp-group { display: flex; flex-direction: column; gap: 0.6rem; }

.yb-imp-group__title {
    margin: 0;
    font-size: 0.72rem;
    font-weight: 700;
    letter-spacing: 0.1em;
    text-transform: uppercase;
    color: var(--yb-text-soft);
}

.yb-imp-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(260px, 1fr));
    gap: 0.75rem;
}

.yb-imp-card {
    display: flex;
    flex-direction: column;
    gap: 0.55rem;
    padding: 0.9rem 1rem;
    border: 1px solid var(--yb-border);
    border-radius: var(--yb-radius);
    background: var(--yb-card);
    box-shadow: var(--yb-shadow-xs);
    text-decoration: none;
    color: inherit;
    transition: transform var(--yb-dur) var(--yb-ease),
                box-shadow var(--yb-dur) var(--yb-ease),
                border-color var(--yb-dur) var(--yb-ease);
}

a.yb-imp-card:hover {
    transform: translateY(-2px);
    box-shadow: var(--yb-shadow);
    border-color: rgba(var(--yb-accent-rgb), 0.45);
}

.yb-imp-card.is-locked { opacity: 0.6; box-shadow: none; }

.yb-imp-card__head { display: flex; align-items: center; gap: 0.55rem; }

.yb-imp-card__icon {
    flex: none;
    width: 2rem;
    height: 2rem;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--yb-radius-sm);
    background: rgba(var(--yb-accent-rgb), 0.1);
    color: var(--yb-accent);
}

.yb-imp-card__title { font-weight: 600; color: var(--yb-text); }
.yb-imp-card__go { margin-left: auto; color: var(--yb-text-soft); }

.yb-imp-card__note {
    margin: 0;
    font-size: 0.8rem;
    line-height: 1.45;
    color: var(--yb-text-muted);
}

/* The scope chip. Not decoration — this is the blast radius of a full load, which is why it sits on
   the card at all, before anyone has committed to anything. */
.yb-imp-scope {
    align-self: flex-start;
    display: inline-flex;
    align-items: center;
    gap: 0.3rem;
    padding: 3px 8px;
    border-radius: var(--yb-radius-sm);
    border: 1px solid var(--yb-border);
    font-size: 0.7rem;
    font-weight: 600;
    color: var(--yb-text-muted);
    background: var(--yb-surface-2);
}

.yb-imp-scope--product { color: var(--yb-text-muted); }
.yb-imp-scope--org { color: var(--yb-accent); border-color: rgba(var(--yb-accent-rgb), 0.3); }
.yb-imp-scope--branch { color: var(--yb-accent); border-color: rgba(var(--yb-accent-rgb), 0.3); }

/* ── The run page ─────────────────────────────────────────────────── */
.yb-imp-cols {
    display: grid;
    grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
    gap: 1rem;
    align-items: start;
}

@media (max-width: 1100px) {
    .yb-imp-cols { grid-template-columns: 1fr; }
}

.yb-imp-form { display: flex; flex-direction: column; gap: 0.85rem; }

.yb-imp-panel {
    padding: 1rem 1.1rem;
    border: 1px solid var(--yb-border);
    border-radius: var(--yb-radius);
    background: var(--yb-surface);
    box-shadow: var(--yb-shadow-xs);
}

.yb-imp-panel__head {
    display: flex;
    align-items: flex-start;
    gap: 0.65rem;
    margin-bottom: 0.85rem;
}

/* The steps are a real sequence — target, then file, then how — so numbering them carries
   information rather than decorating. */
.yb-imp-step {
    flex: none;
    width: 1.55rem;
    height: 1.55rem;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--yb-radius-pill);
    background: rgba(var(--yb-accent-rgb), 0.12);
    color: var(--yb-accent);
    font-size: 0.78rem;
    font-weight: 700;
}

.yb-imp-panel__title {
    margin: 0;
    font-size: 0.98rem;
    font-weight: 600;
    color: var(--yb-text);
}

.yb-imp-panel__sub {
    margin: 0.1rem 0 0;
    font-size: 0.8rem;
    color: var(--yb-text-muted);
}

.yb-imp-note {
    display: flex;
    align-items: center;
    gap: 0.5rem;
    padding: 0.6rem 0.75rem;
    border: 1px dashed var(--yb-border-strong);
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface-2);
    font-size: 0.84rem;
    color: var(--yb-text-muted);
}

.yb-imp-note i { color: var(--yb-accent); }

/* ── Template + file ─────────────────────────────────────────────── */
.yb-imp-templates {
    display: flex;
    align-items: center;
    gap: 0.5rem;
    margin-bottom: 0.75rem;
    flex-wrap: wrap;
}

.yb-imp-templates__label {
    font-size: 0.78rem;
    font-weight: 600;
    color: var(--yb-text-soft);
    margin-right: 0.15rem;
}

.yb-imp-drop {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: 0.2rem;
    width: 100%;
    padding: 1.4rem 1rem;
    border: 2px dashed var(--yb-border-strong);
    border-radius: var(--yb-radius);
    background: var(--yb-surface-2);
    cursor: pointer;
    text-align: center;
    transition: border-color var(--yb-dur) var(--yb-ease), background-color var(--yb-dur) var(--yb-ease);
}

.yb-imp-drop:hover { border-color: var(--yb-accent); }

.yb-imp-drop.is-set {
    border-style: solid;
    border-color: var(--yb-success);
    background: rgba(var(--yb-success-rgb), 0.07);
}

/* The whole tile is the label, so the native input is hidden but still focusable via the label. */
.yb-imp-drop__input {
    position: absolute;
    width: 1px;
    height: 1px;
    opacity: 0;
    pointer-events: none;
}

.yb-imp-drop:focus-within {
    outline: 2px solid var(--yb-accent);
    outline-offset: 2px;
}

.yb-imp-drop__icon { font-size: 1.5rem; color: var(--yb-text-soft); }
.yb-imp-drop.is-set .yb-imp-drop__icon { color: var(--yb-success); }
.yb-imp-drop__main { font-weight: 600; color: var(--yb-text); word-break: break-all; }
.yb-imp-drop__sub { font-size: 0.78rem; color: var(--yb-text-muted); }

/* ── Load mode: the destructive choice ───────────────────────────── */
.yb-imp-choice {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 0.6rem;
}

@media (max-width: 640px) {
    .yb-imp-choice { grid-template-columns: 1fr; }
}

.yb-imp-mode {
    display: flex;
    flex-direction: column;
    gap: 0.25rem;
    padding: 0.75rem 0.85rem;
    text-align: left;
    border: 1px solid var(--yb-border-strong);
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface);
    cursor: pointer;
    transition: border-color var(--yb-dur) var(--yb-ease), background-color var(--yb-dur) var(--yb-ease);
}

.yb-imp-mode:hover { border-color: var(--yb-accent); }

.yb-imp-mode.is-active {
    border-color: var(--yb-accent);
    background: rgba(var(--yb-accent-rgb), 0.08);
    box-shadow: inset 0 0 0 1px var(--yb-accent);
}

.yb-imp-mode__title {
    display: inline-flex;
    align-items: center;
    gap: 0.35rem;
    font-weight: 600;
    color: var(--yb-text);
}

.yb-imp-mode__sub { font-size: 0.78rem; line-height: 1.4; color: var(--yb-text-muted); }

/* Full is the one that deletes — it reads as danger even before it is chosen, so nobody picks it by
   pattern-matching "the other one". */
.yb-imp-mode--full:hover { border-color: var(--yb-danger); }

.yb-imp-mode--full.is-active {
    border-color: var(--yb-danger);
    background: rgba(var(--yb-danger-rgb), 0.08);
    box-shadow: inset 0 0 0 1px var(--yb-danger);
}

.yb-imp-mode--full .yb-imp-mode__title i { color: var(--yb-danger); }

.yb-imp-danger {
    margin-top: 0.75rem;
    padding: 0.85rem 1rem;
    border: 1px solid rgba(var(--yb-danger-rgb), 0.32);
    border-left: 3px solid var(--yb-danger);
    border-radius: var(--yb-radius-sm);
    background: rgba(var(--yb-danger-rgb), 0.07);
}

.yb-imp-danger__head {
    display: flex;
    align-items: flex-start;
    gap: 0.5rem;
    font-weight: 700;
    color: var(--yb-text);
}

.yb-imp-danger__head i { color: var(--yb-danger); margin-top: 0.1rem; }

.yb-imp-danger__body {
    margin: 0.35rem 0 0 1.55rem;
    font-size: 0.82rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-imp-override {
    margin-top: 0.85rem;
    padding-top: 0.75rem;
    border-top: 1px dashed rgba(var(--yb-danger-rgb), 0.32);
}

.yb-imp-override__check {
    display: flex;
    align-items: flex-start;
    gap: 0.55rem;
    font-size: 0.82rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
    cursor: pointer;
}

.yb-imp-override__check input { margin-top: 0.2rem; flex: none; }
.yb-imp-override__check strong { color: var(--yb-text); }

.yb-imp-strict {
    display: flex;
    align-items: center;
    gap: 0.65rem;
    flex-wrap: wrap;
    margin-top: 0.9rem;
    padding-top: 0.9rem;
    border-top: 1px solid var(--yb-border);
}

.yb-imp-strict__label { font-size: 0.8rem; font-weight: 600; color: var(--yb-text-soft); }

.yb-imp-actions {
    display: flex;
    align-items: center;
    justify-content: flex-end;
    gap: 0.5rem;
}

/* The submit button becomes the danger action when it would delete. */
.yb-imp-submit--full {
    background: var(--yb-danger);
    border-color: var(--yb-danger);
    color: #fff;
    box-shadow: 0 4px 12px rgba(var(--yb-danger-rgb), 0.28);
}

.yb-imp-submit--full:hover:not(:disabled) { filter: brightness(0.94); }

/* ── Report ──────────────────────────────────────────────────────── */
.yb-imp-result { position: sticky; top: 1rem; }

.yb-imp-result__idle {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: 0.5rem;
    min-height: 12rem;
    padding: 2rem;
    border: 1px dashed var(--yb-border);
    border-radius: var(--yb-radius);
    color: var(--yb-text-soft);
    font-size: 0.86rem;
}

.yb-imp-result__idle i { font-size: 1.6rem; }

.yb-imp-report {
    border: 1px solid var(--yb-border);
    border-left: 3px solid var(--yb-border-strong);
    border-radius: var(--yb-radius);
    background: var(--yb-surface);
    box-shadow: var(--yb-shadow-xs);
    padding: 1rem 1.1rem;
}

.yb-imp-report--ok { border-left-color: var(--yb-success); }
.yb-imp-report--pending { border-left-color: var(--yb-warning); }
.yb-imp-report--bad { border-left-color: var(--yb-danger); }

.yb-imp-report__head { display: flex; align-items: flex-start; gap: 0.7rem; }

.yb-imp-report__badge {
    flex: none;
    width: 2.2rem;
    height: 2.2rem;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--yb-radius);
    font-size: 1rem;
}

.yb-imp-report--ok .yb-imp-report__badge { background: rgba(var(--yb-success-rgb), 0.12); color: var(--yb-success); }
.yb-imp-report--pending .yb-imp-report__badge { background: rgba(var(--yb-warning-rgb), 0.14); color: var(--yb-warning); }
.yb-imp-report--bad .yb-imp-report__badge { background: rgba(var(--yb-danger-rgb), 0.12); color: var(--yb-danger); }

.yb-imp-report__eyebrow {
    display: block;
    font-size: 0.66rem;
    font-weight: 700;
    letter-spacing: 0.1em;
    text-transform: uppercase;
    color: var(--yb-text-soft);
}

.yb-imp-report__title {
    margin: 0;
    font-family: var(--yb-font-display);
    font-size: 1.05rem;
    font-weight: 600;
    color: var(--yb-text);
}

.yb-imp-report__file {
    font-size: 0.78rem;
    color: var(--yb-text-muted);
    word-break: break-all;
}

.yb-imp-report__batch {
    display: flex;
    align-items: flex-start;
    gap: 0.5rem;
    margin-top: 0.85rem;
    padding: 0.7rem 0.8rem;
    border: 1px solid rgba(var(--yb-danger-rgb), 0.32);
    border-radius: var(--yb-radius-sm);
    background: rgba(var(--yb-danger-rgb), 0.07);
    font-size: 0.84rem;
    line-height: 1.5;
    color: var(--yb-text);
}

.yb-imp-report__batch i { color: var(--yb-danger); margin-top: 0.1rem; flex: none; }

.yb-imp-report__pending {
    display: flex;
    align-items: flex-start;
    gap: 0.5rem;
    margin-top: 0.85rem;
    padding: 0.7rem 0.8rem;
    border: 1px solid rgba(var(--yb-warning-rgb), 0.32);
    border-radius: var(--yb-radius-sm);
    background: rgba(var(--yb-warning-rgb), 0.09);
    font-size: 0.84rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-imp-report__pending i { color: var(--yb-warning); margin-top: 0.1rem; flex: none; }

/* The approval a committed batch spent. Single-use — it authorized this run and nothing else. */
.yb-imp-report__authorized {
    display: flex;
    align-items: flex-start;
    gap: 0.5rem;
    margin-top: 0.85rem;
    padding: 0.7rem 0.8rem;
    border: 1px solid rgba(var(--yb-success-rgb), 0.3);
    border-radius: var(--yb-radius-sm);
    background: rgba(var(--yb-success-rgb), 0.08);
    font-size: 0.84rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-imp-report__authorized i { color: var(--yb-success); margin-top: 0.1rem; flex: none; }

/* A gated delta needs a reason too — but it is optional, so it must not shout like the
   full-load danger panel it sits next to. */
.yb-imp-reason {
    margin-top: 0.85rem;
    padding-top: 0.85rem;
    border-top: 1px dashed var(--yb-border);
}

/* ── The approval gate (#169) ─────────────────────────────────────────────────
   Sits above the upload form, because when it has something to say it IS the next
   instruction: an approved-but-unspent batch needs the same file uploaded again, and
   nothing about that is guessable from the form. */
.yb-imp-gate {
    margin-bottom: 1.25rem;
    padding: 1rem 1.15rem;
    border: 1px solid var(--yb-border);
    border-left: 3px solid var(--yb-border-strong);
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface-2);
}

.yb-imp-gate--ready {
    border-color: rgba(var(--yb-success-rgb), 0.3);
    border-left-color: var(--yb-success);
    background: rgba(var(--yb-success-rgb), 0.07);
}

.yb-imp-gate--waiting {
    border-color: rgba(var(--yb-warning-rgb), 0.32);
    border-left-color: var(--yb-warning);
    background: rgba(var(--yb-warning-rgb), 0.08);
}

.yb-imp-gate--mismatch {
    border-color: rgba(var(--yb-danger-rgb), 0.32);
    border-left-color: var(--yb-danger);
    background: rgba(var(--yb-danger-rgb), 0.07);
}

.yb-imp-gate__head {
    display: flex;
    align-items: flex-start;
    gap: 0.65rem;
}

.yb-imp-gate__head > i {
    flex: none;
    margin-top: 0.15rem;
    font-size: 1.15rem;
}

.yb-imp-gate--ready .yb-imp-gate__head > i { color: var(--yb-success); }
.yb-imp-gate--waiting .yb-imp-gate__head > i { color: var(--yb-warning); }
.yb-imp-gate--mismatch .yb-imp-gate__head > i { color: var(--yb-danger); }

.yb-imp-gate__title {
    margin: 0;
    font-size: 1rem;
    font-weight: 700;
    color: var(--yb-text);
}

.yb-imp-gate__sub {
    margin: 0.25rem 0 0;
    font-size: 0.85rem;
    line-height: 1.55;
    color: var(--yb-text-muted);
}

.yb-imp-gate__sub strong { color: var(--yb-text); }

/* The two-trip flow, drawn. Operators do not read "you must re-submit" in a paragraph;
   they read it as a step that is not ticked. */
.yb-imp-gate__steps {
    display: flex;
    flex-wrap: wrap;
    gap: 0.4rem 1.25rem;
    margin: 0.9rem 0 0;
    padding: 0;
    list-style: none;
    counter-reset: gate;
}

.yb-imp-gate__steps li {
    display: flex;
    align-items: center;
    gap: 0.45rem;
    font-size: 0.82rem;
    color: var(--yb-text-muted);
    counter-increment: gate;
}

.yb-imp-gate__steps li::before {
    content: counter(gate);
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex: none;
    width: 1.25rem;
    height: 1.25rem;
    font-size: 0.7rem;
    font-weight: 700;
    color: var(--yb-text-muted);
    background: var(--yb-surface);
    border: 1px solid var(--yb-border-strong);
    border-radius: var(--yb-radius-sm);
}

.yb-imp-gate__steps li.is-done { color: var(--yb-text-muted); }

.yb-imp-gate__steps li.is-done::before {
    content: "\F26E"; /* bi-check-lg */
    font-family: "bootstrap-icons";
    color: #fff;
    background: var(--yb-success);
    border-color: var(--yb-success);
}

.yb-imp-gate__steps li.is-now {
    font-weight: 700;
    color: var(--yb-text);
}

.yb-imp-gate__steps li.is-now::before {
    color: #fff;
    background: var(--yb-brand-600);
    border-color: var(--yb-brand-600);
}

.yb-imp-gate__note {
    display: flex;
    align-items: flex-start;
    gap: 0.5rem;
    margin-top: 0.9rem;
    padding-top: 0.75rem;
    border-top: 1px dashed var(--yb-border-strong);
    font-size: 0.82rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-imp-gate__note i { flex: none; margin-top: 0.1rem; color: var(--yb-warning); }
.yb-imp-gate__note strong { color: var(--yb-text); }
.yb-imp-gate--mismatch .yb-imp-gate__note i { color: var(--yb-danger); }

.yb-imp-gate__actions {
    display: flex;
    align-items: center;
    gap: 0.75rem;
    flex-wrap: wrap;
    margin-top: 0.9rem;
}

.yb-imp-gate__keep {
    font-size: 0.78rem;
    color: var(--yb-text-muted);
}

.yb-imp-counts {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(72px, 1fr));
    gap: 0.4rem;
    margin-top: 0.9rem;
}

.yb-imp-count {
    display: flex;
    flex-direction: column;
    align-items: center;
    padding: 0.5rem 0.35rem;
    border: 1px solid var(--yb-border);
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface-2);
}

.yb-imp-count__num { font-size: 1.25rem; font-weight: 700; line-height: 1; color: var(--yb-text); }

.yb-imp-count__cap {
    margin-top: 0.2rem;
    font-size: 0.64rem;
    text-transform: uppercase;
    letter-spacing: 0.05em;
    color: var(--yb-text-soft);
    text-align: center;
}

.yb-imp-count--ok .yb-imp-count__num { color: var(--yb-success); }
.yb-imp-count--warn .yb-imp-count__num { color: var(--yb-warning); }
.yb-imp-count--bad .yb-imp-count__num { color: var(--yb-danger); }

/* ── Row failures ────────────────────────────────────────────────── */
.yb-imp-rows { margin-top: 1rem; }

.yb-imp-rows__bar {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 0.5rem;
    flex-wrap: wrap;
    margin-bottom: 0.5rem;
}

.yb-imp-rows__title {
    margin: 0;
    font-size: 0.8rem;
    font-weight: 700;
    color: var(--yb-text);
}

.yb-imp-rows__export { padding: 0.3rem 0.7rem; font-size: 0.78rem; }

.yb-imp-rows__filter {
    display: flex;
    flex-wrap: wrap;
    width: 100%;
    margin-bottom: 0.5rem;
}

.yb-imp-rows__filter .yb-seg__btn { font-size: 0.74rem; padding: 0.25rem 0.55rem; }

.yb-imp-rows__scroll {
    max-height: 22rem;
    overflow: auto;
    border: 1px solid var(--yb-border);
    border-radius: var(--yb-radius-sm);
}

.yb-imp-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 0.8rem;
}

.yb-imp-table th {
    position: sticky;
    top: 0;
    z-index: 1;
    padding: 0.45rem 0.6rem;
    text-align: left;
    font-size: 0.68rem;
    text-transform: uppercase;
    letter-spacing: 0.05em;
    color: var(--yb-text-soft);
    background: var(--yb-surface-2);
    border-bottom: 1px solid var(--yb-border);
}

.yb-imp-table td {
    padding: 0.45rem 0.6rem;
    border-bottom: 1px solid var(--yb-border);
    color: var(--yb-text-muted);
    vertical-align: top;
}

.yb-imp-table tr:last-child td { border-bottom: 0; }

.yb-imp-table__line {
    font-variant-numeric: tabular-nums;
    font-weight: 700;
    color: var(--yb-text);
    white-space: nowrap;
}

.yb-imp-table__key { color: var(--yb-text); word-break: break-all; }
.yb-imp-table__why { line-height: 1.45; }

.yb-imp-col {
    display: inline-block;
    margin-right: 0.3rem;
    padding: 0 4px;
    border-radius: 3px;
    background: var(--yb-surface-sunken);
    color: var(--yb-text);
    font-size: 0.74rem;
}

.yb-imp-rowstatus {
    display: inline-block;
    padding: 2px 7px;
    border-radius: var(--yb-radius-sm);
    font-size: 0.68rem;
    font-weight: 700;
    text-transform: capitalize;
}

.yb-imp-rowstatus--ok { background: rgba(var(--yb-success-rgb), 0.12); color: var(--yb-success); }
.yb-imp-rowstatus--warn { background: rgba(var(--yb-warning-rgb), 0.14); color: var(--yb-warning); }
.yb-imp-rowstatus--bad { background: rgba(var(--yb-danger-rgb), 0.12); color: var(--yb-danger); }

/* A deactivation is a DELETION; a refusal is not. They must not look alike, so the deletion gets a
   solid fill rather than a tint — it is the only row status that removed something. (#168) */
.yb-imp-rowstatus--danger {
    background: var(--yb-danger);
    color: #fff;
}

/* ── Partially done ──────────────────────────────────────────────────
   A report can be `committed` AND carry a batch_error: the rows went in, but the destructive half of
   the load was refused. It is neither a success nor a failure, and it must not borrow the styling of
   either — hence its own amber identity. (#168) */
.yb-imp-report--partial { border-left-color: var(--yb-warning); }

.yb-imp-report--partial .yb-imp-report__badge {
    background: rgba(var(--yb-warning-rgb), 0.14);
    color: var(--yb-warning);
}

.yb-imp-count--danger .yb-imp-count__num { color: var(--yb-danger); }

.yb-imp-report__when {
    margin-left: auto;
    font-size: 0.74rem;
    color: var(--yb-text-soft);
    white-space: nowrap;
}

/* ── History ─────────────────────────────────────────────────────── */
.yb-imp-history__actions {
    display: flex;
    gap: 0.5rem;
    flex-wrap: wrap;
}

.yb-imp-runs {
    display: flex;
    flex-direction: column;
    gap: 0.45rem;
}

.yb-imp-run {
    display: flex;
    flex-direction: column;
    gap: 0.25rem;
    padding: 0.65rem 0.8rem;
    text-align: left;
    border: 1px solid var(--yb-border);
    border-left-width: 3px;
    border-radius: var(--yb-radius-sm);
    background: var(--yb-card);
    cursor: pointer;
    transition: border-color var(--yb-dur) var(--yb-ease), background-color var(--yb-dur) var(--yb-ease);
}

.yb-imp-run:hover { border-color: var(--yb-accent); }
.yb-imp-run.is-active { background: rgba(var(--yb-accent-rgb), 0.07); box-shadow: inset 0 0 0 1px var(--yb-accent); }

.yb-imp-run--ok { border-left-color: var(--yb-success); }
.yb-imp-run--partial { border-left-color: var(--yb-warning); }
.yb-imp-run--pending { border-left-color: var(--yb-warning); }
.yb-imp-run--bad { border-left-color: var(--yb-danger); }

.yb-imp-run__top {
    display: flex;
    align-items: center;
    gap: 0.4rem;
    flex-wrap: wrap;
}

.yb-imp-run__outcome { font-weight: 700; font-size: 0.84rem; color: var(--yb-text); }

.yb-imp-run__mode {
    padding: 1px 6px;
    border-radius: var(--yb-radius-sm);
    border: 1px solid var(--yb-border);
    background: var(--yb-surface-2);
    font-size: 0.66rem;
    font-weight: 700;
    text-transform: uppercase;
    letter-spacing: 0.05em;
    color: var(--yb-text-soft);
}

.yb-imp-run__when { margin-left: auto; font-size: 0.72rem; color: var(--yb-text-soft); white-space: nowrap; }
.yb-imp-run__file { font-size: 0.78rem; color: var(--yb-text-muted); word-break: break-all; }

.yb-imp-run__counts {
    display: flex;
    gap: 0.3rem;
    flex-wrap: wrap;
    font-size: 0.74rem;
    color: var(--yb-text-soft);
}

.yb-imp-run__counts .is-bad { color: var(--yb-danger); }
.yb-imp-run__counts .is-warn { color: var(--yb-warning); }
.yb-imp-run__counts .is-danger { color: var(--yb-danger); font-weight: 600; }

/* ══ ERP roster sync + held exits (TrilokAPI #144/#166 · TrilokWeb #185) ═══════

   Everything below is about ONE distinction that the existing import palette does not
   make: PROPOSED removal versus removal. Deactivated already owns --yb-danger. A
   proposal is not a deletion and must not borrow that weight — but it is not a
   harmless skip either, so it does not borrow --yb-warning's "nothing happened"
   reading. It gets the brand ramp: attention, not alarm.

   Tokens only — indigo brand, semantic danger/warning/success, --yb-radius-*,
   --yb-surface-*. Dark mode rides the [data-theme="dark"] token overrides, so there
   are no per-component dark rules here. */

/* ── ERP sync health card ───────────────────────────────────────────────────── */
.yb-erp-card {
    display: flex;
    align-items: flex-start;
    gap: 0.9rem;
    margin: 0 0 1.25rem;
    padding: 0.95rem 1.05rem;
    border: 1px solid var(--yb-border);
    border-left: 3px solid var(--yb-text-soft);
    border-radius: var(--yb-radius-md);
    background: var(--yb-surface);
    box-shadow: var(--yb-shadow-sm);
    /* The page shell centres its text (col-12 text-center on the layout); this is prose. */
    text-align: left;
}

.yb-erp-card__icon {
    flex: none;
    display: grid;
    place-items: center;
    width: 2.1rem;
    height: 2.1rem;
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface-2);
    color: var(--yb-text-soft);
    font-size: 1.05rem;
}

.yb-erp-card__body { flex: 1 1 auto; min-width: 0; }

.yb-erp-card__title {
    margin: 0 0 0.15rem;
    font-size: 0.95rem;
    font-weight: 600;
    color: var(--yb-text);
}

.yb-erp-card__note {
    margin: 0;
    font-size: 0.84rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-erp-card__actions { flex: none; align-self: center; }

/* Health states. The left rule carries the verdict, so the card reads at a glance in a
   column of other cards. */
.yb-erp-card--ok { border-left-color: var(--yb-success); }
.yb-erp-card--ok .yb-erp-card__icon { color: var(--yb-success); background: rgba(var(--yb-success-rgb), 0.1); }

.yb-erp-card--failing { border-left-color: var(--yb-warning); }
.yb-erp-card--failing .yb-erp-card__icon { color: var(--yb-warning); background: rgba(var(--yb-warning-rgb), 0.12); }

/* Stale, blocked and never-run are the three that mean the roster on screen is not the
   school's. They share the danger treatment because they share that consequence. */
.yb-erp-card--stale,
.yb-erp-card--blocked,
.yb-erp-card--never {
    border-left-color: var(--yb-danger);
    background: rgba(var(--yb-danger-rgb), 0.04);
}

.yb-erp-card--stale .yb-erp-card__icon,
.yb-erp-card--blocked .yb-erp-card__icon,
.yb-erp-card--never .yb-erp-card__icon {
    color: var(--yb-danger);
    background: rgba(var(--yb-danger-rgb), 0.1);
}

.yb-erp-blocked {
    display: flex;
    flex-direction: column;
    gap: 0.25rem;
    margin-top: 0.6rem;
    padding: 0.6rem 0.7rem;
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface-2);
    font-size: 0.82rem;
    line-height: 1.5;
}

.yb-erp-blocked__id { font-weight: 600; color: var(--yb-text); }
.yb-erp-blocked__id code { font-size: 0.8rem; }
.yb-erp-blocked__why { color: var(--yb-danger); }
.yb-erp-blocked__fix { color: var(--yb-text-muted); }

.yb-erp-card__link {
    display: inline-flex;
    align-items: center;
    gap: 0.35rem;
    margin-top: 0.55rem;
    font-size: 0.83rem;
    font-weight: 600;
    color: var(--yb-danger);
    text-decoration: none;
}

.yb-erp-card__link:hover { text-decoration: underline; }

.yb-erp-card__pending,
.yb-erp-card__outcome {
    margin: 0.5rem 0 0;
    font-size: 0.8rem;
    color: var(--yb-text-soft);
}

.yb-erp-card__outcome.is-bad { color: var(--yb-danger); }

/* ── Proposed exits on an import report ─────────────────────────────────────── */

/* The proposal treatment. Brand indigo, NOT danger: nobody has been removed. */
.yb-imp-count--proposed .yb-imp-count__num { color: var(--yb-brand-600); }

.yb-imp-rowstatus--proposed {
    background: rgba(31, 111, 229, 0.12);
    color: var(--yb-brand-600);
}

.yb-imp-report__exits {
    display: flex;
    align-items: flex-start;
    gap: 0.5rem;
    margin-top: 0.85rem;
    padding: 0.7rem 0.8rem;
    border: 1px solid rgba(31, 111, 229, 0.28);
    border-radius: var(--yb-radius-sm);
    background: rgba(31, 111, 229, 0.06);
    font-size: 0.84rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-imp-report__exits i { color: var(--yb-brand-600); margin-top: 0.1rem; flex: none; }
.yb-imp-report__exits strong { color: var(--yb-text); }
.yb-imp-report__exits a { margin-left: 0.25rem; font-weight: 600; }

/* Provenance — quiet by design. It is a record to be found later, not a thing to read
   on the way past. */
.yb-imp-report__provenance {
    display: flex;
    flex-wrap: wrap;
    gap: 0.35rem 1.1rem;
    margin-top: 0.7rem;
    font-size: 0.78rem;
    color: var(--yb-text-soft);
}

.yb-imp-report__provenance i { margin-right: 0.3rem; }
.yb-imp-report__provenance code { font-size: 0.76rem; }

/* ── Exit application review (#185) ─────────────────────────────────────────────
   The page's whole job is to make a list of names unavoidable before a decision is
   reachable. The visual weight follows that: the hero states what is being asked with
   a number in it, the two steps are numbered so that "approve" and "apply" cannot be
   read as one action, and a refusal from the rail is presented as an answer rather
   than an error. */
.yb-exit-hero {
    padding: 1.1rem 1.2rem;
    margin-bottom: 1.25rem;
    border: 1px solid rgba(var(--yb-danger-rgb), 0.28);
    border-left: 3px solid var(--yb-danger);
    border-radius: var(--yb-radius-md);
    background: rgba(var(--yb-danger-rgb), 0.05);
    /* The page shell centres its text (col-12 text-center on the layout); this is prose. */
    text-align: left;
}

.yb-exit-hero.is-decided {
    border-color: var(--yb-border);
    border-left-color: var(--yb-text-soft);
    background: var(--yb-surface-2);
}

.yb-exit-hero-head {
    display: flex;
    align-items: center;
    gap: 0.6rem;
    margin-bottom: 0.5rem;
}

.yb-exit-hero-head i { color: var(--yb-danger); font-size: 1.2rem; }
.yb-exit-hero.is-decided .yb-exit-hero-head i { color: var(--yb-text-soft); }

.yb-exit-hero-head h2 {
    margin: 0;
    font-size: 1.05rem;
    font-weight: 650;
    color: var(--yb-text);
}

/* The API's own ratio sentence. It already says the dangerous thing; give it room. */
.yb-exit-ratio {
    margin: 0 0 0.5rem;
    padding: 0.55rem 0.7rem;
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface);
    font-size: 0.86rem;
    font-weight: 600;
    color: var(--yb-text);
}

.yb-exit-caution {
    margin: 0 0 0.75rem;
    font-size: 0.84rem;
    line-height: 1.55;
    color: var(--yb-text-muted);
}

.yb-exit-meta {
    display: flex;
    flex-wrap: wrap;
    gap: 0.4rem 1.5rem;
    margin: 0;
    font-size: 0.79rem;
}

.yb-exit-meta div { display: flex; gap: 0.35rem; }
.yb-exit-meta dt { color: var(--yb-text-soft); font-weight: 500; }
.yb-exit-meta dd { margin: 0; color: var(--yb-text); font-weight: 600; }

.yb-exit-list-head {
    display: flex;
    align-items: baseline;
    flex-wrap: wrap;
    gap: 0.75rem;
    margin-bottom: 0.6rem;
    /* The page shell centres its text (col-12 text-center on the layout); this is prose. */
    text-align: left;
}

.yb-exit-list-head h3 {
    margin: 0;
    font-size: 0.95rem;
    font-weight: 650;
    color: var(--yb-text);
}

/* The stated count and the listed rows disagreeing is never smoothed over. */
.yb-exit-mismatch {
    display: inline-flex;
    align-items: center;
    gap: 0.35rem;
    padding: 0.25rem 0.55rem;
    border-radius: var(--yb-radius-sm);
    background: rgba(var(--yb-warning-rgb), 0.14);
    color: var(--yb-warning);
    font-size: 0.79rem;
    font-weight: 600;
}

/* Numbered steps. The numbers are the point — they are what stops "approve" reading as
   "remove". */
.yb-exit-step {
    display: flex;
    gap: 0.9rem;
    margin-top: 1.25rem;
    padding: 1rem 1.1rem;
    border: 1px solid var(--yb-border);
    border-radius: var(--yb-radius-md);
    background: var(--yb-surface);
    /* The page shell centres its text (col-12 text-center on the layout); this is prose. */
    text-align: left;
}

.yb-exit-step.is-apply {
    border-color: rgba(var(--yb-danger-rgb), 0.32);
    background: rgba(var(--yb-danger-rgb), 0.05);
}

.yb-exit-step-num {
    flex: none;
    display: grid;
    place-items: center;
    width: 1.75rem;
    height: 1.75rem;
    border-radius: var(--yb-radius-sm);
    background: var(--yb-brand-600);
    color: #fff;
    font-weight: 700;
    font-size: 0.85rem;
}

.yb-exit-step.is-apply .yb-exit-step-num { background: var(--yb-danger); }

.yb-exit-step-body h4 {
    margin: 0 0 0.2rem;
    font-size: 0.92rem;
    font-weight: 650;
    color: var(--yb-text);
}

.yb-exit-step-body p {
    margin: 0 0 0.7rem;
    font-size: 0.83rem;
    line-height: 1.5;
    color: var(--yb-text-muted);
}

.yb-exit-blocked {
    margin: 0.5rem 0 0;
    font-size: 0.8rem;
    color: var(--yb-text-soft);
}

/* The rail refusing is the feature working — it reads as an explanation with a next
   step, not as a failure. */
.yb-exit-refusal {
    margin-top: 1.25rem;
    padding: 1rem 1.1rem;
    border: 1px solid rgba(var(--yb-warning-rgb), 0.35);
    border-left: 3px solid var(--yb-warning);
    border-radius: var(--yb-radius-md);
    background: rgba(var(--yb-warning-rgb), 0.07);
    /* The page shell centres its text (col-12 text-center on the layout); this is prose. */
    text-align: left;
}

.yb-exit-refusal h4 {
    display: flex;
    align-items: center;
    gap: 0.45rem;
    margin: 0 0 0.5rem;
    font-size: 0.92rem;
    font-weight: 650;
    color: var(--yb-text);
}

.yb-exit-refusal h4 i { color: var(--yb-warning); }

.yb-exit-refusal p {
    margin: 0 0 0.65rem;
    font-size: 0.84rem;
    line-height: 1.55;
    color: var(--yb-text-muted);
}

.yb-exit-refusal-reason {
    padding: 0.55rem 0.7rem;
    border-radius: var(--yb-radius-sm);
    background: var(--yb-surface);
    color: var(--yb-text) !important;
    font-weight: 600;
}

.yb-exit-result { margin-top: 1.5rem; }
.yb-exit-result h4 { font-size: 0.92rem; font-weight: 650; margin-bottom: 0.5rem; }

/* ── Rollover windows (#166) ────────────────────────────────────────────────────
   Styled as a REASSURANCE, not a warning. The page's message is that a window
   narrows what may happen, so the explainer uses the success ramp — the opposite of
   what "override" styling would say. */
.yb-rollover-explainer {
    display: flex;
    gap: 0.9rem;
    margin-bottom: 1.25rem;
    padding: 1rem 1.1rem;
    border: 1px solid rgba(var(--yb-success-rgb), 0.3);
    border-left: 3px solid var(--yb-success);
    border-radius: var(--yb-radius-md);
    background: rgba(var(--yb-success-rgb), 0.06);
    /* The page shell centres its text (col-12 text-center on the layout); this is prose. */
    text-align: left;
    /* The page shell centres its text (col-12 text-center on the layout); this is prose. */
    text-align: left;
}

.yb-rollover-explainer > i { color: var(--yb-success); font-size: 1.2rem; margin-top: 0.1rem; }

.yb-rollover-explainer h3 {
    margin: 0 0 0.3rem;
    font-size: 0.95rem;
    font-weight: 650;
    color: var(--yb-text);
}

.yb-rollover-explainer p {
    margin: 0;
    font-size: 0.84rem;
    line-height: 1.55;
    color: var(--yb-text-muted);
}

.yb-rollover-cohort { font-weight: 600; color: var(--yb-text); }

.yb-rollover-state {
    display: inline-block;
    padding: 0.18rem 0.5rem;
    border-radius: var(--yb-radius-sm);
    font-size: 0.75rem;
    font-weight: 600;
}

.yb-rollover-state.is-open { background: rgba(var(--yb-success-rgb), 0.12); color: var(--yb-success); }
.yb-rollover-state.is-used { background: rgba(31, 111, 229, 0.12); color: var(--yb-brand-600); }
.yb-rollover-state.is-revoked { background: rgba(var(--yb-danger-rgb), 0.12); color: var(--yb-danger); }
/* Lapsed is deliberately the quietest: nothing happened, and nothing is wrong. */
.yb-rollover-state.is-lapsed { background: var(--yb-surface-2); color: var(--yb-text-soft); }

.yb-rollover-link { font-size: 0.8rem; font-weight: 600; }

.yb-field-hint {
    margin: 0.3rem 0 0;
    font-size: 0.78rem;
    line-height: 1.45;
    color: var(--yb-text-soft);
}

/* "Removes people" outranks the generic destructive flag in the approvals queue: this
   row does not sweep rows absent from a file, it removes a list of named children. */
.yb-gov-flag.is-exit {
    background: rgba(var(--yb-danger-rgb), 0.14);
    color: var(--yb-danger);
}

/* The apply outcome, stated in the exit page's own terms before the generic report. See the
   comment at its call site: "Imported" is the right headline for an upload and the wrong one for
   a run whose job is to remove people and which may correctly remove none. */
.yb-exit-outcome {
    margin: 0 0 0.75rem;
    padding: 0.6rem 0.75rem;
    border-radius: var(--yb-radius-sm);
    background: rgba(var(--yb-danger-rgb), 0.07);
    border-left: 3px solid var(--yb-danger);
    font-size: 0.86rem;
    line-height: 1.55;
    color: var(--yb-text-muted);
    text-align: left;
}

.yb-exit-outcome strong { color: var(--yb-text); }

/* Removing nobody is not a failure — it is the commonest honest outcome, and it should not wear
   the same red as a mass deactivation. */
.yb-exit-outcome.is-none {
    background: var(--yb-surface-2);
    border-left-color: var(--yb-text-soft);
}
