130 lines
3.0 KiB
TypeScript
130 lines
3.0 KiB
TypeScript
import {html} from 'htm/preact';
|
|
import {Component} from 'preact';
|
|
|
|
import {Redirect, SimpleRedirect} from '../../redirect/exports.js';
|
|
import storage from '../../redirect/storage.js';
|
|
|
|
import Editor from './editor.js';
|
|
import Usage from './usage.js';
|
|
|
|
type Props = Record<string, unknown>;
|
|
|
|
type State = {
|
|
redirects: Redirect[];
|
|
};
|
|
|
|
export class PageMain extends Component<Props, State> {
|
|
constructor(props: Props) {
|
|
super(props);
|
|
|
|
this.state = {
|
|
redirects: [],
|
|
};
|
|
}
|
|
|
|
async componentDidMount() {
|
|
const redirects = await storage.getRedirects();
|
|
|
|
// Sort the redirects by:
|
|
// * Matcher Type
|
|
// * then Matcher Value
|
|
// * then Redirect Type
|
|
// * finally Redirect Value
|
|
redirects.sort((a, b) => {
|
|
const {
|
|
matcherType: mTypeA,
|
|
matcherValue: mValueA,
|
|
redirectType: rTypeA,
|
|
redirectValue: rValueA,
|
|
} = a.parameters;
|
|
const {
|
|
matcherType: mTypeB,
|
|
matcherValue: mValueB,
|
|
redirectType: rTypeB,
|
|
redirectValue: rValueB,
|
|
} = b.parameters;
|
|
|
|
if (mTypeA !== mTypeB) {
|
|
return mTypeA.localeCompare(mTypeB);
|
|
}
|
|
|
|
if (mValueA !== mValueB) {
|
|
return mValueA.localeCompare(mValueB);
|
|
}
|
|
|
|
if (rTypeA !== rTypeB) {
|
|
return rTypeA.localeCompare(rTypeB);
|
|
}
|
|
|
|
return rValueA.localeCompare(rValueB);
|
|
});
|
|
|
|
this.setState({redirects});
|
|
}
|
|
|
|
addNewRedirect = async () => {
|
|
const redirect = new SimpleRedirect({
|
|
enabled: true,
|
|
id: await storage.nextRedirectId(),
|
|
matcherType: 'hostname',
|
|
matcherValue: 'example.com',
|
|
redirectType: 'hostname',
|
|
redirectValue: 'example.org',
|
|
});
|
|
await storage.savePrepared(await storage.prepareForStorage(redirect));
|
|
this.setState({
|
|
redirects: [redirect, ...this.state.redirects],
|
|
});
|
|
};
|
|
|
|
removeRedirect = (id: number) => {
|
|
this.setState({
|
|
redirects: this.state.redirects.filter(
|
|
(redirect) => redirect.parameters.id !== id,
|
|
),
|
|
});
|
|
};
|
|
|
|
saveRedirect = (redirect: Redirect) => {
|
|
const redirectIndex = this.state.redirects.findIndex(
|
|
(found) => found.parameters.id === redirect.parameters.id,
|
|
);
|
|
if (redirectIndex === -1) {
|
|
this.setState({
|
|
redirects: [redirect, ...this.state.redirects],
|
|
});
|
|
} else {
|
|
const redirects = [...this.state.redirects];
|
|
redirects[redirectIndex] = redirect;
|
|
this.setState({redirects});
|
|
}
|
|
};
|
|
|
|
render() {
|
|
const editors = this.state.redirects.map(
|
|
(redirect) =>
|
|
html`
|
|
<${Editor}
|
|
key=${redirect.idString()}
|
|
redirect=${redirect}
|
|
removeRedirect=${this.removeRedirect}
|
|
saveRedirect=${this.saveRedirect}
|
|
/>
|
|
`,
|
|
);
|
|
|
|
return html`
|
|
<main class="page-main">
|
|
<div class="editors">
|
|
<button class="button new-redirect" onClick=${this.addNewRedirect}>
|
|
Add New Redirect
|
|
</button>
|
|
|
|
${editors}
|
|
</div>
|
|
<${Usage} />
|
|
</main>
|
|
`;
|
|
}
|
|
}
|