feat(webhooks): event-type multi-select + schema draft events (E)
This commit is contained in:
@@ -159,8 +159,8 @@ i18n
|
||||
'webhooks.field.scopeFilterHint': 'Пусто = все scope',
|
||||
'webhooks.field.dictionaryFilter': 'Справочники (CSV)',
|
||||
'webhooks.field.dictionaryFilterHint': 'Через запятую: spacecraft, satellite_type. Пусто = все',
|
||||
'webhooks.field.eventTypeFilter': 'Типы событий (CSV)',
|
||||
'webhooks.field.eventTypeFilterHint': 'record.created, record.updated, record.closed. Пусто = все',
|
||||
'webhooks.field.eventTypeFilter': 'Типы событий',
|
||||
'webhooks.field.eventTypeFilterHint': 'Record*, Definition*, SchemaDraft*. Пусто = все события.',
|
||||
'webhooks.field.description': 'Описание',
|
||||
'webhooks.field.createdBy': 'Создатель',
|
||||
'webhooks.error.nameUrlRequired': 'Имя и URL обязательны',
|
||||
@@ -799,8 +799,8 @@ i18n
|
||||
'webhooks.field.scopeFilterHint': 'Empty = all scopes',
|
||||
'webhooks.field.dictionaryFilter': 'Dictionaries (CSV)',
|
||||
'webhooks.field.dictionaryFilterHint': 'Comma-separated: spacecraft, satellite_type. Empty = all',
|
||||
'webhooks.field.eventTypeFilter': 'Event types (CSV)',
|
||||
'webhooks.field.eventTypeFilterHint': 'record.created, record.updated, record.closed. Empty = all',
|
||||
'webhooks.field.eventTypeFilter': 'Event types',
|
||||
'webhooks.field.eventTypeFilterHint': 'Record*, Definition*, SchemaDraft*. Empty = all events.',
|
||||
'webhooks.field.description': 'Description',
|
||||
'webhooks.field.createdBy': 'Created by',
|
||||
'webhooks.error.nameUrlRequired': 'Name and URL are required',
|
||||
|
||||
@@ -49,6 +49,34 @@ const SCOPE_OPTIONS: SelectOption[] = [
|
||||
{ id: 'RESTRICTED', label: 'RESTRICTED' },
|
||||
]
|
||||
|
||||
/**
|
||||
* Known outbox event types в порядке от самых частых (record CRUD) до
|
||||
* реже встречающихся (schema workflow). Backend emit'ит PascalCase
|
||||
* (см. DictionaryRecordService, DictionaryDefinitionService,
|
||||
* SchemaDraftService). При новых событиях — добавлять сюда.
|
||||
*
|
||||
* <p>Pre-v2.4: hint текст в форме фигурировал dot-case формат
|
||||
* `record.created` — это был docs bug, backend такие не emit'ит.
|
||||
* Multi-select закрывает дыру и не даёт пользователю ввести неверное
|
||||
* строковое имя.
|
||||
*/
|
||||
const EVENT_TYPE_OPTIONS: SelectOption[] = [
|
||||
// Record CRUD
|
||||
{ id: 'RecordCreated', label: 'RecordCreated' },
|
||||
{ id: 'RecordUpdated', label: 'RecordUpdated' },
|
||||
{ id: 'RecordDeleted', label: 'RecordDeleted' },
|
||||
// Dict definition / schema
|
||||
{ id: 'DefinitionCreated', label: 'DefinitionCreated' },
|
||||
{ id: 'DefinitionUpdated', label: 'DefinitionUpdated' },
|
||||
// Schema workflow (v2.2.0+)
|
||||
{ id: 'SchemaDraftCreated', label: 'SchemaDraftCreated' },
|
||||
{ id: 'SchemaDraftUpdated', label: 'SchemaDraftUpdated' },
|
||||
{ id: 'SchemaDraftReviewRequested', label: 'SchemaDraftReviewRequested' },
|
||||
{ id: 'SchemaDraftDecided', label: 'SchemaDraftDecided' },
|
||||
{ id: 'SchemaDraftPublished', label: 'SchemaDraftPublished' },
|
||||
{ id: 'SchemaDraftWithdrawn', label: 'SchemaDraftWithdrawn' },
|
||||
]
|
||||
|
||||
function WebhooksPage() {
|
||||
const { t } = useTranslation()
|
||||
const { data, isLoading, error } = useWebhookSubscriptions()
|
||||
@@ -206,7 +234,7 @@ function CreateWebhookDialog({ open, onClose, onSuccess }: CreateDialogProps) {
|
||||
const [url, setUrl] = useState('')
|
||||
const [scopeFilter, setScopeFilter] = useState<string[]>([])
|
||||
const [dictionaryFilterCsv, setDictionaryFilterCsv] = useState('')
|
||||
const [eventTypeFilterCsv, setEventTypeFilterCsv] = useState('')
|
||||
const [eventTypeFilter, setEventTypeFilter] = useState<string[]>([])
|
||||
const [description, setDescription] = useState('')
|
||||
const [errorMsg, setErrorMsg] = useState<string | null>(null)
|
||||
|
||||
@@ -215,7 +243,7 @@ function CreateWebhookDialog({ open, onClose, onSuccess }: CreateDialogProps) {
|
||||
setUrl('')
|
||||
setScopeFilter([])
|
||||
setDictionaryFilterCsv('')
|
||||
setEventTypeFilterCsv('')
|
||||
setEventTypeFilter([])
|
||||
setDescription('')
|
||||
setErrorMsg(null)
|
||||
}
|
||||
@@ -243,7 +271,7 @@ function CreateWebhookDialog({ open, onClose, onSuccess }: CreateDialogProps) {
|
||||
url: url.trim(),
|
||||
scopeFilter: scopeFilter.length > 0 ? (scopeFilter as DataScope[]) : undefined,
|
||||
dictionaryFilter: csvToArray(dictionaryFilterCsv),
|
||||
eventTypeFilter: csvToArray(eventTypeFilterCsv),
|
||||
eventTypeFilter: eventTypeFilter.length > 0 ? eventTypeFilter : undefined,
|
||||
active: true,
|
||||
description: description.trim() || undefined,
|
||||
}
|
||||
@@ -297,12 +325,12 @@ function CreateWebhookDialog({ open, onClose, onSuccess }: CreateDialogProps) {
|
||||
value={dictionaryFilterCsv}
|
||||
onChange={(e) => setDictionaryFilterCsv(e.target.value)}
|
||||
/>
|
||||
<TextInput
|
||||
<MultiSelect
|
||||
label={t('webhooks.field.eventTypeFilter')}
|
||||
placeholder="record.created, record.updated"
|
||||
options={EVENT_TYPE_OPTIONS}
|
||||
value={eventTypeFilter}
|
||||
onChange={(ids) => setEventTypeFilter(ids as string[])}
|
||||
hint={t('webhooks.field.eventTypeFilterHint')}
|
||||
value={eventTypeFilterCsv}
|
||||
onChange={(e) => setEventTypeFilterCsv(e.target.value)}
|
||||
/>
|
||||
<TextArea
|
||||
label={t('webhooks.field.description')}
|
||||
|
||||
Reference in New Issue
Block a user