web: add sentry, add spinner button as base for action button
This commit is contained in:
parent
2417d5a59e
commit
a8dad2e393
|
@ -30,3 +30,5 @@ values =
|
||||||
[bumpversion:file:passbook/__init__.py]
|
[bumpversion:file:passbook/__init__.py]
|
||||||
|
|
||||||
[bumpversion:file:proxy/pkg/version.go]
|
[bumpversion:file:proxy/pkg/version.go]
|
||||||
|
|
||||||
|
[bumpversion:file:web/src/constants.ts]
|
||||||
|
|
|
@ -15,6 +15,10 @@ class ConfigSerializer(Serializer):
|
||||||
branding_logo = ReadOnlyField()
|
branding_logo = ReadOnlyField()
|
||||||
branding_title = ReadOnlyField()
|
branding_title = ReadOnlyField()
|
||||||
|
|
||||||
|
error_reporting_enabled = ReadOnlyField()
|
||||||
|
error_reporting_environment = ReadOnlyField()
|
||||||
|
error_reporting_send_pii = ReadOnlyField()
|
||||||
|
|
||||||
def create(self, request: Request) -> Response:
|
def create(self, request: Request) -> Response:
|
||||||
raise NotImplementedError
|
raise NotImplementedError
|
||||||
|
|
||||||
|
@ -34,6 +38,9 @@ class ConfigsViewSet(ViewSet):
|
||||||
{
|
{
|
||||||
"branding_logo": CONFIG.y("passbook.branding.logo"),
|
"branding_logo": CONFIG.y("passbook.branding.logo"),
|
||||||
"branding_title": CONFIG.y("passbook.branding.title"),
|
"branding_title": CONFIG.y("passbook.branding.title"),
|
||||||
|
"error_reporting_enabled": CONFIG.y("error_reporting.enabled"),
|
||||||
|
"error_reporting_environment": CONFIG.y("error_reporting.environment"),
|
||||||
|
"error_reporting_send_pii": CONFIG.y("error_reporting.send_pii"),
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
return Response(config.data)
|
return Response(config.data)
|
||||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -96,6 +96,117 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"@sentry/browser": {
|
||||||
|
"version": "5.27.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/@sentry/browser/-/browser-5.27.6.tgz",
|
||||||
|
"integrity": "sha512-pqrojE2ZmLUVz7l/ogtogK0+M2pK3bigYm0fja7vG7F7kXnCAwqAHDYfkFXEvFI8WvNwH+niy28lSoV95lnm0Q==",
|
||||||
|
"requires": {
|
||||||
|
"@sentry/core": "5.27.6",
|
||||||
|
"@sentry/types": "5.27.6",
|
||||||
|
"@sentry/utils": "5.27.6",
|
||||||
|
"tslib": "^1.9.3"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"tslib": {
|
||||||
|
"version": "1.14.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
|
||||||
|
"integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg=="
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@sentry/core": {
|
||||||
|
"version": "5.27.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/@sentry/core/-/core-5.27.6.tgz",
|
||||||
|
"integrity": "sha512-izCS5iyc6HAfpW1AsGXLAKetx82C1Sq1siAh97tOlSK58PVJAEH/WMiej9WuZJxCDTOtj94QtoLflssrZyAtFg==",
|
||||||
|
"requires": {
|
||||||
|
"@sentry/hub": "5.27.6",
|
||||||
|
"@sentry/minimal": "5.27.6",
|
||||||
|
"@sentry/types": "5.27.6",
|
||||||
|
"@sentry/utils": "5.27.6",
|
||||||
|
"tslib": "^1.9.3"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"tslib": {
|
||||||
|
"version": "1.14.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
|
||||||
|
"integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg=="
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@sentry/hub": {
|
||||||
|
"version": "5.27.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/@sentry/hub/-/hub-5.27.6.tgz",
|
||||||
|
"integrity": "sha512-bOMky3iu7zEghSaWmTayfme5tCpUok841qDCGxGKuyAtOhBDsgGNS/ApNEEDF2fyX0oo4G1cHYPWhX90ZFf/xA==",
|
||||||
|
"requires": {
|
||||||
|
"@sentry/types": "5.27.6",
|
||||||
|
"@sentry/utils": "5.27.6",
|
||||||
|
"tslib": "^1.9.3"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"tslib": {
|
||||||
|
"version": "1.14.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
|
||||||
|
"integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg=="
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@sentry/minimal": {
|
||||||
|
"version": "5.27.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/@sentry/minimal/-/minimal-5.27.6.tgz",
|
||||||
|
"integrity": "sha512-pKhzVQX9nL4m1dcnb2i2Y47IWVNs+K3wiYLgCB9hl9+ApxppfOc+fquiFoCloST3IuaD4yly2TtbOJgAMWcMxQ==",
|
||||||
|
"requires": {
|
||||||
|
"@sentry/hub": "5.27.6",
|
||||||
|
"@sentry/types": "5.27.6",
|
||||||
|
"tslib": "^1.9.3"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"tslib": {
|
||||||
|
"version": "1.14.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
|
||||||
|
"integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg=="
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@sentry/tracing": {
|
||||||
|
"version": "5.27.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/@sentry/tracing/-/tracing-5.27.6.tgz",
|
||||||
|
"integrity": "sha512-ms3vprEId+hi8hcqtf8weqsNGASaDXAZzIOT4g2gASGpwLb5hLuScpM8z6Yhu5FGjb8DektlW5OrXJSsStIozw==",
|
||||||
|
"requires": {
|
||||||
|
"@sentry/hub": "5.27.6",
|
||||||
|
"@sentry/minimal": "5.27.6",
|
||||||
|
"@sentry/types": "5.27.6",
|
||||||
|
"@sentry/utils": "5.27.6",
|
||||||
|
"tslib": "^1.9.3"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"tslib": {
|
||||||
|
"version": "1.14.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
|
||||||
|
"integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg=="
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"@sentry/types": {
|
||||||
|
"version": "5.27.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/@sentry/types/-/types-5.27.6.tgz",
|
||||||
|
"integrity": "sha512-XOW9W8DrMk++4Hk7gWi9o5VR0o/GrqGfTKyFsHSIjqt2hL6kiMPvKeb2Hhmp7Iq37N2bDmRdWpM5m+68S2Jk6w=="
|
||||||
|
},
|
||||||
|
"@sentry/utils": {
|
||||||
|
"version": "5.27.6",
|
||||||
|
"resolved": "https://registry.npmjs.org/@sentry/utils/-/utils-5.27.6.tgz",
|
||||||
|
"integrity": "sha512-/QMVLv+zrTfiIj2PU+SodSbSzD5MmamMOaljkDsRIVsj6gpkm1/VG1g2+40TZ0FbQ4hCW2F+iR7cnqzZBNmchA==",
|
||||||
|
"requires": {
|
||||||
|
"@sentry/types": "5.27.6",
|
||||||
|
"tslib": "^1.9.3"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"tslib": {
|
||||||
|
"version": "1.14.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/tslib/-/tslib-1.14.1.tgz",
|
||||||
|
"integrity": "sha512-Xni35NKzjgMrwevysHTCArtLDpPvye8zV/0E4EyYn43P7/7qvQwPh9BGkHewbMulVntbigmcT7rdX3BNo9wRJg=="
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"@types/chart.js": {
|
"@types/chart.js": {
|
||||||
"version": "2.9.28",
|
"version": "2.9.28",
|
||||||
"resolved": "https://registry.npmjs.org/@types/chart.js/-/chart.js-2.9.28.tgz",
|
"resolved": "https://registry.npmjs.org/@types/chart.js/-/chart.js-2.9.28.tgz",
|
||||||
|
|
|
@ -8,6 +8,8 @@
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@fortawesome/fontawesome-free": "^5.15.1",
|
"@fortawesome/fontawesome-free": "^5.15.1",
|
||||||
"@patternfly/patternfly": "^4.65.6",
|
"@patternfly/patternfly": "^4.65.6",
|
||||||
|
"@sentry/browser": "^5.27.6",
|
||||||
|
"@sentry/tracing": "^5.27.6",
|
||||||
"@types/chart.js": "^2.9.28",
|
"@types/chart.js": "^2.9.28",
|
||||||
"@types/codemirror": "0.0.100",
|
"@types/codemirror": "0.0.100",
|
||||||
"chart.js": "^2.9.4",
|
"chart.js": "^2.9.4",
|
||||||
|
|
|
@ -1,10 +1,31 @@
|
||||||
import { DefaultClient } from "./client";
|
import { DefaultClient } from "./client";
|
||||||
|
import * as Sentry from "@sentry/browser";
|
||||||
|
import { Integrations } from "@sentry/tracing";
|
||||||
|
import { VERSION } from "../constants";
|
||||||
|
|
||||||
export class Config {
|
export class Config {
|
||||||
branding_logo?: string;
|
branding_logo?: string;
|
||||||
branding_title?: string;
|
branding_title?: string;
|
||||||
|
|
||||||
|
error_reporting_enabled?: boolean;
|
||||||
|
error_reporting_environment?: string;
|
||||||
|
error_reporting_send_pii?: boolean;
|
||||||
|
|
||||||
static get(): Promise<Config> {
|
static get(): Promise<Config> {
|
||||||
return DefaultClient.fetch<Config>(["root", "config"]);
|
return DefaultClient.fetch<Config>(["root", "config"])
|
||||||
|
.then((config) => {
|
||||||
|
if (config.error_reporting_enabled) {
|
||||||
|
Sentry.init({
|
||||||
|
dsn: "https://33cdbcb23f8b436dbe0ee06847410b67@sentry.beryju.org/3",
|
||||||
|
release: `passbook@${VERSION}`,
|
||||||
|
integrations: [new Integrations.BrowserTracing()],
|
||||||
|
tracesSampleRate: 1.0,
|
||||||
|
environment: config.error_reporting_environment,
|
||||||
|
sendDefaultPii: config.error_reporting_send_pii,
|
||||||
|
});
|
||||||
|
console.debug(`passbook/config: Sentry enabled.`);
|
||||||
|
}
|
||||||
|
return config;
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,3 +28,4 @@ export const ColorStyles = css`
|
||||||
background-color: var(--pf-global--danger-color--100);
|
background-color: var(--pf-global--danger-color--100);
|
||||||
}
|
}
|
||||||
`;
|
`;
|
||||||
|
export const VERSION = "0.12.11-stable";
|
||||||
|
|
|
@ -1,64 +1,13 @@
|
||||||
import { getCookie } from "../utils";
|
import { getCookie } from "../utils";
|
||||||
import { css, customElement, html, LitElement, property } from "lit-element";
|
import { customElement, html, property } from "lit-element";
|
||||||
// @ts-ignore
|
import { ERROR_CLASS, SUCCESS_CLASS } from "../constants";
|
||||||
import GlobalsStyle from "@patternfly/patternfly/base/patternfly-globals.css";
|
import { SpinnerButton } from "./SpinnerButton";
|
||||||
// @ts-ignore
|
|
||||||
import ButtonStyle from "@patternfly/patternfly/components/Button/button.css";
|
|
||||||
// @ts-ignore
|
|
||||||
import SpinnerStyle from "@patternfly/patternfly/components/Spinner/spinner.css";
|
|
||||||
import {
|
|
||||||
ColorStyles,
|
|
||||||
ERROR_CLASS,
|
|
||||||
PRIMARY_CLASS,
|
|
||||||
PROGRESS_CLASS,
|
|
||||||
SUCCESS_CLASS,
|
|
||||||
} from "../constants";
|
|
||||||
|
|
||||||
@customElement("pb-action-button")
|
@customElement("pb-action-button")
|
||||||
export class ActionButton extends LitElement {
|
export class ActionButton extends SpinnerButton {
|
||||||
@property()
|
@property()
|
||||||
url: string = "";
|
url: string = "";
|
||||||
|
|
||||||
@property()
|
|
||||||
isRunning = false;
|
|
||||||
|
|
||||||
static get styles() {
|
|
||||||
return [
|
|
||||||
GlobalsStyle,
|
|
||||||
ButtonStyle,
|
|
||||||
SpinnerStyle,
|
|
||||||
ColorStyles,
|
|
||||||
css`
|
|
||||||
button {
|
|
||||||
/* Have to use !important here, as buttons with pf-m-progress have transition already */
|
|
||||||
transition: all var(--pf-c-button--m-progress--TransitionDuration) ease 0s !important;
|
|
||||||
}
|
|
||||||
`,
|
|
||||||
];
|
|
||||||
}
|
|
||||||
|
|
||||||
constructor() {
|
|
||||||
super();
|
|
||||||
this.classList.add(PRIMARY_CLASS);
|
|
||||||
}
|
|
||||||
|
|
||||||
setLoading() {
|
|
||||||
this.isRunning = true;
|
|
||||||
this.classList.add(PROGRESS_CLASS);
|
|
||||||
this.requestUpdate();
|
|
||||||
}
|
|
||||||
|
|
||||||
setDone(statusClass: string) {
|
|
||||||
this.isRunning = false;
|
|
||||||
this.classList.remove(PROGRESS_CLASS);
|
|
||||||
this.classList.replace(PRIMARY_CLASS, statusClass);
|
|
||||||
this.requestUpdate();
|
|
||||||
setTimeout(() => {
|
|
||||||
this.classList.replace(statusClass, PRIMARY_CLASS);
|
|
||||||
this.requestUpdate();
|
|
||||||
}, 1000);
|
|
||||||
}
|
|
||||||
|
|
||||||
callAction() {
|
callAction() {
|
||||||
if (this.isRunning === true) {
|
if (this.isRunning === true) {
|
||||||
return;
|
return;
|
||||||
|
@ -80,26 +29,4 @@ export class ActionButton extends LitElement {
|
||||||
this.setDone(ERROR_CLASS);
|
this.setDone(ERROR_CLASS);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
render() {
|
|
||||||
return html`<button
|
|
||||||
class="pf-c-button pf-m-progress ${this.classList.toString()}"
|
|
||||||
@click=${() => this.callAction()}
|
|
||||||
>
|
|
||||||
${this.isRunning
|
|
||||||
? html` <span class="pf-c-button__progress">
|
|
||||||
<span
|
|
||||||
class="pf-c-spinner pf-m-md"
|
|
||||||
role="progressbar"
|
|
||||||
aria-valuetext="Loading..."
|
|
||||||
>
|
|
||||||
<span class="pf-c-spinner__clipper"></span>
|
|
||||||
<span class="pf-c-spinner__lead-ball"></span>
|
|
||||||
<span class="pf-c-spinner__tail-ball"></span>
|
|
||||||
</span>
|
|
||||||
</span>`
|
|
||||||
: ""}
|
|
||||||
<slot></slot>
|
|
||||||
</button>`;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -11,6 +11,8 @@ import ButtonStyle from "@patternfly/patternfly/components/Button/button.css";
|
||||||
import fa from "@fortawesome/fontawesome-free/css/solid.css";
|
import fa from "@fortawesome/fontawesome-free/css/solid.css";
|
||||||
|
|
||||||
import { convertToSlug } from "../utils";
|
import { convertToSlug } from "../utils";
|
||||||
|
import { SpinnerButton } from "./SpinnerButton";
|
||||||
|
import { PRIMARY_CLASS } from "../constants";
|
||||||
|
|
||||||
@customElement("pb-modal-button")
|
@customElement("pb-modal-button")
|
||||||
export class ModalButton extends LitElement {
|
export class ModalButton extends LitElement {
|
||||||
|
@ -119,6 +121,9 @@ export class ModalButton extends LitElement {
|
||||||
this.querySelector("[slot=modal]")!.innerHTML = t;
|
this.querySelector("[slot=modal]")!.innerHTML = t;
|
||||||
this.updateHandlers();
|
this.updateHandlers();
|
||||||
this.open = true;
|
this.open = true;
|
||||||
|
this.querySelectorAll<SpinnerButton>("pb-spinner-button").forEach(sb => {
|
||||||
|
sb.setDone(PRIMARY_CLASS);
|
||||||
|
});
|
||||||
})
|
})
|
||||||
.catch((e) => {
|
.catch((e) => {
|
||||||
console.error(e);
|
console.error(e);
|
||||||
|
|
|
@ -0,0 +1,84 @@
|
||||||
|
import { css, customElement, html, LitElement, property } from "lit-element";
|
||||||
|
// @ts-ignore
|
||||||
|
import GlobalsStyle from "@patternfly/patternfly/base/patternfly-globals.css";
|
||||||
|
// @ts-ignore
|
||||||
|
import ButtonStyle from "@patternfly/patternfly/components/Button/button.css";
|
||||||
|
// @ts-ignore
|
||||||
|
import SpinnerStyle from "@patternfly/patternfly/components/Spinner/spinner.css";
|
||||||
|
import {
|
||||||
|
ColorStyles,
|
||||||
|
PRIMARY_CLASS,
|
||||||
|
PROGRESS_CLASS,
|
||||||
|
} from "../constants";
|
||||||
|
|
||||||
|
@customElement("pb-spinner-button")
|
||||||
|
export class SpinnerButton extends LitElement {
|
||||||
|
@property()
|
||||||
|
isRunning = false;
|
||||||
|
|
||||||
|
static get styles() {
|
||||||
|
return [
|
||||||
|
GlobalsStyle,
|
||||||
|
ButtonStyle,
|
||||||
|
SpinnerStyle,
|
||||||
|
ColorStyles,
|
||||||
|
css`
|
||||||
|
button {
|
||||||
|
/* Have to use !important here, as buttons with pf-m-progress have transition already */
|
||||||
|
transition: all var(--pf-c-button--m-progress--TransitionDuration) ease 0s !important;
|
||||||
|
}
|
||||||
|
`,
|
||||||
|
];
|
||||||
|
}
|
||||||
|
|
||||||
|
constructor() {
|
||||||
|
super();
|
||||||
|
this.classList.add(PRIMARY_CLASS);
|
||||||
|
}
|
||||||
|
|
||||||
|
setLoading() {
|
||||||
|
this.isRunning = true;
|
||||||
|
this.classList.add(PROGRESS_CLASS);
|
||||||
|
this.requestUpdate();
|
||||||
|
}
|
||||||
|
|
||||||
|
setDone(statusClass: string) {
|
||||||
|
this.isRunning = false;
|
||||||
|
this.classList.remove(PROGRESS_CLASS);
|
||||||
|
this.classList.replace(PRIMARY_CLASS, statusClass);
|
||||||
|
this.requestUpdate();
|
||||||
|
setTimeout(() => {
|
||||||
|
this.classList.replace(statusClass, PRIMARY_CLASS);
|
||||||
|
this.requestUpdate();
|
||||||
|
}, 1000);
|
||||||
|
}
|
||||||
|
|
||||||
|
callAction() {
|
||||||
|
if (this.isRunning === true) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
this.setLoading();
|
||||||
|
}
|
||||||
|
|
||||||
|
render() {
|
||||||
|
return html`<button
|
||||||
|
class="pf-c-button pf-m-progress ${this.classList.toString()}"
|
||||||
|
@click=${() => this.callAction()}
|
||||||
|
>
|
||||||
|
${this.isRunning
|
||||||
|
? html` <span class="pf-c-button__progress">
|
||||||
|
<span
|
||||||
|
class="pf-c-spinner pf-m-md"
|
||||||
|
role="progressbar"
|
||||||
|
aria-valuetext="Loading..."
|
||||||
|
>
|
||||||
|
<span class="pf-c-spinner__clipper"></span>
|
||||||
|
<span class="pf-c-spinner__lead-ball"></span>
|
||||||
|
<span class="pf-c-spinner__tail-ball"></span>
|
||||||
|
</span>
|
||||||
|
</span>`
|
||||||
|
: ""}
|
||||||
|
<slot></slot>
|
||||||
|
</button>`;
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,6 +1,7 @@
|
||||||
import "construct-style-sheets-polyfill";
|
import "construct-style-sheets-polyfill";
|
||||||
|
|
||||||
import "./elements/ActionButton";
|
import "./elements/ActionButton";
|
||||||
|
import "./elements/SpinnerButton";
|
||||||
import "./elements/AdminLoginsChart";
|
import "./elements/AdminLoginsChart";
|
||||||
import "./elements/CodeMirror";
|
import "./elements/CodeMirror";
|
||||||
import "./elements/Dropdown";
|
import "./elements/Dropdown";
|
||||||
|
|
|
@ -22,24 +22,24 @@ export class BoundPoliciesList extends Table {
|
||||||
|
|
||||||
row(item: any): string[] {
|
row(item: any): string[] {
|
||||||
return [
|
return [
|
||||||
item.policy.name,
|
item.policy_obj.name,
|
||||||
item.enabled,
|
item.enabled,
|
||||||
item.order,
|
item.order,
|
||||||
item.timeout,
|
item.timeout,
|
||||||
`
|
`
|
||||||
<pb-modal-button href="{% url 'passbook_admin:policy-binding-update' pk=binding.pk %}">
|
<pb-modal-button href="administration/policies/bindings/${item.pk}/update/">
|
||||||
<button slot="trigger" class="pf-c-button pf-m-secondary">
|
<pb-spinner-button slot="trigger" class="pf-m-secondary">
|
||||||
Edit
|
Edit
|
||||||
</button>
|
</pb-spinner-button>
|
||||||
<div slot="modal"></div>
|
<div slot="modal"></div>
|
||||||
</pb-modal-button>
|
</pb-modal-button>
|
||||||
<pb-modal-button href="{% url 'passbook_admin:policy-binding-delete' pk=binding.pk %}">
|
<pb-modal-button href="administration/policies/bindings/${item.pk}/delete/">
|
||||||
<button slot="trigger" class="pf-c-button pf-m-danger">
|
<pb-spinner-button slot="trigger" class="pf-m-danger">
|
||||||
Delete
|
Delete
|
||||||
</button>
|
</pb-spinner-button>
|
||||||
<div slot="modal"></div>
|
<div slot="modal"></div>
|
||||||
</pb-modal-button>
|
</pb-modal-button>
|
||||||
`
|
`,
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Reference in New Issue