Add Expiry Indicator functionality with configuration and command set
- Implemented ExpiryItemService to manage expiry date logic for list items. - Created ExpiryModels to define types and structures for expiry configurations and rules. - Added RestError utility for handling API response errors. - Developed ExpiryIndicatorFieldCustomizer to display expiry information in list views. - Introduced ExpiryIndicatorCommandSet for extending expiry dates and managing settings. - Added settings dialog for configuring expiry settings. - Implemented localization support for English and German languages. - Added TypeScript configuration files for project setup. - Included TSLint configuration for code quality enforcement.
This commit is contained in:
125
src/extensions/expiryIndicatorCommandSet/ExpirySettingsDialog.ts
Normal file
125
src/extensions/expiryIndicatorCommandSet/ExpirySettingsDialog.ts
Normal file
@@ -0,0 +1,125 @@
|
||||
import { BaseDialog, IDialogConfiguration } from '@microsoft/sp-dialog';
|
||||
import {
|
||||
IExpiryConfig,
|
||||
IExpiryColumnRule,
|
||||
IExpiryValueRule,
|
||||
normalizeConfig
|
||||
} from '../../common/ExpiryModels';
|
||||
import * as strings from 'ExpiryIndicatorCommandSetStrings';
|
||||
|
||||
export class ExpirySettingsDialog extends BaseDialog {
|
||||
private _config: IExpiryConfig;
|
||||
private _save: (config: IExpiryConfig) => Promise<void>;
|
||||
|
||||
public constructor(config: IExpiryConfig, save: (config: IExpiryConfig) => Promise<void>) {
|
||||
super();
|
||||
this._config = config;
|
||||
this._save = save;
|
||||
}
|
||||
|
||||
public render(): void {
|
||||
this.domElement.innerHTML =
|
||||
'<div style="max-width:760px;padding:20px;font-family:Segoe UI,Arial,sans-serif">' +
|
||||
'<h2 style="margin-top:0">' + strings.SettingsTitle + '</h2>' +
|
||||
'<div style="display:grid;grid-template-columns:1fr 1fr;gap:12px">' +
|
||||
this._input('baseField', strings.BaseField) +
|
||||
this._input('expiryField', strings.ExpiryField) +
|
||||
this._input('lifetimeValue', strings.DefaultLifetimeValue, 'number') +
|
||||
'<label>' + strings.DefaultLifetimeUnit +
|
||||
'<select data-field="lifetimeUnit" style="display:block;width:100%;padding:6px;margin-top:4px">' +
|
||||
'<option value="days">days</option><option value="months">months</option><option value="years">years</option>' +
|
||||
'</select>' +
|
||||
'</label>' +
|
||||
'</div>' +
|
||||
'<label style="display:block;margin-top:12px">' + strings.DefaultColumnRulesJson +
|
||||
'<textarea data-field="defaultColumnRule" rows="10" style="display:block;width:100%;box-sizing:border-box;font-family:Consolas,monospace;margin-top:4px"></textarea>' +
|
||||
'</label>' +
|
||||
'<label style="display:block;margin-top:12px">' + strings.RulesJson +
|
||||
'<textarea data-field="rules" rows="12" style="display:block;width:100%;box-sizing:border-box;font-family:Consolas,monospace;margin-top:4px"></textarea>' +
|
||||
'</label>' +
|
||||
'<label style="display:block;margin-top:12px"><input data-field="confirmExtension" type="checkbox"> ' +
|
||||
strings.ConfirmExtension + '</label>' +
|
||||
'<label style="display:block;margin-top:12px">' + strings.NullText +
|
||||
'<input data-field="nullText" type="text" style="display:block;width:100%;box-sizing:border-box;padding:6px;margin-top:4px">' +
|
||||
'</label>' +
|
||||
'<div data-field="error" style="color:#a4262c;min-height:20px;margin-top:10px"></div>' +
|
||||
'<div style="text-align:right;margin-top:12px">' +
|
||||
'<button data-action="cancel" type="button" style="padding:7px 18px;margin-right:8px">' + strings.Cancel + '</button>' +
|
||||
'<button data-action="save" type="button" style="padding:7px 18px;background:#0078d4;color:#fff;border:0">' + strings.Save + '</button>' +
|
||||
'</div>' +
|
||||
'</div>';
|
||||
|
||||
this._setValue('baseField', this._config.baseField);
|
||||
this._setValue('expiryField', this._config.expiryField);
|
||||
this._setValue('lifetimeValue', String(this._config.default.lifeTime.value));
|
||||
this._setValue('lifetimeUnit', this._config.default.lifeTime.unit);
|
||||
this._setValue('defaultColumnRule', JSON.stringify(this._config.default.columnRule, undefined, 2));
|
||||
this._setValue('rules', JSON.stringify(this._config.rules, undefined, 2));
|
||||
this._setValue('nullText', this._config.nullText);
|
||||
(this._field('confirmExtension') as HTMLInputElement).checked = this._config.confirmExtension;
|
||||
|
||||
(this.domElement.querySelector('[data-action="cancel"]') as HTMLButtonElement).onclick = (): void => {
|
||||
this.close();
|
||||
};
|
||||
(this.domElement.querySelector('[data-action="save"]') as HTMLButtonElement).onclick = (): void => {
|
||||
this._saveForm();
|
||||
};
|
||||
}
|
||||
|
||||
public getConfig(): IDialogConfiguration {
|
||||
return { isBlocking: true };
|
||||
}
|
||||
|
||||
private _saveForm(): void {
|
||||
const saveButton: HTMLButtonElement = this.domElement.querySelector('[data-action="save"]') as HTMLButtonElement;
|
||||
const errorElement: HTMLElement = this._field('error') as HTMLElement;
|
||||
errorElement.textContent = '';
|
||||
|
||||
try {
|
||||
const defaultColumnRule: IExpiryColumnRule[] = JSON.parse(this._value('defaultColumnRule'));
|
||||
const rules: IExpiryValueRule[] = JSON.parse(this._value('rules'));
|
||||
const config: IExpiryConfig = normalizeConfig({
|
||||
baseField: this._value('baseField').trim(),
|
||||
expiryField: this._value('expiryField').trim(),
|
||||
default: {
|
||||
lifeTime: {
|
||||
value: Number(this._value('lifetimeValue')),
|
||||
unit: this._value('lifetimeUnit')
|
||||
},
|
||||
columnRule: defaultColumnRule
|
||||
},
|
||||
rules: rules,
|
||||
nullText: this._value('nullText'),
|
||||
confirmExtension: (this._field('confirmExtension') as HTMLInputElement).checked
|
||||
});
|
||||
|
||||
saveButton.disabled = true;
|
||||
this._save(config).then((): void => {
|
||||
this._config = config;
|
||||
this.close();
|
||||
}).catch((error: Error): void => {
|
||||
saveButton.disabled = false;
|
||||
errorElement.textContent = error && error.message ? error.message : String(error);
|
||||
});
|
||||
} catch (error) {
|
||||
errorElement.textContent = strings.InvalidJson + ': ' + (error && error.message ? error.message : String(error));
|
||||
}
|
||||
}
|
||||
|
||||
private _input(field: string, label: string, type?: string): string {
|
||||
return '<label>' + label + '<input data-field="' + field + '" type="' + (type || 'text') +
|
||||
'" style="display:block;width:100%;box-sizing:border-box;padding:6px;margin-top:4px"></label>';
|
||||
}
|
||||
|
||||
private _field(name: string): Element {
|
||||
return this.domElement.querySelector('[data-field="' + name + '"]') as Element;
|
||||
}
|
||||
|
||||
private _value(name: string): string {
|
||||
return (this._field(name) as HTMLInputElement).value;
|
||||
}
|
||||
|
||||
private _setValue(name: string, value: string): void {
|
||||
(this._field(name) as HTMLInputElement).value = value;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user