mirror of
https://gitlab.com/comunic/comunicconsole
synced 2025-03-14 18:22:38 +00:00
187 lines
4.2 KiB
TypeScript
187 lines
4.2 KiB
TypeScript
|
import {
|
||
|
Table,
|
||
|
TableHead,
|
||
|
TableRow,
|
||
|
TableCell,
|
||
|
TableBody,
|
||
|
IconButton,
|
||
|
Divider,
|
||
|
Button,
|
||
|
} from "@material-ui/core";
|
||
|
import { Delete } from "@material-ui/icons";
|
||
|
import React from "react";
|
||
|
import { AdminAccount, AccountHelper } from "../../helpers/AccountHelper";
|
||
|
import { AdminAccountKey, AdminKeyHelper } from "../../helpers/AdminKeyHelper";
|
||
|
import { CopyToClipboard } from "../../utils/ClipboardUtils";
|
||
|
import { AsyncWidget } from "../widgets/AsyncWidget";
|
||
|
import {
|
||
|
matConfirm,
|
||
|
snackbar,
|
||
|
matAlert,
|
||
|
input,
|
||
|
} from "../widgets/DialogsProvider";
|
||
|
import { TimestampWidget } from "../widgets/TimestampWidget";
|
||
|
import { SettingsSection } from "./SettingsSection";
|
||
|
|
||
|
export class KeySettingsSection extends React.Component<
|
||
|
{ admin: AdminAccount },
|
||
|
{ keys: AdminAccountKey[]; counter: number }
|
||
|
> {
|
||
|
constructor(props: any) {
|
||
|
super(props);
|
||
|
|
||
|
this.state = {
|
||
|
keys: [],
|
||
|
counter: 1,
|
||
|
};
|
||
|
|
||
|
this.load = this.load.bind(this);
|
||
|
this.build = this.build.bind(this);
|
||
|
this.generateResetToken = this.generateResetToken.bind(this);
|
||
|
this.registerNewKey = this.registerNewKey.bind(this);
|
||
|
this.deleteKey = this.deleteKey.bind(this);
|
||
|
}
|
||
|
|
||
|
async load() {
|
||
|
const keys = await AdminKeyHelper.GetAdminKeys(this.props.admin.id);
|
||
|
|
||
|
this.setState({ keys: keys });
|
||
|
}
|
||
|
|
||
|
async generateResetToken() {
|
||
|
try {
|
||
|
if (
|
||
|
!(await matConfirm(
|
||
|
"Do you really want to generate a reset token for this account?"
|
||
|
))
|
||
|
)
|
||
|
return;
|
||
|
|
||
|
const token = await AccountHelper.GenerateResetToken(
|
||
|
this.props.admin.id
|
||
|
);
|
||
|
|
||
|
CopyToClipboard(token.token);
|
||
|
snackbar("Reset token was successfully copied to the clipboard!");
|
||
|
} catch (e) {
|
||
|
console.error(e);
|
||
|
matAlert("Failed to generate a token!");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
async registerNewKey() {
|
||
|
try {
|
||
|
const challenge =
|
||
|
await AdminKeyHelper.GetKeyRegistrationChallenge();
|
||
|
const credential = await navigator.credentials.create(challenge);
|
||
|
|
||
|
if (credential == null) throw new Error("Operation aborted!");
|
||
|
|
||
|
const name = await input({
|
||
|
label: "Key name",
|
||
|
maxLength: 40,
|
||
|
minLength: 2,
|
||
|
});
|
||
|
|
||
|
await AdminKeyHelper.RegisterKey(name, credential);
|
||
|
|
||
|
snackbar("Successfully enrolled a new key!");
|
||
|
|
||
|
this.setState({ counter: this.state.counter + 1 });
|
||
|
} catch (e) {
|
||
|
console.error(e);
|
||
|
matAlert("Failed to register a new key!");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
async deleteKey(key: AdminAccountKey) {
|
||
|
try {
|
||
|
if (
|
||
|
!(await matConfirm(
|
||
|
"Do you really want to delete the key '" + key.name + "' ?"
|
||
|
))
|
||
|
)
|
||
|
return;
|
||
|
|
||
|
await AdminKeyHelper.DeleteAuthKey(this.props.admin.id, key.id);
|
||
|
|
||
|
snackbar("The key was successfully deleted!");
|
||
|
this.setState({ counter: this.state.counter + 1 });
|
||
|
} catch (e) {
|
||
|
console.error(e);
|
||
|
matAlert("Failed to delete key!");
|
||
|
}
|
||
|
}
|
||
|
|
||
|
render() {
|
||
|
return (
|
||
|
<AsyncWidget
|
||
|
errorMessage="Failed to load admin keys!"
|
||
|
load={this.load}
|
||
|
onBuild={this.build}
|
||
|
key={this.props.admin.id + "-" + this.state.counter}
|
||
|
></AsyncWidget>
|
||
|
);
|
||
|
}
|
||
|
|
||
|
build() {
|
||
|
return (
|
||
|
<SettingsSection title="Security keys">
|
||
|
<Table aria-label="simple table">
|
||
|
<TableHead>
|
||
|
<TableRow>
|
||
|
<TableCell>Key name</TableCell>
|
||
|
<TableCell align="right">Date added</TableCell>
|
||
|
<TableCell align="right"></TableCell>
|
||
|
</TableRow>
|
||
|
</TableHead>
|
||
|
<TableBody>
|
||
|
{this.state.keys.map((key) => (
|
||
|
<TableRow key={key.id}>
|
||
|
<TableCell component="th" scope="row">
|
||
|
{key.name}
|
||
|
</TableCell>
|
||
|
<TableCell align="right">
|
||
|
<TimestampWidget time={key.time_add} />
|
||
|
</TableCell>
|
||
|
<TableCell align="right">
|
||
|
<IconButton
|
||
|
aria-label="delete"
|
||
|
size="small"
|
||
|
onClick={() => this.deleteKey(key)}
|
||
|
>
|
||
|
<Delete />
|
||
|
</IconButton>
|
||
|
</TableCell>
|
||
|
</TableRow>
|
||
|
))}
|
||
|
</TableBody>
|
||
|
</Table>
|
||
|
|
||
|
<Divider />
|
||
|
|
||
|
{/* Action buttons */}
|
||
|
<div
|
||
|
style={{
|
||
|
textAlign: "right",
|
||
|
margin: "5px 10px",
|
||
|
}}
|
||
|
>
|
||
|
<Button onClick={this.generateResetToken}>
|
||
|
New reset token
|
||
|
</Button>
|
||
|
<Button
|
||
|
disabled={
|
||
|
this.props.admin.id !==
|
||
|
AccountHelper.currentAccount.id
|
||
|
}
|
||
|
onClick={this.registerNewKey}
|
||
|
>
|
||
|
Register a new key
|
||
|
</Button>
|
||
|
</div>
|
||
|
</SettingsSection>
|
||
|
);
|
||
|
}
|
||
|
}
|