0
0
Fork 0
mirror of https://github.com/discourse/discourse.git synced 2026-08-05 21:16:17 +08:00
discourse/app/assets/stylesheets/admin/dashboard.scss
Martin Brennan 8faf71e3bb
FIX: Redirect upcoming change notifications to What's New when permanent (#41385)
When an upcoming change was automatically enabled, the notification
linked admins to the upcoming changes config page. But once a change
reaches permanent status it no longer appears there (that page only
lists experimental through stable) and instead surfaces on the What's
New page. So if the notification was left unread until the change became
permanent, clicking it dropped the admin on an empty filtered list.

This resolves the change's status at click time rather than baking it
into the notification. The permanent change names are now exposed to
staff via the site serializer, and the notification's link checks them:
if every referenced change is now permanent, it sends the admin to
What's New scrolled to that change's card; otherwise it keeps the
existing upcoming changes page where the still non-permanent changes
remain actionable.

To support the scroll, every What's New item now has a stable id anchor,
and the page accepts a scrollTo query param that scrolls to and briefly
highlights the matching card once the feed loads.
2026-07-03 15:28:21 +10:00

846 lines
14 KiB
SCSS
Vendored

@use "lib/viewport";
.admin-reports,
.dashboard-next {
&.admin-contents {
nav {
position: relative;
width: calc(100% + 10px);
padding-left: 10px;
margin-left: -10px;
margin-right: -10px;
}
}
}
.dashboard-next {
.nav {
display: flex;
margin: 0 0 2em 0;
border-bottom: 1px solid var(--content-border-color);
font-size: var(--font-up-1);
white-space: nowrap;
flex-wrap: nowrap;
overflow-x: auto;
// Fade-out for horizontal scroll nav
&::before {
content: "";
position: absolute;
width: 10px;
margin-left: -10px;
height: 100%;
background: linear-gradient(
to left,
rgb(var(--secondary-rgb), 1),
rgb(var(--secondary-rgb), 0)
);
}
&::after {
content: "";
position: absolute;
right: 0;
width: 30px;
height: 100%;
background: linear-gradient(
to right,
rgb(var(--secondary-rgb), 0),
rgb(var(--secondary-rgb), 1)
);
}
.navigation-link {
@include viewport.until(sm) {
padding: 0.4em;
font-size: var(--font-down-1);
}
.emoji {
margin-right: 0.5em;
@include viewport.until(sm) {
width: 1.3em;
height: 1.3em;
margin-right: 0;
}
}
}
}
.sections {
display: flex;
flex-direction: column;
}
.section-columns {
display: flex;
justify-content: space-between;
@include viewport.until(lg) {
flex-direction: column;
}
.section-column {
min-width: calc(50% - 0.5em);
max-width: 100%;
&:last-child {
margin-left: 0.5em;
}
&:first-child {
margin-right: 0.5em;
}
@include viewport.until(lg) {
min-width: 100%;
&:last-child {
order: 1;
}
&:first-child {
order: 2;
}
}
}
@include viewport.until(lg) {
.section-column:last-child,
.section-column:first-child {
margin: 0;
}
}
}
.section {
.section-title {
display: flex;
align-items: center;
justify-content: space-between;
border-bottom: 1px solid var(--content-border-color);
padding-bottom: 0.5em;
@media screen and (width <= 400px) {
flex-wrap: wrap;
}
h2 {
margin: 0 0.5em 0 0;
a {
color: var(--primary);
}
}
}
.section-body {
margin-top: 1em;
> p {
margin-top: 0;
}
}
}
.admin-report .header {
border: 0;
padding: 0;
margin-bottom: 1em;
}
.admin-report.description-in-tooltip .header {
.d-page-subheader {
.d-page-subheader__title-row {
margin-bottom: 0;
}
}
.fk-d-tooltip__trigger {
margin-left: 0.5em;
max-width: 20px;
}
}
.charts {
display: grid;
grid-template-columns: repeat(12, 1fr);
column-gap: 1em;
row-gap: 1em;
.admin-report {
grid-column: span 4;
&.consolidated-page-views,
&.site-traffic {
grid-column: span 12;
}
.header {
display: grid;
grid-template-areas: "title tooltip trend" "description description description";
grid-template-columns: auto 1fr;
.d-page-subheader {
display: contents;
}
.d-page-subheader__description {
grid-area: description;
margin-top: 0;
}
.trend {
grid-area: trend;
white-space: nowrap;
align-self: start;
}
}
}
@include viewport.until(lg) {
.admin-report {
grid-column: span 12;
}
}
.chart-canvas-container {
position: relative;
margin-left: -5px;
}
.site-traffic .chart-canvas-container {
height: 250px;
}
.chart-canvas {
width: 100%;
height: 100%;
}
}
.misc {
display: flex;
border: 1px solid var(--content-border-color);
.storage-stats,
.last-dashboard-update {
flex: 1 1 50%;
box-sizing: border-box;
margin: 1em 0;
padding: 0 1em;
}
.storage-stats {
display: flex;
flex-wrap: wrap;
justify-content: space-between;
border-right: 1px solid var(--content-border-color);
.backups,
.uploads {
flex: 1 1 100%;
}
.uploads p:last-of-type {
margin-bottom: 0;
}
}
@media screen and (width <= 400px) {
flex-wrap: wrap;
.storage-stats,
.last-dashboard-update {
flex: 1 1 100%;
text-align: left;
}
.last-dashboard-update {
display: block;
margin: 0 20px 20px 20px;
padding: 20px 0 0 0;
border-top: 1px solid var(--content-border-color);
border-left: none;
}
}
.last-dashboard-update {
text-align: center;
display: flex;
flex-direction: column;
justify-content: center;
div {
align-self: center;
h4 {
margin-bottom: 0;
}
}
}
}
.top-referred-topics {
margin-bottom: 2em;
}
.top-referred-topics,
.trending-search {
th:first-of-type {
text-align: left;
}
}
.period-chooser .period-chooser-header {
font-size: var(--font-down-2);
}
.dashboard-problems {
margin-bottom: 2em;
.problem-messages {
margin-bottom: 1em;
ul {
margin: 0 0 0 1.25em;
li.dashboard-problem {
padding: 0.5em 0.5em;
.notice {
display: flex;
justify-content: space-between;
align-items: center;
}
.message {
margin-right: var(--space-4);
}
}
}
}
.d-icon-triangle-exclamation {
color: var(--danger);
}
.actions {
margin: 1em 0 0 0;
display: flex;
align-items: center;
color: var(--primary-medium);
.btn {
margin-right: 1em;
}
}
}
}
.counters-list {
display: flex;
flex: 1 0 0px;
flex-direction: column;
.counters-header {
display: grid;
flex: 1 0 auto;
grid-template-columns: 33% repeat(auto-fit, minmax(20px, 1fr));
border: 1px solid var(--content-border-color);
border-bottom: 0;
font-weight: 700;
text-align: right;
align-items: center;
padding: 0.65em 0.25em;
}
.admin-report .chart__body {
border: 1px solid var(--content-border-color);
&:hover {
background-color: var(--primary-very-low);
}
}
.alert {
margin-bottom: 0;
}
.admin-report:not(:last-child) {
.chart__body {
border-bottom: 0;
}
.conditional-loading-section.is-loading {
border-bottom: 0;
}
}
.admin-report .conditional-loading-section.is-loading {
display: flex;
flex-direction: row;
padding: 0.5em 0.25em;
align-items: flex-start;
justify-content: flex-start;
border: 1px solid var(--content-border-color);
.title {
font-size: var(--font-0);
}
.spinner {
margin: 0;
width: 8px;
height: 8px;
margin-left: 0.5em;
}
}
.admin-report .chart__body .report-alert {
display: flex;
flex-direction: row;
padding: 0.5em 0.25em;
align-items: center;
text-align: left;
border: 0;
&:hover {
background-color: var(--primary-very-low);
}
.d-icon {
font-size: var(--font-up-1);
margin: 0 0.25em 0 0;
color: var(--primary-low-mid);
}
}
}
.activity-metrics {
margin-bottom: 2em;
@include viewport.until(sm) {
.counters-list {
font-size: var(--font-down-1);
}
}
}
.user-metrics {
display: flex;
flex-wrap: wrap;
justify-content: space-between;
flex-direction: column;
.dashboard-inline-table {
flex: 1 0 auto;
max-width: 95%;
}
.table-cell {
display: flex;
flex: 0 1 auto;
margin: 0 10px 5px 0;
padding: 1px;
border-radius: 10px;
.label {
display: flex;
align-items: center;
color: var(--primary);
justify-content: center;
border-radius: 9px 0 0 9px;
padding: 0 5px 0 8px;
.d-icon {
margin-right: 5px;
font-size: var(--font-down-1);
}
}
.value {
background: var(--secondary);
border-radius: 0 9px 9px 0;
padding: 0 8px 0 5px;
}
&.user-newuser {
.label {
color: var(--primary-high);
}
}
&.user-basic,
&.user-member {
background: var(--bronze);
.label {
color: var(--secondary);
}
}
&.user-regular {
background: var(--silver);
.label {
color: var(--secondary);
}
}
&.user-leader {
background: var(--gold);
.label {
color: var(--secondary);
}
}
}
}
.rtl .dashboard-next {
.section-column {
&:last-child {
margin-right: 1em;
margin-left: 0;
}
&:first-child {
margin-left: 1em;
margin-right: 0;
}
}
.user-metrics .table-cell {
margin: 0 0 5px 10px;
}
.table-cell {
.label {
border-radius: 0 9px 9px 0;
.d-icon {
margin-right: 0;
margin-left: 5px;
}
}
.value {
border-radius: 9px 0 0 9px;
padding: 0 5px 0 8px;
}
}
}
.users-by-trust-level,
.users-by-type {
margin-bottom: 2em;
}
.community-health.section {
margin-bottom: 2em;
}
.dashboard-moderation,
.dashboard-security {
.section-body {
margin-bottom: 2em;
}
.main-section {
display: grid;
grid-template-columns: repeat(12, 1fr);
column-gap: 1em;
row-gap: 1em;
> * {
grid-column: span 12;
}
.admin-dashboard-security-bottom-outlet,
.admin-dashboard-moderation-bottom-outlet {
display: grid;
grid-template-columns: repeat(12, 1fr);
column-gap: 1em;
row-gap: 1em;
}
}
.admin-report {
grid-column: span 12;
}
}
.dashboard-moderation {
.admin-dashboard-moderation-top {
display: grid;
grid-template-columns: repeat(12, 1fr);
column-gap: 1em;
row-gap: 1em;
}
}
.version-checks {
display: flex;
flex-wrap: wrap;
.section-title {
flex: 1 1 100%;
border-bottom: 1px solid var(--content-border-color);
padding-bottom: 0.5em;
}
h2 {
margin: 0;
}
}
.version-check {
display: flex;
flex: 1 1 50%;
flex-wrap: wrap;
align-items: flex-start;
align-self: flex-start;
justify-content: space-between;
padding-top: 1em;
.update-header {
flex: 1 1 100%;
@media screen and (width <= 650px) {
margin: 0;
}
tr {
border: none;
}
th {
background: transparent;
padding: 0;
}
}
h2 {
flex: 1 1 100%;
}
.version-number {
font-size: var(--font-up-2);
line-height: var(--line-height-small);
box-sizing: border-box;
font-weight: bold;
margin-bottom: 2em;
margin-right: 1em;
flex: 1 1 27%;
h3 {
flex: 1 0 auto;
margin: 0;
white-space: nowrap;
}
.commits-ahead {
font-size: var(--font-down-2-rem);
font-weight: normal;
color: var(--primary-medium);
cursor: help;
}
h4 {
font-size: var(--font-down-2);
margin-bottom: 0.5em;
}
.version-links {
display: flex;
flex-wrap: wrap;
gap: var(--space-4);
margin-top: var(--space-1);
a {
display: inline-flex;
align-items: center;
gap: var(--space-1);
font-size: var(--font-down-3);
font-weight: normal;
white-space: nowrap;
}
}
}
.version-status {
display: flex;
align-items: center;
margin: 0 0 1em 0;
flex: 1 1 24%;
box-sizing: border-box;
padding-right: 20px;
min-width: 250px;
@include viewport.until(lg) {
max-width: unset;
}
.face {
margin: 0 0.75em 0 0;
font-size: var(--font-up-3);
}
}
&.critical .version-notes .normal-note {
display: none;
}
&.normal .version-notes .critical-note {
display: none;
}
.face .fa {
font-size: var(--font-up-4);
}
.up-to-date {
color: var(--success);
}
.updates-available {
color: var(--danger);
}
.critical-updates-available {
color: var(--danger);
}
}
.update-nag {
.d-icon {
font-size: var(--font-up-3);
}
}
.dashboard-next.general {
display: flex;
flex-direction: column;
}
.dashboard-new-features {
&.ordered-first {
order: -1;
}
&:not(.ordered-first) {
.new-features-dismiss {
display: none;
}
}
.section-footer {
margin: 1.5em;
display: flex;
justify-content: flex-end;
align-items: center;
.btn {
margin-left: 1em;
}
}
}
.whats-new,
.dashboard {
.admin-config-area-card__title {
font-size: var(--font-up-1);
margin-bottom: 1em;
}
.admin-new-feature-item__learn-more {
display: inline-block;
}
}
.admin-new-features {
&__group {
margin-bottom: 1em;
}
}
.admin-new-feature-item__body {
display: flex;
justify-content: space-between;
margin-bottom: 1em;
.d-toggle-switch {
margin-left: 1em;
align-items: flex-start;
}
p {
margin-top: 0;
}
}
.admin-new-feature-item__screenshot {
margin-bottom: 1em;
width: 100%;
}
.admin-new-feature-item__tooltip-header {
font-weight: bold;
}
.admin-new-feature-item__tooltip-content {
margin-top: 0.5em;
}
.admin-new-feature-item {
display: flex;
align-items: flex-start;
border-bottom: 1px solid var(--content-border-color);
transition: background-color 0.5s ease;
&.--highlighted {
background-color: var(--highlight-low);
}
&:not(:first-child) {
margin-top: var(--space-4);
}
&:last-child {
border-bottom: none;
}
&__new-feature-emoji {
font-size: 1.2em;
padding-left: 0;
padding-right: 0.5em;
}
&__content {
width: 100%;
}
&__header {
display: flex;
align-items: baseline;
font-weight: bold;
margin-bottom: 0.5em;
}
&__new-feature-version {
margin-left: auto;
color: var(--primary-low-mid);
@include viewport.until(sm) {
font-size: var(--font-down-1);
}
}
@include viewport.until(sm) {
h3 {
margin-right: 0.5em;
}
}
}