providers: allow previewing mappings for other users (#8297)
* rework access check to do better validation
Signed-off-by: Jens Langhammer <jens@goauthentik.io>
* providers: allow previewing mappings for other users
Signed-off-by: Jens Langhammer <jens@goauthentik.io>
* fix ui
Signed-off-by: Jens Langhammer <jens@goauthentik.io>
* Revert "rework access check to do better validation"
This reverts commit 81077a7e7b.
* prepare
Signed-off-by: Jens Langhammer <jens@goauthentik.io>
---------
Signed-off-by: Jens Langhammer <jens@goauthentik.io>
This commit is contained in:
@ -1,5 +1,6 @@
|
||||
import "@goauthentik/admin/providers/RelatedApplicationButton";
|
||||
import "@goauthentik/admin/providers/oauth2/OAuth2ProviderForm";
|
||||
import renderDescriptionList from "@goauthentik/app/components/DescriptionList";
|
||||
import { DEFAULT_CONFIG } from "@goauthentik/common/api/config";
|
||||
import { EVENT_REFRESH } from "@goauthentik/common/constants";
|
||||
import { convertToTitle } from "@goauthentik/common/utils";
|
||||
@ -30,11 +31,14 @@ import PFGrid from "@patternfly/patternfly/layouts/Grid/grid.css";
|
||||
import PFBase from "@patternfly/patternfly/patternfly-base.css";
|
||||
|
||||
import {
|
||||
CoreApi,
|
||||
CoreUsersListRequest,
|
||||
OAuth2Provider,
|
||||
OAuth2ProviderSetupURLs,
|
||||
PropertyMappingPreview,
|
||||
ProvidersApi,
|
||||
RbacPermissionsAssignedByUsersListModelEnum,
|
||||
User,
|
||||
} from "@goauthentik/api";
|
||||
|
||||
@customElement("ak-provider-oauth2-view")
|
||||
@ -59,6 +63,9 @@ export class OAuth2ProviderViewPage extends AKElement {
|
||||
@state()
|
||||
preview?: PropertyMappingPreview;
|
||||
|
||||
@state()
|
||||
previewUser?: User;
|
||||
|
||||
static get styles(): CSSResult[] {
|
||||
return [
|
||||
PFBase,
|
||||
@ -83,6 +90,15 @@ export class OAuth2ProviderViewPage extends AKElement {
|
||||
});
|
||||
}
|
||||
|
||||
fetchPreview(): void {
|
||||
new ProvidersApi(DEFAULT_CONFIG)
|
||||
.providersOauth2PreviewUserRetrieve({
|
||||
id: this.provider?.pk || 0,
|
||||
forUser: this.previewUser?.pk,
|
||||
})
|
||||
.then((preview) => (this.preview = preview));
|
||||
}
|
||||
|
||||
render(): TemplateResult {
|
||||
if (!this.provider) {
|
||||
return html``;
|
||||
@ -107,11 +123,7 @@ export class OAuth2ProviderViewPage extends AKElement {
|
||||
slot="page-preview"
|
||||
data-tab-title="${msg("Preview")}"
|
||||
@activate=${() => {
|
||||
new ProvidersApi(DEFAULT_CONFIG)
|
||||
.providersOauth2PreviewUserRetrieve({
|
||||
id: this.provider?.pk || 0,
|
||||
})
|
||||
.then((preview) => (this.preview = preview));
|
||||
this.fetchPreview();
|
||||
}}
|
||||
>
|
||||
${this.renderTabPreview()}
|
||||
@ -354,8 +366,50 @@ export class OAuth2ProviderViewPage extends AKElement {
|
||||
class="pf-c-page__main-section pf-m-no-padding-mobile pf-l-grid pf-m-gutter"
|
||||
>
|
||||
<div class="pf-c-card">
|
||||
<div class="pf-c-card__title">
|
||||
${msg("Example JWT payload (for currently authenticated user)")}
|
||||
<div class="pf-c-card__title">${msg("JWT payload")}</div>
|
||||
<div class="pf-c-card__body">
|
||||
${renderDescriptionList(
|
||||
[
|
||||
[
|
||||
msg("Preview for user"),
|
||||
html`
|
||||
<ak-search-select
|
||||
.fetchObjects=${async (query?: string): Promise<User[]> => {
|
||||
const args: CoreUsersListRequest = {
|
||||
ordering: "username",
|
||||
};
|
||||
if (query !== undefined) {
|
||||
args.search = query;
|
||||
}
|
||||
const users = await new CoreApi(
|
||||
DEFAULT_CONFIG,
|
||||
).coreUsersList(args);
|
||||
return users.results;
|
||||
}}
|
||||
.renderElement=${(user: User): string => {
|
||||
return user.username;
|
||||
}}
|
||||
.renderDescription=${(user: User): TemplateResult => {
|
||||
return html`${user.name}`;
|
||||
}}
|
||||
.value=${(user: User | undefined): number | undefined => {
|
||||
return user?.pk;
|
||||
}}
|
||||
.selected=${(user: User): boolean => {
|
||||
return user.pk === this.previewUser?.pk;
|
||||
}}
|
||||
?blankable=${true}
|
||||
@ak-change=${(ev: CustomEvent) => {
|
||||
this.previewUser = ev.detail.value;
|
||||
this.fetchPreview();
|
||||
}}
|
||||
>
|
||||
</ak-search-select>
|
||||
`,
|
||||
],
|
||||
],
|
||||
{ horizontal: true },
|
||||
)}
|
||||
</div>
|
||||
<div class="pf-c-card__body">
|
||||
${this.preview
|
||||
|
||||
@ -1,5 +1,6 @@
|
||||
import "@goauthentik/admin/providers/RelatedApplicationButton";
|
||||
import "@goauthentik/admin/providers/saml/SAMLProviderForm";
|
||||
import renderDescriptionList from "@goauthentik/app/components/DescriptionList";
|
||||
import "@goauthentik/app/elements/rbac/ObjectPermissionsPage";
|
||||
import { DEFAULT_CONFIG } from "@goauthentik/common/api/config";
|
||||
import { EVENT_REFRESH } from "@goauthentik/common/constants";
|
||||
@ -34,11 +35,14 @@ import PFBase from "@patternfly/patternfly/patternfly-base.css";
|
||||
|
||||
import {
|
||||
CertificateKeyPair,
|
||||
CoreApi,
|
||||
CoreUsersListRequest,
|
||||
CryptoApi,
|
||||
ProvidersApi,
|
||||
RbacPermissionsAssignedByUsersListModelEnum,
|
||||
SAMLMetadata,
|
||||
SAMLProvider,
|
||||
User,
|
||||
} from "@goauthentik/api";
|
||||
|
||||
interface SAMLPreviewAttribute {
|
||||
@ -96,6 +100,9 @@ export class SAMLProviderViewPage extends AKElement {
|
||||
@state()
|
||||
verifier?: CertificateKeyPair;
|
||||
|
||||
@state()
|
||||
previewUser?: User;
|
||||
|
||||
static get styles(): CSSResult[] {
|
||||
return [
|
||||
PFBase,
|
||||
@ -120,6 +127,17 @@ export class SAMLProviderViewPage extends AKElement {
|
||||
});
|
||||
}
|
||||
|
||||
fetchPreview(): void {
|
||||
new ProvidersApi(DEFAULT_CONFIG)
|
||||
.providersSamlPreviewUserRetrieve({
|
||||
id: this.provider?.pk || 0,
|
||||
forUser: this.previewUser?.pk,
|
||||
})
|
||||
.then((preview) => {
|
||||
this.preview = preview.preview as SAMLPreviewAttribute;
|
||||
});
|
||||
}
|
||||
|
||||
renderRelatedObjects(): TemplateResult {
|
||||
const relatedObjects = [];
|
||||
if (this.provider?.assignedApplicationName) {
|
||||
@ -203,13 +221,7 @@ export class SAMLProviderViewPage extends AKElement {
|
||||
slot="page-preview"
|
||||
data-tab-title="${msg("Preview")}"
|
||||
@activate=${() => {
|
||||
new ProvidersApi(DEFAULT_CONFIG)
|
||||
.providersSamlPreviewUserRetrieve({
|
||||
id: this.provider?.pk || 0,
|
||||
})
|
||||
.then((preview) => {
|
||||
this.preview = preview.preview as SAMLPreviewAttribute;
|
||||
});
|
||||
this.fetchPreview();
|
||||
}}
|
||||
>
|
||||
${this.renderTabPreview()}
|
||||
@ -494,6 +506,47 @@ export class SAMLProviderViewPage extends AKElement {
|
||||
>
|
||||
<div class="pf-c-card">
|
||||
<div class="pf-c-card__title">${msg("Example SAML attributes")}</div>
|
||||
<div class="pf-c-card__body">
|
||||
${renderDescriptionList([
|
||||
[
|
||||
"Preview for user",
|
||||
html`
|
||||
<ak-search-select
|
||||
.fetchObjects=${async (query?: string): Promise<User[]> => {
|
||||
const args: CoreUsersListRequest = {
|
||||
ordering: "username",
|
||||
};
|
||||
if (query !== undefined) {
|
||||
args.search = query;
|
||||
}
|
||||
const users = await new CoreApi(
|
||||
DEFAULT_CONFIG,
|
||||
).coreUsersList(args);
|
||||
return users.results;
|
||||
}}
|
||||
.renderElement=${(user: User): string => {
|
||||
return user.username;
|
||||
}}
|
||||
.renderDescription=${(user: User): TemplateResult => {
|
||||
return html`${user.name}`;
|
||||
}}
|
||||
.value=${(user: User | undefined): number | undefined => {
|
||||
return user?.pk;
|
||||
}}
|
||||
.selected=${(user: User): boolean => {
|
||||
return user.pk === this.previewUser?.pk;
|
||||
}}
|
||||
?blankable=${true}
|
||||
@ak-change=${(ev: CustomEvent) => {
|
||||
this.previewUser = ev.detail.value;
|
||||
this.fetchPreview();
|
||||
}}
|
||||
>
|
||||
</ak-search-select>
|
||||
`,
|
||||
],
|
||||
])}
|
||||
</div>
|
||||
<div class="pf-c-card__body">
|
||||
<dl class="pf-c-description-list pf-m-2-col-on-lg">
|
||||
<div class="pf-c-description-list__group">
|
||||
@ -519,11 +572,7 @@ export class SAMLProviderViewPage extends AKElement {
|
||||
</dt>
|
||||
<dd class="pf-c-description-list__description">
|
||||
<div class="pf-c-description-list__text">
|
||||
<ul class="pf-c-list">
|
||||
${attr.Value.map((value) => {
|
||||
return html` <li><pre>${value}</pre></li> `;
|
||||
})}
|
||||
</ul>
|
||||
<ul class="pf-c-list"></ul>
|
||||
</div>
|
||||
</dd>
|
||||
</div>`;
|
||||
|
||||
@ -1,3 +1,5 @@
|
||||
import { first } from "@goauthentik/app/common/utils";
|
||||
|
||||
import { TemplateResult, html, nothing } from "lit";
|
||||
import { classMap } from "lit/directives/class-map.js";
|
||||
import { map } from "lit/directives/map.js";
|
||||
@ -7,10 +9,10 @@ export type DescriptionPair = [string, DescriptionDesc];
|
||||
export type DescriptionRecord = { term: string; desc: DescriptionDesc };
|
||||
|
||||
interface DescriptionConfig {
|
||||
horizontal: boolean;
|
||||
compact: boolean;
|
||||
twocolumn: boolean;
|
||||
threecolumn: boolean;
|
||||
horizontal?: boolean;
|
||||
compact?: boolean;
|
||||
twocolumn?: boolean;
|
||||
threecolumn?: boolean;
|
||||
}
|
||||
|
||||
const isDescriptionRecordCollection = (v: Array<unknown>): v is DescriptionRecord[] =>
|
||||
@ -78,10 +80,10 @@ export function renderDescriptionList(
|
||||
) {
|
||||
const checkedTerms = alignTermType(terms);
|
||||
const classes = classMap({
|
||||
"pf-m-horizontal": config.horizontal,
|
||||
"pf-m-compact": config.compact,
|
||||
"pf-m-2-col-on-lg": config.twocolumn,
|
||||
"pf-m-3-col-on-lg": config.threecolumn,
|
||||
"pf-m-horizontal": first(config.horizontal, false),
|
||||
"pf-m-compact": first(config.compact, false),
|
||||
"pf-m-2-col-on-lg": first(config.twocolumn, false),
|
||||
"pf-m-3-col-on-lg": first(config.threecolumn, false),
|
||||
});
|
||||
|
||||
return html`
|
||||
|
||||
@ -168,6 +168,7 @@ export abstract class AKChart<T> extends AKElement {
|
||||
getOptions(): ChartOptions {
|
||||
return {
|
||||
maintainAspectRatio: false,
|
||||
responsive: true,
|
||||
scales: {
|
||||
x: {
|
||||
type: "time",
|
||||
|
||||
Reference in New Issue
Block a user