@goodandready/dsh-cron 0.3.12 → 0.3.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/lib/client.js CHANGED
@@ -4,6 +4,7 @@ factory: (require) => {
4
4
  var module = { exports: {} }
5
5
  var exports = module.exports
6
6
  const React = window.React || require('react');
7
+ const h = (...args) => (React && React.createElement ? React.createElement(...args) : null);
7
8
  const ReactDOM = window.ReactDOM || require('react-dom/client');
8
9
  const PLUGIN_ID = '@goodandready/dsh-cron';
9
10
  const NS = 'dsh-cron';
@@ -42,7 +43,7 @@ CoreChevron = primitives && primitives.IconChevronDownOutline14;
42
43
  } catch (e) {
43
44
  /* Optional core chevron primitive not available; SVG fallback used */
44
45
  }
45
- const chevronNode = () => (CoreChevron ? React.createElement(CoreChevron) : React.createElement('span', { style: { display: 'flex', alignItems: 'center' }, dangerouslySetInnerHTML: { __html: ICON_CHEVRON_DOWN } }));
46
+ const chevronNode = () => (CoreChevron ? h(CoreChevron) : h('span', { style: { display: 'flex', alignItems: 'center' }, dangerouslySetInnerHTML: { __html: ICON_CHEVRON_DOWN } }));
46
47
  const STRINGS = {
47
48
  en: {
48
49
  'sidebar.label': 'Scheduled tasks', 'sidebar.jobsTitle': 'Active jobs',
@@ -280,7 +281,7 @@ en: {
280
281
  'approval.approved': 'Approved', 'approval.rejected': 'Rejected',
281
282
  'chainGraph.modalTitle': 'Visual Chain & Checkpoint Graph', 'chainGraph.viewGraph': 'Chain Graph',
282
283
  'chainGraph.noNodes': 'No chained steps found for this task or run.', 'chainGraph.retryStep': 'Retry Step',
283
- 'chainGraph.stepSuccess': 'Success', 'chainGraph.stepFailed': 'Failed', 'chainGraph.stepPending': 'Pending', 'chainGraph.close': 'Close',
284
+ 'chainGraph.stepSuccess': 'Success', 'chainGraph.stepFailed': 'Failed', 'chainGraph.stepPending': 'Pending', 'chainGraph.close': 'Close', 'chainGraph.decisionNode': 'Decision Node', 'chainGraph.stepSkipped': 'Skipped', 'history.doctorDiagnosis': 'Doctor Diagnosis & Suggested Fix', 'history.doctorApply': '1-Click Apply Fix', 'history.doctorRevert': 'Revert to Previous Code', 'history.autoHealed': 'Auto-Healed by Doctor', 'form.autoHealLabel': 'Autonomous Self-Healing Doctor', 'form.autoHealHint': 'Automatically diagnose and apply safe fixes upon failure (max 1 auto-patch/day)', 'form.elseTaskLabel': 'Default Fallback Task (elseTask)', 'form.elseTaskHint': 'Target task to trigger if no conditional branch rules matched', 'form.elseTaskPlaceholder': 'e.g. task-fallback',
284
285
  'adaptive.badge': 'Adaptive', 'adaptive.idle': 'idle', 'adaptive.backoff': 'backoff',
285
286
  'form.adaptiveEnabled': 'Adaptive Polling', 'form.adaptiveHint': 'Exponential backoff when no changes are detected',
286
287
  'liveLog.modalTitle': 'Real-Time Streaming Execution Logs', 'liveLog.viewLog': 'Live Stream',
@@ -462,7 +463,7 @@ zh: {
462
463
  'approval.approved': '已批准', 'approval.rejected': '已拒绝',
463
464
  'chainGraph.modalTitle': '任务链与检查点依赖图', 'chainGraph.viewGraph': '任务链图',
464
465
  'chainGraph.noNodes': '未找到该任务或运行的关联步骤。', 'chainGraph.retryStep': '重试此步骤',
465
- 'chainGraph.stepSuccess': '成功', 'chainGraph.stepFailed': '失败', 'chainGraph.stepPending': '等待中', 'chainGraph.close': '关闭',
466
+ 'chainGraph.stepSuccess': '成功', 'chainGraph.stepFailed': '失败', 'chainGraph.stepPending': '等待中', 'chainGraph.close': '关闭', 'chainGraph.decisionNode': '条件决策节点', 'chainGraph.stepSkipped': '已跳过', 'history.doctorDiagnosis': 'Doctor 诊断与建议修复', 'history.doctorApply': '一键应用修复', 'history.doctorRevert': '恢复上一版本代码', 'history.autoHealed': '已由 Doctor 自动修复', 'form.autoHealLabel': '自主 Self-Healing Doctor 自动修复', 'form.autoHealHint': '当任务失败时自动诊断并安全修复(每天上限 1 次)', 'form.elseTaskLabel': '默认后备任务 (elseTask)', 'form.elseTaskHint': '当没有分支条件匹配时触发的目标任务', 'form.elseTaskPlaceholder': '如 task-fallback',
466
467
  'adaptive.badge': '自适应', 'adaptive.idle': '空闲', 'adaptive.backoff': '避让中',
467
468
  'form.adaptiveEnabled': '自适应轮询 (Adaptive Polling)', 'form.adaptiveHint': '数据无变化时指数级延长执行间隔',
468
469
  'liveLog.modalTitle': '实时任务执行日志流', 'liveLog.viewLog': '实时日志',
@@ -781,10 +782,10 @@ console.error('[dsh-cron] React error:', error, errorInfo);
781
782
  }
782
783
  render() {
783
784
  if (this.state.hasError) {
784
- return React.createElement('div', { className: 'dsh-cron-status-banner', 'data-type': 'error', style: { margin: '12px 0' } },
785
- React.createElement('div', { style: { fontWeight: 600, marginBottom: '6px' } }, '⚠️ Cron UI error:'),
786
- React.createElement('div', { style: { fontSize: '12px', wordBreak: 'break-all' } }, String((this.state.error && this.state.error.message) || this.state.error)),
787
- React.createElement('button', {
785
+ return h('div', { className: 'dsh-cron-status-banner', 'data-type': 'error', style: { margin: '12px 0' } },
786
+ h('div', { style: { fontWeight: 600, marginBottom: '6px' } }, '⚠️ Cron UI error:'),
787
+ h('div', { style: { fontSize: '12px', wordBreak: 'break-all' } }, String((this.state.error && this.state.error.message) || this.state.error)),
788
+ h('button', {
788
789
  type: 'button',
789
790
  className: 'dsh-cron-btn-secondary',
790
791
  style: { marginTop: '10px', fontSize: '12px', padding: '4px 10px' },
@@ -979,9 +980,9 @@ return out;
979
980
  }
980
981
  function renderDeliverySettings({ T, values, onChange, onChannelTemplate, sections, onToggleSection }) {
981
982
  const val = (key) => (values[key] === undefined || values[key] === null ? '' : String(values[key]));
982
- const field = (f) => React.createElement('div', { className: 'dsh-cron-form-group', key: f.key, style: { marginBottom: '10px' } },
983
- React.createElement('label', null, T(f.labelKey)),
984
- React.createElement('input', f.numeric ? {
983
+ const field = (f) => h('div', { className: 'dsh-cron-form-group', key: f.key, style: { marginBottom: '10px' } },
984
+ h('label', null, T(f.labelKey)),
985
+ h('input', f.numeric ? {
985
986
  type: 'number',
986
987
  min: f.min !== undefined ? f.min : 1000,
987
988
  step: 1000,
@@ -999,49 +1000,49 @@ onChange: (e) => onChange(f.key, e.target.value)
999
1000
  );
1000
1001
  const section = (key, titleKey, children) => {
1001
1002
  const open = Boolean(sections[key]);
1002
- return React.createElement('div', { className: 'dsh-cron-section', key },
1003
- React.createElement('button', {
1003
+ return h('div', { className: 'dsh-cron-section', key },
1004
+ h('button', {
1004
1005
  type: 'button',
1005
1006
  className: 'dsh-cron-section-head',
1006
1007
  'aria-expanded': open ? 'true' : 'false',
1007
1008
  onClick: () => onToggleSection(key)
1008
1009
  },
1009
- React.createElement('span', null, T(titleKey)),
1010
- React.createElement('span', { className: 'dsh-cron-section-chevron', 'data-open': open ? 'true' : 'false' }, '▾')
1010
+ h('span', null, T(titleKey)),
1011
+ h('span', { className: 'dsh-cron-section-chevron', 'data-open': open ? 'true' : 'false' }, '▾')
1011
1012
  ),
1012
- open && React.createElement('div', { className: 'dsh-cron-section-body' }, children)
1013
+ open && h('div', { className: 'dsh-cron-section-body' }, children)
1013
1014
  );
1014
1015
  };
1015
1016
  return [
1016
1017
  section('secrets', 'settings.secretsSection', [
1017
- React.createElement('div', { className: 'dsh-cron-hint', key: 'hint', style: { marginBottom: '10px' } }, T('settings.secretsHint')),
1018
+ h('div', { className: 'dsh-cron-hint', key: 'hint', style: { marginBottom: '10px' } }, T('settings.secretsHint')),
1018
1019
  ...DELIVERY_SETTING_FIELDS.filter((f) => f.group === 'secrets').map(field),
1019
1020
  ]),
1020
1021
  section('channels', 'settings.deliverySection', [
1021
- React.createElement('div', { className: 'dsh-cron-form-row', key: 'row' },
1022
+ h('div', { className: 'dsh-cron-form-row', key: 'row' },
1022
1023
  ...DELIVERY_SETTING_FIELDS.filter((f) => f.group === 'channels').map(field)
1023
1024
  ),
1024
1025
  ]),
1025
1026
  section('automation', 'settings.automationSection', [
1026
- React.createElement('div', { className: 'dsh-cron-hint', key: 'hint', style: { marginBottom: '10px' } }, T('settings.automationHint')),
1027
- React.createElement('div', { className: 'dsh-cron-form-row', key: 'row' },
1027
+ h('div', { className: 'dsh-cron-hint', key: 'hint', style: { marginBottom: '10px' } }, T('settings.automationHint')),
1028
+ h('div', { className: 'dsh-cron-form-row', key: 'row' },
1028
1029
  ...DELIVERY_SETTING_FIELDS.filter((f) => f.group === 'automation').map(field)
1029
1030
  ),
1030
1031
  ]),
1031
1032
  section('templates', 'settings.templatesSection', [
1032
- React.createElement('div', { className: 'dsh-cron-form-group', key: 'global', style: { marginBottom: '10px' } },
1033
- React.createElement('label', null, T('settings.templateLabel')),
1034
- React.createElement('input', {
1033
+ h('div', { className: 'dsh-cron-form-group', key: 'global', style: { marginBottom: '10px' } },
1034
+ h('label', null, T('settings.templateLabel')),
1035
+ h('input', {
1035
1036
  type: 'text',
1036
1037
  value: val('template'),
1037
1038
  onChange: (e) => onChange('template', e.target.value)
1038
1039
  }),
1039
- React.createElement('div', { className: 'dsh-cron-hint' }, T('settings.templateHint'))
1040
+ h('div', { className: 'dsh-cron-hint' }, T('settings.templateHint'))
1040
1041
  ),
1041
- React.createElement('div', { className: 'dsh-cron-form-row', key: 'perchannel' },
1042
- ...DELIVERY_CHANNELS.map((id) => React.createElement('div', { className: 'dsh-cron-form-group', key: id, style: { marginBottom: '10px' } },
1043
- React.createElement('label', null, T('settings.channelTemplateLabel', { channel: T(CHANNEL_LABEL_KEYS[id]) })),
1044
- React.createElement('input', {
1042
+ h('div', { className: 'dsh-cron-form-row', key: 'perchannel' },
1043
+ ...DELIVERY_CHANNELS.map((id) => h('div', { className: 'dsh-cron-form-group', key: id, style: { marginBottom: '10px' } },
1044
+ h('label', null, T('settings.channelTemplateLabel', { channel: T(CHANNEL_LABEL_KEYS[id]) })),
1045
+ h('input', {
1045
1046
  type: 'text',
1046
1047
  value: (values.channelTemplates && values.channelTemplates[id]) || '',
1047
1048
  onChange: (e) => onChannelTemplate(id, e.target.value)
@@ -1079,9 +1080,49 @@ if (nodeStatus === 'failed') hasFailure = true;
1079
1080
  nodeStatus = 'running';
1080
1081
  }
1081
1082
  const deps = sanitizeDependsOn(task.dependsOn);
1082
- nodes.push({ id, title: task.title || id, type: task.type || 'prompt', status: nodeStatus, durationMs, retryCount, outputSnippet, isFocus: Boolean(focusTaskId && id === focusTaskId), isRetryable: nodeStatus === 'failed', dependsOn: deps, joinPolicy: sanitizeJoinPolicy(task.joinPolicy) });
1083
+ const hasBranches = Array.isArray(task.branchRules) && task.branchRules.length > 0;
1084
+ nodes.push({
1085
+ id,
1086
+ title: task.title || id,
1087
+ type: task.type || 'prompt',
1088
+ status: nodeStatus,
1089
+ durationMs,
1090
+ retryCount,
1091
+ outputSnippet,
1092
+ isFocus: Boolean(focusTaskId && id === focusTaskId),
1093
+ isRetryable: nodeStatus === 'failed',
1094
+ isDecisionNode: hasBranches,
1095
+ branchRulesCount: hasBranches ? task.branchRules.length : 0,
1096
+ elseTask: task.elseTask || null,
1097
+ dependsOn: deps,
1098
+ joinPolicy: sanitizeJoinPolicy(task.joinPolicy)
1099
+ });
1083
1100
  for (const d of deps) edges.push({ from: d, to: id, type: 'dependsOn', label: task.joinPolicy === 'any_success' ? 'join:any' : 'join:all' });
1101
+ if (hasBranches) {
1102
+ for (const rule of task.branchRules) {
1103
+ if (rule && rule.targetTask) {
1104
+ edges.push({
1105
+ from: id,
1106
+ to: String(rule.targetTask).trim(),
1107
+ type: 'branch',
1108
+ label: rule.label || ('[if: ' + rule.field + ' ' + rule.operator + ' ' + (rule.value != null ? rule.value : '') + ']').trim(),
1109
+ condition: { field: rule.field, operator: rule.operator, value: rule.value }
1110
+ });
1111
+ }
1112
+ }
1113
+ }
1114
+ if (task.elseTask) {
1115
+ edges.push({
1116
+ from: id,
1117
+ to: String(task.elseTask).trim(),
1118
+ type: 'branch_else',
1119
+ label: '[else]',
1120
+ isElse: true
1121
+ });
1122
+ }
1123
+ if (!hasBranches) {
1084
1124
  for (const t of parseChainTargets(task.onSuccess)) edges.push({ from: id, to: t, type: 'onSuccess', label: 'onSuccess' });
1125
+ }
1085
1126
  for (const f of parseChainTargets(task.onFailure)) edges.push({ from: id, to: f, type: 'onFailure', label: 'onFailure' });
1086
1127
  }
1087
1128
  return { nodes, edges, hasFailure };
@@ -1091,68 +1132,68 @@ if (!isOpen) return null;
1091
1132
  const graph = data?.graph || { nodes: [], edges: [], hasFailure: false };
1092
1133
  const chainRunId = data?.chainRunId || '';
1093
1134
  const nodes = graph.nodes || [];
1094
- return React.createElement('div', {
1135
+ return h('div', {
1095
1136
  className: 'dsh-cron-modal-overlay',
1096
1137
  onClick: onClose
1097
1138
  },
1098
- React.createElement('div', {
1139
+ h('div', {
1099
1140
  className: 'dsh-cron-modal',
1100
1141
  style: { maxWidth: '820px', width: '92vw', maxHeight: '88vh', display: 'flex', flexDirection: 'column' },
1101
1142
  role: 'dialog',
1102
1143
  'aria-modal': 'true',
1103
1144
  onClick: (e) => e.stopPropagation()
1104
1145
  },
1105
- React.createElement('div', {
1146
+ h('div', {
1106
1147
  className: 'dsh-cron-modal-head',
1107
1148
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', borderBottom: '1px solid var(--dsw-alias-border-l2)', paddingBottom: '12px' }
1108
1149
  },
1109
- React.createElement('div', null,
1110
- React.createElement('div', {
1150
+ h('div', null,
1151
+ h('div', {
1111
1152
  className: 'dsh-cron-modal-title',
1112
1153
  style: { margin: 0, display: 'flex', alignItems: 'center', gap: '8px' }
1113
1154
  },
1114
- React.createElement('span', { style: { fontSize: '18px' } }, '🕸️'),
1155
+ h('span', { style: { fontSize: '18px' } }, '🕸️'),
1115
1156
  T_KEY(t, 'chainGraph.modalTitle')
1116
1157
  ),
1117
- chainRunId && React.createElement('div', {
1158
+ chainRunId && h('div', {
1118
1159
  style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #888)', marginTop: '4px', fontFamily: 'monospace' }
1119
1160
  }, 'Run ID: ' + chainRunId)
1120
1161
  ),
1121
- React.createElement('button', {
1162
+ h('button', {
1122
1163
  type: 'button',
1123
1164
  className: 'dsh-cron-icon-btn',
1124
1165
  onClick: onClose
1125
1166
  }, '✕')
1126
1167
  ),
1127
- React.createElement('div', {
1168
+ h('div', {
1128
1169
  style: { flex: 1, overflowY: 'auto', padding: '16px 0', minHeight: '260px' }
1129
1170
  },
1130
- loading && React.createElement('div', {
1171
+ loading && h('div', {
1131
1172
  className: 'dsh-cron-history-empty'
1132
1173
  }, T_KEY(t, 'history.loading')),
1133
- !loading && nodes.length === 0 && React.createElement('div', {
1174
+ !loading && nodes.length === 0 && h('div', {
1134
1175
  className: 'dsh-cron-history-empty'
1135
1176
  }, T_KEY(t, 'chainGraph.noNodes')),
1136
- !loading && nodes.length > 0 && React.createElement('div', {
1177
+ !loading && nodes.length > 0 && h('div', {
1137
1178
  style: { display: 'flex', flexDirection: 'column', gap: '16px' }
1138
1179
  },
1139
- React.createElement('div', {
1180
+ h('div', {
1140
1181
  style: { display: 'flex', gap: '12px', fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #888)', padding: '0 4px' }
1141
1182
  },
1142
- React.createElement('span', { style: { display: 'inline-flex', alignItems: 'center', gap: '4px' } },
1143
- React.createElement('span', { style: { width: '8px', height: '8px', borderRadius: '50%', background: 'var(--dsh-cron-success)' } }),
1183
+ h('span', { style: { display: 'inline-flex', alignItems: 'center', gap: '4px' } },
1184
+ h('span', { style: { width: '8px', height: '8px', borderRadius: '50%', background: 'var(--dsh-cron-success)' } }),
1144
1185
  T_KEY(t, 'chainGraph.stepSuccess')
1145
1186
  ),
1146
- React.createElement('span', { style: { display: 'inline-flex', alignItems: 'center', gap: '4px' } },
1147
- React.createElement('span', { style: { width: '8px', height: '8px', borderRadius: '50%', background: 'var(--dsh-cron-danger)' } }),
1187
+ h('span', { style: { display: 'inline-flex', alignItems: 'center', gap: '4px' } },
1188
+ h('span', { style: { width: '8px', height: '8px', borderRadius: '50%', background: 'var(--dsh-cron-danger)' } }),
1148
1189
  T_KEY(t, 'chainGraph.stepFailed')
1149
1190
  ),
1150
- React.createElement('span', { style: { display: 'inline-flex', alignItems: 'center', gap: '4px' } },
1151
- React.createElement('span', { style: { width: '8px', height: '8px', borderRadius: '50%', background: 'var(--dsw-alias-label-tertiary, #888)' } }),
1191
+ h('span', { style: { display: 'inline-flex', alignItems: 'center', gap: '4px' } },
1192
+ h('span', { style: { width: '8px', height: '8px', borderRadius: '50%', background: 'var(--dsw-alias-label-tertiary, #888)' } }),
1152
1193
  T_KEY(t, 'chainGraph.stepPending')
1153
1194
  )
1154
1195
  ),
1155
- React.createElement('div', {
1196
+ h('div', {
1156
1197
  style: {
1157
1198
  display: 'flex',
1158
1199
  flexWrap: 'wrap',
@@ -1172,7 +1213,7 @@ const borderColor = isOk
1172
1213
  : isFailed
1173
1214
  ? 'var(--dsh-cron-danger)'
1174
1215
  : 'var(--dsw-alias-border-l2)';
1175
- return React.createElement('div', {
1216
+ return h('div', {
1176
1217
  key: n.id || idx,
1177
1218
  style: {
1178
1219
  flex: '1 1 220px',
@@ -1187,13 +1228,13 @@ gap: '8px',
1187
1228
  boxShadow: isFailed ? '0 0 0 1px var(--dsh-cron-danger)' : 'none'
1188
1229
  }
1189
1230
  },
1190
- React.createElement('div', {
1231
+ h('div', {
1191
1232
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'flex-start', gap: '6px' }
1192
1233
  },
1193
- React.createElement('div', {
1234
+ h('div', {
1194
1235
  style: { fontWeight: '600', fontSize: '13px', color: 'var(--dsw-alias-label-primary)' }
1195
1236
  }, n.title || n.id),
1196
- React.createElement('span', {
1237
+ h('span', {
1197
1238
  style: {
1198
1239
  fontSize: '10px',
1199
1240
  padding: '2px 6px',
@@ -1204,19 +1245,22 @@ color: isOk ? 'var(--dsh-cron-success)' : isFailed ? 'var(--dsh-cron-danger)' :
1204
1245
  }
1205
1246
  }, isOk ? '✓ ' + T_KEY(t, 'chainGraph.stepSuccess') : isFailed ? '✗ ' + T_KEY(t, 'chainGraph.stepFailed') : '⏳ ' + T_KEY(t, 'chainGraph.stepPending'))
1206
1247
  ),
1207
- React.createElement('div', {
1248
+ h('div', {
1208
1249
  style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary)', display: 'flex', gap: '8px', flexWrap: 'wrap' }
1209
1250
  },
1210
- n.durationMs > 0 && React.createElement('span', null, n.durationMs + 'ms'),
1211
- n.retryCount > 0 && React.createElement('span', { style: { color: 'var(--dsh-cron-warning)' } }, '↻ ' + n.retryCount),
1212
- n.joinPolicy && n.dependsOn?.length > 0 && React.createElement('span', {
1251
+ n.durationMs > 0 && h('span', null, n.durationMs + 'ms'),
1252
+ n.retryCount > 0 && h('span', { style: { color: 'var(--dsh-cron-warning)' } }, '↻ ' + n.retryCount),
1253
+ n.joinPolicy && n.dependsOn?.length > 0 && h('span', {
1213
1254
  style: { background: 'var(--dsw-alias-bg-layer-3)', padding: '1px 4px', borderRadius: '4px' }
1214
1255
  }, n.joinPolicy === 'any_success' ? 'join:any' : 'join:all')
1215
1256
  ),
1216
- n.dependsOn?.length > 0 && React.createElement('div', {
1257
+ n.isDecisionNode && h('div', {
1258
+ style: { fontSize: '11px', color: 'var(--dsh-cron-warning)', fontWeight: '600', display: 'flex', alignItems: 'center', gap: '4px' }
1259
+ }, '🔀 ' + T_KEY(t, 'chainGraph.decisionNode') + ' (' + n.branchRulesCount + ')'),
1260
+ n.dependsOn?.length > 0 && h('div', {
1217
1261
  style: { fontSize: '11px', color: 'var(--dsw-alias-label-tertiary)' }
1218
1262
  }, '← ' + n.dependsOn.join(', ')),
1219
- n.outputSnippet && React.createElement('div', {
1263
+ n.outputSnippet && h('div', {
1220
1264
  style: {
1221
1265
  background: 'var(--dsw-alias-bg-layer-2)',
1222
1266
  border: '1px solid var(--dsw-alias-border-l2)',
@@ -1231,7 +1275,7 @@ maxHeight: '60px',
1231
1275
  overflowY: 'auto'
1232
1276
  }
1233
1277
  }, n.outputSnippet),
1234
- isFailed && chainRunId && React.createElement('button', {
1278
+ isFailed && chainRunId && h('button', {
1235
1279
  type: 'button',
1236
1280
  className: 'dsh-cron-btn-secondary',
1237
1281
  style: {
@@ -1252,11 +1296,11 @@ onClick: () => onRetry && onRetry(n.id)
1252
1296
  )
1253
1297
  )
1254
1298
  ),
1255
- React.createElement('div', {
1299
+ h('div', {
1256
1300
  className: 'dsh-cron-modal-foot',
1257
1301
  style: { borderTop: '1px solid var(--dsw-alias-border-l2)', paddingTop: '12px', marginTop: 'auto' }
1258
1302
  },
1259
- React.createElement('button', {
1303
+ h('button', {
1260
1304
  type: 'button',
1261
1305
  className: 'dsh-cron-btn-primary',
1262
1306
  onClick: onClose
@@ -1274,26 +1318,26 @@ el.scrollTop = el.scrollHeight;
1274
1318
  };
1275
1319
  const isLive = status === 'running' || status === 'connecting';
1276
1320
  const statusColor = isLive ? 'var(--dsh-cron-success, #2a2)' : (status === 'completed' ? 'var(--dsw-alias-label-secondary, #888)' : 'var(--dsh-cron-danger, #e33)');
1277
- return React.createElement('div', {
1321
+ return h('div', {
1278
1322
  className: 'dsh-cron-modal-overlay',
1279
1323
  onClick: onClose
1280
1324
  },
1281
- React.createElement('div', {
1325
+ h('div', {
1282
1326
  className: 'dsh-cron-modal',
1283
1327
  style: { maxWidth: '860px', width: '92vw', height: '80vh', display: 'flex', flexDirection: 'column', background: 'var(--dsw-alias-bg-base, #111)', color: 'var(--dsw-alias-label-primary, #ddd)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '8px' },
1284
1328
  role: 'dialog',
1285
1329
  'aria-modal': 'true',
1286
1330
  onClick: (e) => e.stopPropagation()
1287
1331
  },
1288
- React.createElement('div', {
1332
+ h('div', {
1289
1333
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', padding: '12px 16px', borderBottom: '1px solid var(--dsw-alias-border-l2, #333)', background: 'var(--dsw-alias-bg-layer-2, #111)' }
1290
1334
  },
1291
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
1292
- React.createElement('span', { style: { fontSize: '18px' } }, '📺'),
1293
- React.createElement('div', null,
1294
- React.createElement('div', { style: { fontWeight: '600', fontSize: '14px', color: 'var(--dsw-alias-label-primary, #fff)', display: 'flex', alignItems: 'center', gap: '8px' } },
1335
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
1336
+ h('span', { style: { fontSize: '18px' } }, '📺'),
1337
+ h('div', null,
1338
+ h('div', { style: { fontWeight: '600', fontSize: '14px', color: 'var(--dsw-alias-label-primary, #fff)', display: 'flex', alignItems: 'center', gap: '8px' } },
1295
1339
  T_KEY(t, 'liveLog.modalTitle'),
1296
- React.createElement('span', {
1340
+ h('span', {
1297
1341
  style: {
1298
1342
  display: 'inline-block',
1299
1343
  width: '8px',
@@ -1304,14 +1348,14 @@ boxShadow: isLive ? '0 0 8px ' + statusColor : 'none'
1304
1348
  }
1305
1349
  })
1306
1350
  ),
1307
- React.createElement('div', { style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px', fontFamily: 'monospace' } },
1351
+ h('div', { style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px', fontFamily: 'monospace' } },
1308
1352
  (taskTitle || taskId) + ' · ' + (isLive ? T_KEY(t, 'liveLog.connecting') : (completed ? T_KEY(t, 'liveLog.completed') : status))
1309
1353
  )
1310
1354
  )
1311
1355
  ),
1312
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '12px' } },
1313
- React.createElement('label', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)', display: 'flex', alignItems: 'center', gap: '4px', cursor: 'pointer' } },
1314
- React.createElement('input', {
1356
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '12px' } },
1357
+ h('label', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)', display: 'flex', alignItems: 'center', gap: '4px', cursor: 'pointer' } },
1358
+ h('input', {
1315
1359
  type: 'checkbox',
1316
1360
  checked: Boolean(autoScroll),
1317
1361
  onChange: onToggleAutoScroll,
@@ -1319,7 +1363,7 @@ style: { cursor: 'pointer' }
1319
1363
  }),
1320
1364
  T_KEY(t, 'liveLog.autoScroll')
1321
1365
  ),
1322
- React.createElement('button', {
1366
+ h('button', {
1323
1367
  type: 'button',
1324
1368
  className: 'dsh-cron-icon-btn',
1325
1369
  style: { color: 'var(--dsw-alias-label-secondary, #888)', background: 'transparent', border: 'none', cursor: 'pointer', fontSize: '16px' },
@@ -1327,29 +1371,29 @@ onClick: onClose
1327
1371
  }, '✕')
1328
1372
  )
1329
1373
  ),
1330
- React.createElement('div', {
1374
+ h('div', {
1331
1375
  ref: terminalRef,
1332
1376
  style: { flex: 1, overflowY: 'auto', padding: '14px 16px', fontFamily: 'ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, monospace', fontSize: '12px', lineHeight: '1.5', background: 'var(--dsw-alias-bg-base, #000)' }
1333
1377
  },
1334
- (!logs || logs.length === 0) && React.createElement('div', {
1378
+ (!logs || logs.length === 0) && h('div', {
1335
1379
  style: { color: 'var(--dsw-alias-label-secondary, #888)', fontStyle: 'italic', padding: '20px 0', textAlign: 'center' }
1336
1380
  }, isLive ? T_KEY(t, 'liveLog.waiting') : 'No output captured for this run.'),
1337
1381
  logs && logs.length > 0 && logs.map((item, idx) => {
1338
1382
  const isErr = item.stream === 'stderr';
1339
1383
  const timeStr = item.ts ? new Date(item.ts).toLocaleTimeString() : '';
1340
- return React.createElement('div', {
1384
+ return h('div', {
1341
1385
  key: idx,
1342
1386
  style: { display: 'flex', gap: '8px', color: isErr ? 'var(--dsh-cron-danger, #f55)' : 'var(--dsh-cron-success, #5f5)', wordBreak: 'break-all', whiteSpace: 'pre-wrap' }
1343
1387
  },
1344
- timeStr && React.createElement('span', { style: { color: 'var(--dsw-alias-label-secondary, #555)', userSelect: 'none', flexShrink: 0 } }, '[' + timeStr + ']'),
1345
- React.createElement('span', { style: { flex: 1 } }, item.chunk || item.text || String(item))
1388
+ timeStr && h('span', { style: { color: 'var(--dsw-alias-label-secondary, #555)', userSelect: 'none', flexShrink: 0 } }, '[' + timeStr + ']'),
1389
+ h('span', { style: { flex: 1 } }, item.chunk || item.text || String(item))
1346
1390
  );
1347
1391
  })
1348
1392
  ),
1349
- React.createElement('div', {
1393
+ h('div', {
1350
1394
  style: { display: 'flex', justifyContent: 'flex-end', padding: '10px 16px', borderTop: '1px solid var(--dsw-alias-border-l2, #333)', background: 'var(--dsw-alias-bg-layer-2, #111)' }
1351
1395
  },
1352
- React.createElement('button', {
1396
+ h('button', {
1353
1397
  type: 'button',
1354
1398
  className: 'dsh-cron-btn dsh-cron-btn-secondary',
1355
1399
  style: { padding: '6px 14px', fontSize: '12px' },
@@ -1385,117 +1429,117 @@ const text = [
1385
1429
  ].join(String.fromCharCode(10));
1386
1430
  navigator.clipboard.writeText(text).catch(() => {});
1387
1431
  };
1388
- return React.createElement('div', {
1432
+ return h('div', {
1389
1433
  className: 'dsh-cron-modal-overlay',
1390
1434
  onClick: onClose
1391
1435
  },
1392
- React.createElement('div', {
1436
+ h('div', {
1393
1437
  className: 'dsh-cron-modal',
1394
1438
  style: { maxWidth: '780px', width: '92vw', maxHeight: '86vh', display: 'flex', flexDirection: 'column', background: 'var(--dsw-alias-bg-base, #111)', color: 'var(--dsw-alias-label-primary, #ddd)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '8px' },
1395
1439
  role: 'dialog',
1396
1440
  'aria-modal': 'true',
1397
1441
  onClick: (e) => e.stopPropagation()
1398
1442
  },
1399
- React.createElement('div', {
1443
+ h('div', {
1400
1444
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', padding: '14px 18px', borderBottom: '1px solid var(--dsw-alias-border-l2, #333)', background: 'var(--dsw-alias-bg-layer-2, #111)' }
1401
1445
  },
1402
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
1403
- React.createElement('span', { style: { fontSize: '20px' } }, '📊'),
1404
- React.createElement('div', null,
1405
- React.createElement('div', { style: { fontWeight: '600', fontSize: '15px', color: 'var(--dsw-alias-label-primary, #fff)' } },
1446
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
1447
+ h('span', { style: { fontSize: '20px' } }, '📊'),
1448
+ h('div', null,
1449
+ h('div', { style: { fontWeight: '600', fontSize: '15px', color: 'var(--dsw-alias-label-primary, #fff)' } },
1406
1450
  T_KEY(t, 'digest.modalTitle')
1407
1451
  ),
1408
- React.createElement('div', { style: { fontSize: '11.5px', color: 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px' } },
1452
+ h('div', { style: { fontSize: '11.5px', color: 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px' } },
1409
1453
  (T_KEY(t, 'digest.buttonTitle')) + ' · ' + (periodDays || 7) + 'd'
1410
1454
  )
1411
1455
  )
1412
1456
  ),
1413
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
1414
- React.createElement('button', {
1457
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
1458
+ h('button', {
1415
1459
  type: 'button',
1416
1460
  className: 'dsh-cron-btn-secondary',
1417
1461
  style: { padding: '4px 10px', fontSize: '12px', fontWeight: periodDays === 7 ? '600' : '400', background: periodDays === 7 ? 'var(--dsw-alias-bg-layer-3, #222)' : 'transparent' },
1418
1462
  onClick: () => onSelectPeriod && onSelectPeriod(7)
1419
1463
  }, T_KEY(t, 'digest.period7')),
1420
- React.createElement('button', {
1464
+ h('button', {
1421
1465
  type: 'button',
1422
1466
  className: 'dsh-cron-btn-secondary',
1423
1467
  style: { padding: '4px 10px', fontSize: '12px', fontWeight: periodDays === 30 ? '600' : '400', background: periodDays === 30 ? 'var(--dsw-alias-bg-layer-3, #222)' : 'transparent' },
1424
1468
  onClick: () => onSelectPeriod && onSelectPeriod(30)
1425
1469
  }, T_KEY(t, 'digest.period30')),
1426
- React.createElement('button', {
1470
+ h('button', {
1427
1471
  type: 'button',
1428
1472
  className: 'dsh-cron-icon-btn',
1429
1473
  onClick: onClose,
1430
1474
  style: { marginLeft: '8px' }
1431
- }, React.createElement('span', null, '✕'))
1475
+ }, h('span', null, '✕'))
1432
1476
  )
1433
1477
  ),
1434
- React.createElement('div', {
1478
+ h('div', {
1435
1479
  style: { padding: '16px 18px', overflowY: 'auto', flex: 1, display: 'flex', flexDirection: 'column', gap: '16px' }
1436
1480
  },
1437
- isLoading ? React.createElement('div', { style: { padding: '30px', textAlign: 'center', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'Loading digest metrics...') : React.createElement(React.Fragment, null,
1481
+ isLoading ? h('div', { style: { padding: '30px', textAlign: 'center', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'Loading digest metrics...') : h(React.Fragment, null,
1438
1482
  (() => {
1439
- const renderKpi = (label, val, sub, subCol) => React.createElement('div', { style: { background: 'var(--dsw-alias-bg-layer-2, #111)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '6px', padding: '10px 12px' } },
1440
- React.createElement('div', { style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #888)' } }, label),
1441
- React.createElement('div', { style: { fontSize: '18px', fontWeight: '700', color: 'var(--dsw-alias-label-primary, #fff)', marginTop: '4px' } }, val),
1442
- React.createElement('div', { style: { fontSize: '11px', color: subCol || 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px' } }, sub)
1483
+ const renderKpi = (label, val, sub, subCol) => h('div', { style: { background: 'var(--dsw-alias-bg-layer-2, #111)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '6px', padding: '10px 12px' } },
1484
+ h('div', { style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #888)' } }, label),
1485
+ h('div', { style: { fontSize: '18px', fontWeight: '700', color: 'var(--dsw-alias-label-primary, #fff)', marginTop: '4px' } }, val),
1486
+ h('div', { style: { fontSize: '11px', color: subCol || 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px' } }, sub)
1443
1487
  );
1444
- return React.createElement('div', { style: { display: 'grid', gridTemplateColumns: 'repeat(4, 1fr)', gap: '10px' } },
1488
+ return h('div', { style: { display: 'grid', gridTemplateColumns: 'repeat(4, 1fr)', gap: '10px' } },
1445
1489
  renderKpi(T_KEY(t, 'digest.executions'), digest.totalRuns, digest.successRate + '% SR', digest.successRate >= 90 ? 'var(--dsh-cron-success, #2a2)' : 'var(--dsh-cron-warning, #fa0)'),
1446
1490
  renderKpi(T_KEY(t, 'digest.tokens'), Number(digest.totalTokens || 0).toLocaleString(), 'LLM prompt+out'),
1447
1491
  renderKpi(T_KEY(t, 'digest.cost'), '$' + Number(digest.totalCostUsd || 0).toFixed(4), 'USD estimated'),
1448
1492
  renderKpi(T_KEY(t, 'digest.fleet'), digest.activeTasksCount, digest.pausedTasksCount + ' paused')
1449
1493
  );
1450
1494
  })(),
1451
- React.createElement('div', { style: { background: 'var(--dsw-alias-bg-layer-2, #111)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '6px', padding: '12px' } },
1452
- React.createElement('div', { style: { fontWeight: '600', fontSize: '13px', color: 'var(--dsh-cron-warning, #fa0)', marginBottom: '8px' } },
1495
+ h('div', { style: { background: 'var(--dsw-alias-bg-layer-2, #111)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '6px', padding: '12px' } },
1496
+ h('div', { style: { fontWeight: '600', fontSize: '13px', color: 'var(--dsh-cron-warning, #fa0)', marginBottom: '8px' } },
1453
1497
  '⚠️ ' + (T_KEY(t, 'digest.unstableTitle'))
1454
1498
  ),
1455
- (digest.topUnstableTasks && digest.topUnstableTasks.length > 0) ? React.createElement('div', { style: { display: 'flex', flexDirection: 'column', gap: '6px' } },
1456
- digest.topUnstableTasks.map((tItem, idx) => React.createElement('div', {
1499
+ (digest.topUnstableTasks && digest.topUnstableTasks.length > 0) ? h('div', { style: { display: 'flex', flexDirection: 'column', gap: '6px' } },
1500
+ digest.topUnstableTasks.map((tItem, idx) => h('div', {
1457
1501
  key: tItem.id || idx,
1458
1502
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', fontSize: '12px', padding: '6px 8px', background: 'var(--dsw-alias-bg-base, #111)', borderRadius: '4px', border: '1px solid var(--dsw-alias-border-l2, #222)' }
1459
1503
  },
1460
- React.createElement('span', { style: { fontFamily: 'monospace' } }, (idx + 1) + '. ' + (tItem.name || tItem.id)),
1461
- React.createElement('span', { style: { color: 'var(--dsh-cron-danger, #e33)', fontWeight: '600' } },
1504
+ h('span', { style: { fontFamily: 'monospace' } }, (idx + 1) + '. ' + (tItem.name || tItem.id)),
1505
+ h('span', { style: { color: 'var(--dsh-cron-danger, #e33)', fontWeight: '600' } },
1462
1506
  tItem.failures + ' fail (' + tItem.successRate + '% SR)'
1463
1507
  )
1464
1508
  ))
1465
- ) : React.createElement('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)' } }, '✓ All tasks healthy — 0 failures in window!')
1509
+ ) : h('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)' } }, '✓ All tasks healthy — 0 failures in window!')
1466
1510
  ),
1467
- React.createElement('div', { style: { background: 'var(--dsw-alias-bg-layer-2, #111)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '6px', padding: '12px' } },
1468
- React.createElement('div', { style: { fontWeight: '600', fontSize: '13px', color: 'var(--dsh-cron-info, #4af)', marginBottom: '8px' } },
1511
+ h('div', { style: { background: 'var(--dsw-alias-bg-layer-2, #111)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '6px', padding: '12px' } },
1512
+ h('div', { style: { fontWeight: '600', fontSize: '13px', color: 'var(--dsh-cron-info, #4af)', marginBottom: '8px' } },
1469
1513
  '💰 ' + (T_KEY(t, 'digest.expensiveTitle'))
1470
1514
  ),
1471
- (digest.topExpensiveTasks && digest.topExpensiveTasks.length > 0) ? React.createElement('div', { style: { display: 'flex', flexDirection: 'column', gap: '6px' } },
1472
- digest.topExpensiveTasks.map((tItem, idx) => React.createElement('div', {
1515
+ (digest.topExpensiveTasks && digest.topExpensiveTasks.length > 0) ? h('div', { style: { display: 'flex', flexDirection: 'column', gap: '6px' } },
1516
+ digest.topExpensiveTasks.map((tItem, idx) => h('div', {
1473
1517
  key: tItem.id || idx,
1474
1518
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', fontSize: '12px', padding: '6px 8px', background: 'var(--dsw-alias-bg-base, #111)', borderRadius: '4px', border: '1px solid var(--dsw-alias-border-l2, #222)' }
1475
1519
  },
1476
- React.createElement('span', { style: { fontFamily: 'monospace' } }, (idx + 1) + '. ' + (tItem.name || tItem.id)),
1477
- React.createElement('span', { style: { color: 'var(--dsw-alias-label-primary, #ddd)' } },
1520
+ h('span', { style: { fontFamily: 'monospace' } }, (idx + 1) + '. ' + (tItem.name || tItem.id)),
1521
+ h('span', { style: { color: 'var(--dsw-alias-label-primary, #ddd)' } },
1478
1522
  Number(tItem.tokens || 0).toLocaleString() + ' tok ($' + Number(tItem.costUsd || 0).toFixed(4) + ')'
1479
1523
  )
1480
1524
  ))
1481
- ) : React.createElement('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'No significant token consumption recorded.')
1525
+ ) : h('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'No significant token consumption recorded.')
1482
1526
  )
1483
1527
  )
1484
1528
  ),
1485
- React.createElement('div', {
1529
+ h('div', {
1486
1530
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', padding: '12px 18px', borderTop: '1px solid var(--dsw-alias-border-l2, #333)', background: 'var(--dsw-alias-bg-layer-2, #111)' }
1487
1531
  },
1488
- React.createElement('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)' } },
1532
+ h('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)' } },
1489
1533
  sendStatus || ''
1490
1534
  ),
1491
- React.createElement('div', { style: { display: 'flex', gap: '8px' } },
1492
- React.createElement('button', {
1535
+ h('div', { style: { display: 'flex', gap: '8px' } },
1536
+ h('button', {
1493
1537
  type: 'button',
1494
1538
  className: 'dsh-cron-btn-secondary',
1495
1539
  onClick: copyMarkdown,
1496
1540
  style: { padding: '6px 14px', fontSize: '12px' }
1497
1541
  }, T_KEY(t, 'digest.copyMarkdown')),
1498
- React.createElement('button', {
1542
+ h('button', {
1499
1543
  type: 'button',
1500
1544
  className: 'dsh-cron-btn-primary',
1501
1545
  onClick: onSendTelegram,
@@ -1520,70 +1564,70 @@ if (!isOpen) return null;
1520
1564
  const tab = activeTab || 'timeline';
1521
1565
  const timeline = timelineData || { buckets: [], totalRuns: 0, peakHoursCount: 0, maxConcurrent: 3 };
1522
1566
  const heatmap = heatmapData || { matrix: [], dayLabels: [], hourLabels: [], totalCostUsd: 0, totalTokens: 0, maxCostHour: 0 };
1523
- return React.createElement('div', {
1567
+ return h('div', {
1524
1568
  className: 'dsh-cron-modal-overlay',
1525
1569
  onClick: onClose
1526
1570
  },
1527
- React.createElement('div', {
1571
+ h('div', {
1528
1572
  className: 'dsh-cron-modal',
1529
1573
  style: { maxWidth: '960px', width: '94vw', maxHeight: '88vh', display: 'flex', flexDirection: 'column', background: 'var(--dsw-alias-bg-base, #111)', color: 'var(--dsw-alias-label-primary, #ddd)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '8px' },
1530
1574
  role: 'dialog',
1531
1575
  'aria-modal': 'true',
1532
1576
  onClick: (e) => e.stopPropagation()
1533
1577
  },
1534
- React.createElement('div', {
1578
+ h('div', {
1535
1579
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', padding: '14px 18px', borderBottom: '1px solid var(--dsw-alias-border-l2, #333)', background: 'var(--dsw-alias-bg-layer-2, #111)' }
1536
1580
  },
1537
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
1538
- React.createElement('span', { style: { fontSize: '20px' } }, tab === 'timeline' ? '⏱' : '🔥'),
1539
- React.createElement('div', null,
1540
- React.createElement('div', { style: { fontWeight: '600', fontSize: '15px', color: 'var(--dsw-alias-label-primary, #fff)' } },
1581
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
1582
+ h('span', { style: { fontSize: '20px' } }, tab === 'timeline' ? '⏱' : '🔥'),
1583
+ h('div', null,
1584
+ h('div', { style: { fontWeight: '600', fontSize: '15px', color: 'var(--dsw-alias-label-primary, #fff)' } },
1541
1585
  tab === 'timeline' ? (T_KEY(t, 'timeline.modalTitle')) : (T_KEY(t, 'heatmap.modalTitle'))
1542
1586
  ),
1543
- React.createElement('div', { style: { fontSize: '11.5px', color: 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px' } },
1587
+ h('div', { style: { fontSize: '11.5px', color: 'var(--dsw-alias-label-secondary, #888)', marginTop: '2px' } },
1544
1588
  tab === 'timeline'
1545
1589
  ? (timeline.totalRuns + ' runs projected · ' + (timeline.peakHoursCount ? '⚠️ ' + timeline.peakHoursCount + ' peak hours' : '✓ balanced concurrency'))
1546
1590
  : ('$' + Number(heatmap.totalCostUsd || 0).toFixed(4) + ' USD · ' + Number(heatmap.totalTokens || 0).toLocaleString() + ' tokens')
1547
1591
  )
1548
1592
  )
1549
1593
  ),
1550
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
1551
- React.createElement('button', {
1594
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
1595
+ h('button', {
1552
1596
  type: 'button',
1553
1597
  className: 'dsh-cron-btn-secondary',
1554
1598
  style: { padding: '4px 12px', fontSize: '12px', fontWeight: tab === 'timeline' ? '600' : '400', background: tab === 'timeline' ? 'var(--dsw-alias-bg-layer-3, #222)' : 'transparent' },
1555
1599
  onClick: () => onSelectTab && onSelectTab('timeline')
1556
1600
  }, '⏱ ' + (T_KEY(t, 'timeline.tabTimeline'))),
1557
- React.createElement('button', {
1601
+ h('button', {
1558
1602
  type: 'button',
1559
1603
  className: 'dsh-cron-btn-secondary',
1560
1604
  style: { padding: '4px 12px', fontSize: '12px', fontWeight: tab === 'heatmap' ? '600' : '400', background: tab === 'heatmap' ? 'var(--dsw-alias-bg-layer-3, #222)' : 'transparent' },
1561
1605
  onClick: () => onSelectTab && onSelectTab('heatmap')
1562
1606
  }, '🔥 ' + (T_KEY(t, 'heatmap.tabHeatmap'))),
1563
- React.createElement('button', {
1607
+ h('button', {
1564
1608
  type: 'button',
1565
1609
  className: 'dsh-cron-icon-btn',
1566
1610
  onClick: onClose,
1567
1611
  style: { marginLeft: '8px' }
1568
- }, React.createElement('span', null, '✕'))
1612
+ }, h('span', null, '✕'))
1569
1613
  )
1570
1614
  ),
1571
- React.createElement('div', {
1615
+ h('div', {
1572
1616
  style: { padding: '16px 18px', overflowY: 'auto', flex: 1, display: 'flex', flexDirection: 'column', gap: '14px' }
1573
1617
  },
1574
- isLoading ? React.createElement('div', { style: { padding: '40px', textAlign: 'center', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'Loading visualization data...') : (
1618
+ isLoading ? h('div', { style: { padding: '40px', textAlign: 'center', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'Loading visualization data...') : (
1575
1619
  tab === 'timeline' ? (
1576
- React.createElement('div', { style: { display: 'flex', flexDirection: 'column', gap: '8px' } },
1577
- React.createElement('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)', display: 'flex', justifyContent: 'space-between' } },
1578
- React.createElement('span', null, T_KEY(t, 'timeline.legendDesc')),
1579
- React.createElement('span', { style: { color: 'var(--dsh-cron-warning, #fa0)' } }, '⚠️ ' + (T_KEY(t, 'timeline.peakWarning')) + ' (' + timeline.maxConcurrent + ')')
1620
+ h('div', { style: { display: 'flex', flexDirection: 'column', gap: '8px' } },
1621
+ h('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)', display: 'flex', justifyContent: 'space-between' } },
1622
+ h('span', null, T_KEY(t, 'timeline.legendDesc')),
1623
+ h('span', { style: { color: 'var(--dsh-cron-warning, #fa0)' } }, '⚠️ ' + (T_KEY(t, 'timeline.peakWarning')) + ' (' + timeline.maxConcurrent + ')')
1580
1624
  ),
1581
- React.createElement('div', {
1625
+ h('div', {
1582
1626
  style: { display: 'grid', gridTemplateColumns: 'repeat(12, 1fr)', gap: '8px', marginTop: '6px' }
1583
1627
  },
1584
1628
  (timeline.buckets || []).map((b) => {
1585
1629
  const isPeak = b.isPeak, hasRuns = b.count > 0;
1586
- return React.createElement('div', {
1630
+ return h('div', {
1587
1631
  key: b.index,
1588
1632
  style: {
1589
1633
  background: isPeak ? 'color-mix(in srgb, var(--dsh-cron-danger, #e33) 12%, var(--dsw-alias-bg-layer-2, #111))' : (hasRuns ? 'var(--dsw-alias-bg-layer-2, #111)' : 'var(--dsw-alias-bg-base, #111)'),
@@ -1591,12 +1635,12 @@ border: isPeak ? '1px solid var(--dsh-cron-danger, #e33)' : (hasRuns ? '1px soli
1591
1635
  borderRadius: '6px', padding: '8px', minHeight: '75px', display: 'flex', flexDirection: 'column', justifyContent: 'space-between'
1592
1636
  }
1593
1637
  },
1594
- React.createElement('div', { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', fontSize: '11px' } },
1595
- React.createElement('span', { style: { fontWeight: '600', color: isPeak ? 'var(--dsh-cron-danger, #e33)' : 'var(--dsw-alias-label-primary, #fff)' } }, b.label),
1596
- hasRuns ? React.createElement('span', { style: { fontSize: '10px', padding: '1px 5px', borderRadius: '8px', background: isPeak ? 'var(--dsh-cron-danger, #e33)' : 'var(--dsw-alias-bg-layer-3, #222)', color: '#fff' } }, b.count) : null
1638
+ h('div', { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', fontSize: '11px' } },
1639
+ h('span', { style: { fontWeight: '600', color: isPeak ? 'var(--dsh-cron-danger, #e33)' : 'var(--dsw-alias-label-primary, #fff)' } }, b.label),
1640
+ hasRuns ? h('span', { style: { fontSize: '10px', padding: '1px 5px', borderRadius: '8px', background: isPeak ? 'var(--dsh-cron-danger, #e33)' : 'var(--dsw-alias-bg-layer-3, #222)', color: '#fff' } }, b.count) : null
1597
1641
  ),
1598
- React.createElement('div', { style: { display: 'flex', flexWrap: 'wrap', gap: '3px', marginTop: '4px' } },
1599
- (b.runs || []).slice(0, 3).map((r, rIdx) => React.createElement('span', {
1642
+ h('div', { style: { display: 'flex', flexWrap: 'wrap', gap: '3px', marginTop: '4px' } },
1643
+ (b.runs || []).slice(0, 3).map((r, rIdx) => h('span', {
1600
1644
  key: rIdx, title: (r.title || r.taskId) + ' (' + r.time + ')',
1601
1645
  style: { fontSize: '9.5px', fontFamily: 'monospace', padding: '1px 4px', borderRadius: '3px', background: 'var(--dsw-alias-bg-base, #111)', border: '1px solid var(--dsw-alias-border-l2, #333)', maxWidth: '100%', overflow: 'hidden', textOverflow: 'ellipsis', whiteSpace: 'nowrap' }
1602
1646
  }, r.title || r.taskId))
@@ -1606,36 +1650,36 @@ style: { fontSize: '9.5px', fontFamily: 'monospace', padding: '1px 4px', borderR
1606
1650
  )
1607
1651
  )
1608
1652
  ) : (
1609
- React.createElement('div', { style: { display: 'flex', flexDirection: 'column', gap: '10px' } },
1610
- React.createElement('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)', display: 'flex', justifyContent: 'space-between' } },
1611
- React.createElement('span', null, T_KEY(t, 'heatmap.matrixDesc')),
1612
- React.createElement('span', null, 'Max hour spend: $' + Number(heatmap.maxCostHour || 0).toFixed(4))
1653
+ h('div', { style: { display: 'flex', flexDirection: 'column', gap: '10px' } },
1654
+ h('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #888)', display: 'flex', justifyContent: 'space-between' } },
1655
+ h('span', null, T_KEY(t, 'heatmap.matrixDesc')),
1656
+ h('span', null, 'Max hour spend: $' + Number(heatmap.maxCostHour || 0).toFixed(4))
1613
1657
  ),
1614
- React.createElement('div', {
1658
+ h('div', {
1615
1659
  style: { overflowX: 'auto', paddingBottom: '8px' }
1616
1660
  },
1617
- React.createElement('table', {
1661
+ h('table', {
1618
1662
  style: { borderCollapse: 'collapse', width: '100%', minWidth: '700px', fontSize: '10.5px' }
1619
1663
  },
1620
- React.createElement('thead', null,
1621
- React.createElement('tr', null,
1622
- React.createElement('th', { style: { padding: '4px 6px', textAlign: 'left', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'Day'),
1623
- Array.from({ length: 24 }, (_, h) => React.createElement('th', {
1664
+ h('thead', null,
1665
+ h('tr', null,
1666
+ h('th', { style: { padding: '4px 6px', textAlign: 'left', color: 'var(--dsw-alias-label-secondary, #888)' } }, 'Day'),
1667
+ Array.from({ length: 24 }, (_, h) => h('th', {
1624
1668
  key: h,
1625
1669
  style: { padding: '4px 2px', textAlign: 'center', color: 'var(--dsw-alias-label-secondary, #888)', fontWeight: '400' }
1626
1670
  }, String(h).padStart(2, '0')))
1627
1671
  )
1628
1672
  ),
1629
- React.createElement('tbody', null,
1630
- (heatmap.matrix || []).map((row, dIdx) => React.createElement('tr', { key: dIdx },
1631
- React.createElement('td', { style: { padding: '4px 6px', fontWeight: '600', color: 'var(--dsw-alias-label-primary, #ddd)' } }, (heatmap.dayLabels && heatmap.dayLabels[dIdx]) || 'Day'),
1673
+ h('tbody', null,
1674
+ (heatmap.matrix || []).map((row, dIdx) => h('tr', { key: dIdx },
1675
+ h('td', { style: { padding: '4px 6px', fontWeight: '600', color: 'var(--dsw-alias-label-primary, #ddd)' } }, (heatmap.dayLabels && heatmap.dayLabels[dIdx]) || 'Day'),
1632
1676
  row.map((cell, hIdx) => {
1633
1677
  const intensity = cell.costIntensity || 0;
1634
1678
  const hasSpend = cell.costUsd > 0;
1635
1679
  const bg = hasSpend
1636
1680
  ? 'color-mix(in srgb, var(--dsh-cron-primary, #4af) ' + Math.max(15, Math.round(intensity * 100)) + '%, transparent)'
1637
1681
  : 'transparent';
1638
- return React.createElement('td', {
1682
+ return h('td', {
1639
1683
  key: hIdx,
1640
1684
  title: cell.dayLabel + ' ' + cell.hourLabel + ': $' + cell.costUsd + ' (' + cell.tokens.toLocaleString() + ' tokens, ' + cell.runs + ' runs)',
1641
1685
  style: {
@@ -1645,7 +1689,7 @@ background: bg,
1645
1689
  border: '1px solid var(--dsw-alias-border-l2, #222)',
1646
1690
  cursor: hasSpend ? 'pointer' : 'default'
1647
1691
  }
1648
- }, hasSpend ? React.createElement('span', { style: { fontSize: '9px', color: intensity > 0.5 ? '#fff' : 'var(--dsw-alias-label-primary, #ddd)' } }, '$' + (cell.costUsd >= 0.01 ? cell.costUsd.toFixed(2) : cell.costUsd.toFixed(3).slice(1))) : '·');
1692
+ }, hasSpend ? h('span', { style: { fontSize: '9px', color: intensity > 0.5 ? '#fff' : 'var(--dsw-alias-label-primary, #ddd)' } }, '$' + (cell.costUsd >= 0.01 ? cell.costUsd.toFixed(2) : cell.costUsd.toFixed(3).slice(1))) : '·');
1649
1693
  })
1650
1694
  ))
1651
1695
  )
@@ -1655,10 +1699,10 @@ cursor: hasSpend ? 'pointer' : 'default'
1655
1699
  )
1656
1700
  )
1657
1701
  ),
1658
- React.createElement('div', {
1702
+ h('div', {
1659
1703
  style: { display: 'flex', justifyContent: 'flex-end', padding: '12px 18px', borderTop: '1px solid var(--dsw-alias-border-l2, #333)', background: 'var(--dsw-alias-bg-layer-2, #111)' }
1660
1704
  },
1661
- React.createElement('button', {
1705
+ h('button', {
1662
1706
  type: 'button',
1663
1707
  className: 'dsh-cron-btn-secondary',
1664
1708
  onClick: onClose,
@@ -1716,6 +1760,8 @@ const [formOnSuccess, setFormOnSuccess] = React.useState('');
1716
1760
  const [formOnFailure, setFormOnFailure] = React.useState('');
1717
1761
  const [formDependsOn, setFormDependsOn] = React.useState('');
1718
1762
  const [formJoinPolicy, setFormJoinPolicy] = React.useState('all_success');
1763
+ const [formElseTask, setFormElseTask] = React.useState('');
1764
+ const [formAutoHeal, setFormAutoHeal] = React.useState(false);
1719
1765
  const [formAdaptiveEnabled, setFormAdaptiveEnabled] = React.useState(false);
1720
1766
  const [formAdaptiveMinInterval, setFormAdaptiveMinInterval] = React.useState('5m');
1721
1767
  const [formAdaptiveMaxInterval, setFormAdaptiveMaxInterval] = React.useState('2h');
@@ -2580,6 +2626,24 @@ alert(e.message || 'Error retrying delivery');
2580
2626
  setRetryingDeliveryId(null);
2581
2627
  }
2582
2628
  };
2629
+ const handleApplyDoctorFix = async (taskId, fix) => {
2630
+ try {
2631
+ const { res, data } = await fetchJsonWithTimeout('/dsh-cron/tasks/' + encodeURIComponent(taskId) + '/doctor/apply', {
2632
+ method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ fix }),
2633
+ });
2634
+ if (data && data.ok) { alert('Doctor fix applied successfully! Task code updated.'); await loadTaskHistory(taskId); await fetchTasks(); }
2635
+ else { alert(data?.error || 'Failed to apply doctor fix'); }
2636
+ } catch (e) { alert(e.message || 'Error applying doctor fix'); }
2637
+ };
2638
+ const handleRevertDoctorFix = async (taskId) => {
2639
+ try {
2640
+ const { res, data } = await fetchJsonWithTimeout('/dsh-cron/tasks/' + encodeURIComponent(taskId) + '/doctor/revert', {
2641
+ method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({}),
2642
+ });
2643
+ if (data && data.ok) { alert('Reverted to previous version successfully!'); await loadTaskHistory(taskId); await fetchTasks(); }
2644
+ else { alert(data?.error || 'Failed to revert doctor fix'); }
2645
+ } catch (e) { alert(e.message || 'Error reverting doctor fix'); }
2646
+ };
2583
2647
  const handleResolveUncertain = async (taskId, runId, resolution) => {
2584
2648
  try {
2585
2649
  const { res, data } = await fetchJsonWithTimeout('/dsh-cron/tasks/' + encodeURIComponent(taskId) + '/resolve-uncertain', {
@@ -2947,82 +3011,82 @@ setTimelineLoading(false);
2947
3011
  const onSelectTimelineTab = (tab) => {
2948
3012
  setTimelineTab(tab);
2949
3013
  };
2950
- return React.createElement('div', { className: 'dsh-cron-overlay' },
2951
- React.createElement('div', { className: 'dsh-cron-container' },
2952
- React.createElement('div', { className: 'dsh-cron-top-bar' },
2953
- React.createElement('button', {
3014
+ return h('div', { className: 'dsh-cron-overlay' },
3015
+ h('div', { className: 'dsh-cron-container' },
3016
+ h('div', { className: 'dsh-cron-top-bar' },
3017
+ h('button', {
2954
3018
  type: 'button',
2955
3019
  className: 'dsh-cron-back-btn',
2956
3020
  title: T_KEY(t, 'panel.back'),
2957
3021
  onClick: () => { if (onClose) onClose(); else toggle.set(false); }
2958
3022
  },
2959
- React.createElement('span', svgProps(BACK_ICON)),
2960
- React.createElement('span', null, T_KEY(t, 'panel.back'))
3023
+ h('span', svgProps(BACK_ICON)),
3024
+ h('span', null, T_KEY(t, 'panel.back'))
2961
3025
  )
2962
3026
  ),
2963
- React.createElement('div', { className: 'dsh-cron-header' },
2964
- React.createElement('div', null,
2965
- React.createElement('div', { className: 'dsh-cron-title' }, T_KEY(t, 'panel.title')),
2966
- React.createElement('div', { className: 'dsh-cron-subtitle' }, T_KEY(t, 'panel.subtitle'))
3027
+ h('div', { className: 'dsh-cron-header' },
3028
+ h('div', null,
3029
+ h('div', { className: 'dsh-cron-title' }, T_KEY(t, 'panel.title')),
3030
+ h('div', { className: 'dsh-cron-subtitle' }, T_KEY(t, 'panel.subtitle'))
2967
3031
  ),
2968
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
2969
- React.createElement('button', {
3032
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '10px' } },
3033
+ h('button', {
2970
3034
  type: 'button',
2971
3035
  className: 'dsh-cron-btn-secondary',
2972
3036
  style: { display: 'flex', alignItems: 'center', gap: '6px', height: '36px', padding: '0 12px' },
2973
3037
  title: T_KEY(t, 'timeline.buttonTitle'),
2974
3038
  onClick: () => openTimelineModal('timeline')
2975
3039
  },
2976
- React.createElement('span', { style: { fontSize: '14px' } }, '⏱'),
3040
+ h('span', { style: { fontSize: '14px' } }, '⏱'),
2977
3041
  T_KEY(t, 'timeline.buttonLabel')
2978
3042
  ),
2979
- React.createElement('button', {
3043
+ h('button', {
2980
3044
  type: 'button',
2981
3045
  className: 'dsh-cron-btn-secondary',
2982
3046
  style: { display: 'flex', alignItems: 'center', gap: '6px', height: '36px', padding: '0 12px' },
2983
3047
  title: T_KEY(t, 'digest.buttonTitle'),
2984
3048
  onClick: openAnalyticsDigest
2985
3049
  },
2986
- React.createElement('span', { style: { fontSize: '14px' } }, '📊'),
3050
+ h('span', { style: { fontSize: '14px' } }, '📊'),
2987
3051
  T_KEY(t, 'digest.buttonLabel')
2988
3052
  ),
2989
- React.createElement('button', {
3053
+ h('button', {
2990
3054
  type: 'button',
2991
3055
  className: 'dsh-cron-btn-secondary',
2992
3056
  style: { display: 'flex', alignItems: 'center', gap: '6px', height: '36px', padding: '0 14px' },
2993
3057
  title: T_KEY(t, 'actions.settings'),
2994
3058
  onClick: openSettingsModal
2995
3059
  },
2996
- React.createElement('span', { style: { display: 'flex', alignItems: 'center', color: 'var(--dsh-cron-info)' }, ...iconHtml(ICON_TELEGRAM) }),
3060
+ h('span', { style: { display: 'flex', alignItems: 'center', color: 'var(--dsh-cron-info)' }, ...iconHtml(ICON_TELEGRAM) }),
2997
3061
  T_KEY(t, 'actions.settings')
2998
3062
  ),
2999
- React.createElement('div', { style: { position: 'relative' } },
3000
- React.createElement('button', { className: 'dsh-cron-create-btn', onClick: () => setDropdownOpen(!dropdownOpen) },
3063
+ h('div', { style: { position: 'relative' } },
3064
+ h('button', { className: 'dsh-cron-create-btn', onClick: () => setDropdownOpen(!dropdownOpen) },
3001
3065
  T_KEY(t, 'actions.create'),
3002
- React.createElement('span', iconHtml(ICON_CHEVRON_DOWN))
3066
+ h('span', iconHtml(ICON_CHEVRON_DOWN))
3003
3067
  ),
3004
- dropdownOpen && React.createElement('div', { className: 'dsh-cron-dropdown' },
3005
- React.createElement('button', { className: 'dsh-cron-dropdown-item', onClick: openDshModal }, T_KEY(t, 'actions.createWithDsh')),
3006
- React.createElement('button', { className: 'dsh-cron-dropdown-item', onClick: () => openManualModal(null) }, T_KEY(t, 'actions.setupManually'))
3068
+ dropdownOpen && h('div', { className: 'dsh-cron-dropdown' },
3069
+ h('button', { className: 'dsh-cron-dropdown-item', onClick: openDshModal }, T_KEY(t, 'actions.createWithDsh')),
3070
+ h('button', { className: 'dsh-cron-dropdown-item', onClick: () => openManualModal(null) }, T_KEY(t, 'actions.setupManually'))
3007
3071
  )
3008
3072
  ),
3009
- React.createElement('button', {
3073
+ h('button', {
3010
3074
  type: 'button',
3011
3075
  className: 'dsh-cron-icon-btn',
3012
3076
  title: T_KEY(t, 'transfer.exportTitle'),
3013
3077
  'aria-label': T_KEY(t, 'transfer.exportTitle'),
3014
3078
  disabled: transferBusy,
3015
3079
  onClick: handleExport
3016
- }, React.createElement('span', svgProps(ICON_DOWNLOAD))),
3017
- React.createElement('button', {
3080
+ }, h('span', svgProps(ICON_DOWNLOAD))),
3081
+ h('button', {
3018
3082
  type: 'button',
3019
3083
  className: 'dsh-cron-icon-btn',
3020
3084
  title: T_KEY(t, 'transfer.importTitle'),
3021
3085
  'aria-label': T_KEY(t, 'transfer.importTitle'),
3022
3086
  disabled: transferBusy,
3023
3087
  onClick: () => { if (importFileRef.current) importFileRef.current.click(); }
3024
- }, React.createElement('span', svgProps(ICON_UPLOAD))),
3025
- React.createElement('input', {
3088
+ }, h('span', svgProps(ICON_UPLOAD))),
3089
+ h('input', {
3026
3090
  type: 'file',
3027
3091
  accept: '.json,application/json',
3028
3092
  ref: importFileRef,
@@ -3031,9 +3095,9 @@ onChange: handleImportFile
3031
3095
  })
3032
3096
  )
3033
3097
  ),
3034
- React.createElement('div', { className: 'dsh-cron-search-bar' },
3035
- React.createElement('span', { className: 'dsh-cron-search-icon', ...iconHtml(ICON_SEARCH) }),
3036
- React.createElement('input', {
3098
+ h('div', { className: 'dsh-cron-search-bar' },
3099
+ h('span', { className: 'dsh-cron-search-icon', ...iconHtml(ICON_SEARCH) }),
3100
+ h('input', {
3037
3101
  className: 'dsh-cron-search-input',
3038
3102
  type: 'search',
3039
3103
  'aria-label': T_KEY(t, 'search.placeholder'),
@@ -3042,27 +3106,27 @@ value: query,
3042
3106
  onChange: (e) => setQuery(e.target.value)
3043
3107
  })
3044
3108
  ),
3045
- stats && React.createElement('div', { className: 'dsh-cron-stats-bar' },
3046
- React.createElement('div', { className: 'dsh-cron-stat-card' },
3047
- React.createElement('div', { className: 'dsh-cron-stat-val' }, stats.activeTasks || 0),
3048
- React.createElement('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.activeTasks'))
3109
+ stats && h('div', { className: 'dsh-cron-stats-bar' },
3110
+ h('div', { className: 'dsh-cron-stat-card' },
3111
+ h('div', { className: 'dsh-cron-stat-val' }, stats.activeTasks || 0),
3112
+ h('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.activeTasks'))
3049
3113
  ),
3050
- React.createElement('div', { className: 'dsh-cron-stat-card' },
3051
- React.createElement('div', { className: 'dsh-cron-stat-val' }, stats.totalRuns || 0),
3052
- React.createElement('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.totalRuns'))
3114
+ h('div', { className: 'dsh-cron-stat-card' },
3115
+ h('div', { className: 'dsh-cron-stat-val' }, stats.totalRuns || 0),
3116
+ h('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.totalRuns'))
3053
3117
  ),
3054
- React.createElement('div', { className: 'dsh-cron-stat-card' },
3055
- React.createElement('div', { className: 'dsh-cron-stat-val' }, (stats.totalTokens || 0).toLocaleString()),
3056
- React.createElement('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.totalTokens'))
3118
+ h('div', { className: 'dsh-cron-stat-card' },
3119
+ h('div', { className: 'dsh-cron-stat-val' }, (stats.totalTokens || 0).toLocaleString()),
3120
+ h('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.totalTokens'))
3057
3121
  ),
3058
- React.createElement('div', { className: 'dsh-cron-stat-card' },
3059
- React.createElement('div', { className: 'dsh-cron-stat-val', style: { color: 'var(--dsh-cron-success)' } }, '$' + (stats.totalCostUsd || 0).toFixed(4)),
3060
- React.createElement('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.totalCost'))
3122
+ h('div', { className: 'dsh-cron-stat-card' },
3123
+ h('div', { className: 'dsh-cron-stat-val', style: { color: 'var(--dsh-cron-success)' } }, '$' + (stats.totalCostUsd || 0).toFixed(4)),
3124
+ h('div', { className: 'dsh-cron-stat-lbl' }, T_KEY(t, 'stats.totalCost'))
3061
3125
  )
3062
3126
  ),
3063
- React.createElement('div', { className: 'dsh-cron-tabs' },
3127
+ h('div', { className: 'dsh-cron-tabs' },
3064
3128
  ['all', 'active', 'paused', 'completed'].map((tabName) =>
3065
- React.createElement('button', {
3129
+ h('button', {
3066
3130
  key: tabName,
3067
3131
  className: 'dsh-cron-tab',
3068
3132
  'data-active': tab === tabName ? 'true' : undefined,
@@ -3074,8 +3138,8 @@ tabName === 'all' ? T_KEY(t, 'tabs.all')
3074
3138
  : T_KEY(t, 'tabs.completed'))
3075
3139
  )
3076
3140
  ),
3077
- React.createElement('div', { className: 'dsh-cron-filters' },
3078
- React.createElement('button', {
3141
+ h('div', { className: 'dsh-cron-filters' },
3142
+ h('button', {
3079
3143
  type: 'button',
3080
3144
  className: 'dsh-cron-filter-toggle',
3081
3145
  'aria-expanded': filtersOpen ? 'true' : 'false',
@@ -3084,73 +3148,73 @@ onClick: () => setFiltersOpen(!filtersOpen)
3084
3148
  T_KEY(t, 'filters.title'),
3085
3149
  (filterType || filterModel || filterChannel) ? ' •' : ''
3086
3150
  ),
3087
- filtersOpen && React.createElement('div', { className: 'dsh-cron-filter-panel' },
3088
- React.createElement('label', { className: 'dsh-cron-filter-field' },
3089
- React.createElement('span', null, T_KEY(t, 'filters.type')),
3090
- React.createElement('select', {
3151
+ filtersOpen && h('div', { className: 'dsh-cron-filter-panel' },
3152
+ h('label', { className: 'dsh-cron-filter-field' },
3153
+ h('span', null, T_KEY(t, 'filters.type')),
3154
+ h('select', {
3091
3155
  value: filterType,
3092
3156
  onChange: (e) => setFilterType(e.target.value)
3093
3157
  },
3094
- React.createElement('option', { value: '' }, T_KEY(t, 'filters.any')),
3095
- ...filterTypeOptions.map((value) => React.createElement('option', { key: value, value }, value))
3158
+ h('option', { value: '' }, T_KEY(t, 'filters.any')),
3159
+ ...filterTypeOptions.map((value) => h('option', { key: value, value }, value))
3096
3160
  )
3097
3161
  ),
3098
- React.createElement('label', { className: 'dsh-cron-filter-field' },
3099
- React.createElement('span', null, T_KEY(t, 'filters.model')),
3100
- React.createElement('select', {
3162
+ h('label', { className: 'dsh-cron-filter-field' },
3163
+ h('span', null, T_KEY(t, 'filters.model')),
3164
+ h('select', {
3101
3165
  value: filterModel,
3102
3166
  onChange: (e) => setFilterModel(e.target.value)
3103
3167
  },
3104
- React.createElement('option', { value: '' }, T_KEY(t, 'filters.any')),
3105
- ...filterModelOptions.map((value) => React.createElement('option', { key: value, value }, value))
3168
+ h('option', { value: '' }, T_KEY(t, 'filters.any')),
3169
+ ...filterModelOptions.map((value) => h('option', { key: value, value }, value))
3106
3170
  )
3107
3171
  ),
3108
- React.createElement('label', { className: 'dsh-cron-filter-field' },
3109
- React.createElement('span', null, T_KEY(t, 'filters.channel')),
3110
- React.createElement('select', {
3172
+ h('label', { className: 'dsh-cron-filter-field' },
3173
+ h('span', null, T_KEY(t, 'filters.channel')),
3174
+ h('select', {
3111
3175
  value: filterChannel,
3112
3176
  onChange: (e) => setFilterChannel(e.target.value)
3113
3177
  },
3114
- React.createElement('option', { value: '' }, T_KEY(t, 'filters.any')),
3115
- ...DELIVERY_CHANNELS.map((id) => React.createElement('option', { key: id, value: id }, T_KEY(t, CHANNEL_LABEL_KEYS[id])))
3178
+ h('option', { value: '' }, T_KEY(t, 'filters.any')),
3179
+ ...DELIVERY_CHANNELS.map((id) => h('option', { key: id, value: id }, T_KEY(t, CHANNEL_LABEL_KEYS[id])))
3116
3180
  )
3117
3181
  )
3118
3182
  )
3119
3183
  ),
3120
- fetchError ? React.createElement('div', {
3184
+ fetchError ? h('div', {
3121
3185
  className: 'dsh-cron-status-banner',
3122
3186
  'data-type': 'error',
3123
3187
  style: { margin: '8px 0', display: 'flex', alignItems: 'center', justifyContent: 'space-between' }
3124
3188
  },
3125
- React.createElement('span', null, T_KEY(t, 'banner.loadError', { error: fetchError })),
3126
- React.createElement('button', {
3189
+ h('span', null, T_KEY(t, 'banner.loadError', { error: fetchError })),
3190
+ h('button', {
3127
3191
  type: 'button',
3128
3192
  className: 'dsh-cron-btn-secondary',
3129
3193
  style: { marginLeft: '8px', padding: '2px 8px', fontSize: '12px' },
3130
3194
  onClick: () => fetchTasks()
3131
3195
  }, T_KEY(t, 'banner.retry'))
3132
3196
  ) : null,
3133
- (filterType || filterModel || filterChannel) ? React.createElement('div', {
3197
+ (filterType || filterModel || filterChannel) ? h('div', {
3134
3198
  className: 'dsh-cron-filter-summary',
3135
3199
  style: { fontSize: '12px', color: 'var(--dsw-alias-label-tertiary, #888)', marginBottom: '8px', display: 'flex', gap: '8px', alignItems: 'center' }
3136
3200
  },
3137
- React.createElement('span', null, T_KEY(t, 'filters.showing', { shown: visibleTasks.length, total: tasks.length })),
3138
- React.createElement('button', {
3201
+ h('span', null, T_KEY(t, 'filters.showing', { shown: visibleTasks.length, total: tasks.length })),
3202
+ h('button', {
3139
3203
  type: 'button',
3140
3204
  className: 'dsh-cron-btn-secondary',
3141
3205
  style: { padding: '2px 8px', fontSize: '11px' },
3142
3206
  onClick: resetFilters
3143
3207
  }, T_KEY(t, 'filters.reset'))
3144
3208
  ) : null,
3145
- React.createElement('div', { className: 'dsh-cron-task-list' },
3209
+ h('div', { className: 'dsh-cron-task-list' },
3146
3210
  loading && tasks.length === 0
3147
- ? React.createElement('div', { style: { color: 'var(--dsw-alias-label-tertiary, #888)', padding: '16px 0', fontSize: '14px' } }, T_KEY(t, 'list.loading'))
3211
+ ? h('div', { style: { color: 'var(--dsw-alias-label-tertiary, #888)', padding: '16px 0', fontSize: '14px' } }, T_KEY(t, 'list.loading'))
3148
3212
  : tasks.length === 0
3149
- ? React.createElement('div', { style: { color: 'var(--dsw-alias-label-tertiary, #777)', padding: '16px 0', fontSize: '14px' } }, T_KEY(t, 'list.empty'))
3213
+ ? h('div', { style: { color: 'var(--dsw-alias-label-tertiary, #777)', padding: '16px 0', fontSize: '14px' } }, T_KEY(t, 'list.empty'))
3150
3214
  : visibleTasks.length === 0
3151
- ? React.createElement('div', { style: { color: 'var(--dsw-alias-label-tertiary, #777)', padding: '16px 0', fontSize: '14px', display: 'flex', gap: '10px', alignItems: 'center' } },
3152
- React.createElement('span', null, T_KEY(t, 'filters.empty')),
3153
- React.createElement('button', {
3215
+ ? h('div', { style: { color: 'var(--dsw-alias-label-tertiary, #777)', padding: '16px 0', fontSize: '14px', display: 'flex', gap: '10px', alignItems: 'center' } },
3216
+ h('span', null, T_KEY(t, 'filters.empty')),
3217
+ h('button', {
3154
3218
  type: 'button',
3155
3219
  className: 'dsh-cron-btn-secondary',
3156
3220
  style: { padding: '2px 8px', fontSize: '12px' },
@@ -3158,7 +3222,7 @@ onClick: resetFilters
3158
3222
  }, T_KEY(t, 'filters.reset'))
3159
3223
  )
3160
3224
  : visibleTasks.map((task) =>
3161
- React.createElement('div', {
3225
+ h('div', {
3162
3226
  key: task.id,
3163
3227
  className: 'dsh-cron-task-item',
3164
3228
  'data-task-id': task.id,
@@ -3174,127 +3238,127 @@ openEditModal(task);
3174
3238
  }
3175
3239
  }
3176
3240
  },
3177
- isConfigManaged(task) ? null : React.createElement('button', {
3241
+ isConfigManaged(task) ? null : h('button', {
3178
3242
  type: 'button',
3179
3243
  className: 'dsh-cron-task-status-btn' + (task.running ? ' dsh-cron-pulse' : ''),
3180
3244
  'data-active': task.status === 'active' ? 'true' : undefined,
3181
3245
  title: task.status === 'active' ? T_KEY(t, 'actions.pause') : T_KEY(t, 'actions.resume'),
3182
3246
  'aria-label': task.status === 'active' ? T_KEY(t, 'actions.pause') : T_KEY(t, 'actions.resume'),
3183
3247
  onClick: (e) => { e.stopPropagation(); handleToggleTask(task.id); }
3184
- }, React.createElement('span', svgProps(task.status === 'active' ? ICON_PAUSE : ICON_PLAY))),
3185
- React.createElement('div', { className: 'dsh-cron-task-info' },
3186
- React.createElement('div', { className: 'dsh-cron-task-title' },
3248
+ }, h('span', svgProps(task.status === 'active' ? ICON_PAUSE : ICON_PLAY))),
3249
+ h('div', { className: 'dsh-cron-task-info' },
3250
+ h('div', { className: 'dsh-cron-task-title' },
3187
3251
  task.title,
3188
- React.createElement('span', {
3252
+ h('span', {
3189
3253
  className: 'dsh-cron-type-tag',
3190
3254
  style: task.type === 'script'
3191
3255
  ? { background: 'var(--dsh-cron-info-bg)', color: 'var(--dsh-cron-info)' }
3192
3256
  : { background: 'var(--dsh-cron-success-bg)', color: 'var(--dsh-cron-success)' }
3193
3257
  }, task.type === 'script' ? T_KEY(t, 'list.typeShell') : T_KEY(t, 'list.typeLlm')),
3194
- task.model ? React.createElement('span', { className: 'dsh-cron-task-model-tag' }, task.model.split('/').pop()) : null,
3195
- task.oneShot ? React.createElement('span', { className: 'dsh-cron-oneshot-tag' }, T_KEY(t, 'list.oneShot')) : null,
3196
- isConfigManaged(task) ? React.createElement('span', {
3258
+ task.model ? h('span', { className: 'dsh-cron-task-model-tag' }, task.model.split('/').pop()) : null,
3259
+ task.oneShot ? h('span', { className: 'dsh-cron-oneshot-tag' }, T_KEY(t, 'list.oneShot')) : null,
3260
+ isConfigManaged(task) ? h('span', {
3197
3261
  className: 'dsh-cron-config-tag',
3198
3262
  title: T_KEY(t, 'list.configManagedHint')
3199
3263
  }, T_KEY(t, 'list.configManaged')) : null,
3200
- task.lastDurationMs > 0 ? React.createElement('span', { className: 'dsh-cron-cost-tag', title: 'Last execution duration' }, task.lastDurationMs + 'ms') : null,
3201
- task.onSuccess ? React.createElement('span', { className: 'dsh-cron-type-tag dsh-cron-tag-success', title: 'On success: triggers ' + task.onSuccess }, '➜ ' + task.onSuccess) : null,
3202
- task.onFailure ? React.createElement('span', { className: 'dsh-cron-type-tag dsh-cron-tag-failure', title: 'On failure: triggers ' + task.onFailure }, '↳ ' + task.onFailure) : null,
3203
- (task.dependsOn && (Array.isArray(task.dependsOn) ? task.dependsOn.length > 0 : Boolean(task.dependsOn))) ? React.createElement('span', { className: 'dsh-cron-type-tag dsh-cron-tag-heartbeat', title: 'Depends on: ' + (Array.isArray(task.dependsOn) ? task.dependsOn.join(', ') : task.dependsOn) }, '⛓️ ' + (Array.isArray(task.dependsOn) ? task.dependsOn.join(', ') : task.dependsOn)) : null,
3204
- task.adaptive?.enabled ? React.createElement('span', {
3264
+ task.lastDurationMs > 0 ? h('span', { className: 'dsh-cron-cost-tag', title: 'Last execution duration' }, task.lastDurationMs + 'ms') : null,
3265
+ task.onSuccess ? h('span', { className: 'dsh-cron-type-tag dsh-cron-tag-success', title: 'On success: triggers ' + task.onSuccess }, '➜ ' + task.onSuccess) : null,
3266
+ task.onFailure ? h('span', { className: 'dsh-cron-type-tag dsh-cron-tag-failure', title: 'On failure: triggers ' + task.onFailure }, '↳ ' + task.onFailure) : null,
3267
+ (task.dependsOn && (Array.isArray(task.dependsOn) ? task.dependsOn.length > 0 : Boolean(task.dependsOn))) ? h('span', { className: 'dsh-cron-type-tag dsh-cron-tag-heartbeat', title: 'Depends on: ' + (Array.isArray(task.dependsOn) ? task.dependsOn.join(', ') : task.dependsOn) }, '⛓️ ' + (Array.isArray(task.dependsOn) ? task.dependsOn.join(', ') : task.dependsOn)) : null,
3268
+ task.adaptive?.enabled ? h('span', {
3205
3269
  className: 'dsh-cron-type-tag' + (task.adaptiveState?.backedOff ? ' dsh-cron-tag-failure' : ' dsh-cron-tag-success'),
3206
3270
  title: 'Adaptive: ' + (task.adaptiveState?.effectiveIntervalStr || task.adaptive.minInterval || '5m') + ' (idle: ' + (task.adaptiveState?.idleCount || 0) + ')'
3207
3271
  }, (task.adaptiveState?.backedOff ? '⏳ ' : '⚡ ') + (task.adaptiveState?.effectiveIntervalStr || task.adaptive.minInterval || '5m')) : null,
3208
- task.heartbeatIntervalSeconds > 0 ? React.createElement('span', { className: 'dsh-cron-type-tag dsh-cron-tag-heartbeat', title: 'Heartbeat: every ' + task.heartbeatIntervalSeconds + 's' }, '💓 ' + task.heartbeatIntervalSeconds + 's') : null,
3209
- task.targetSessionId ? React.createElement('span', { className: 'dsh-cron-type-tag dsh-cron-tag-session', title: 'Target session: ' + task.targetSessionId + (task.targetSessionReset && task.targetSessionReset !== 'never' ? ' (' + task.targetSessionReset + ')' : '') }, '🧵 ' + task.targetSessionId) : null,
3210
- task.preflightType && task.preflightType !== 'none' ? React.createElement('span', { className: 'dsh-cron-type-tag dsh-cron-tag-preflight', title: 'Preflight: ' + task.preflightType }, '🛡️ ' + task.preflightType) : null,
3211
- task.totalCostUsd > 0 ? React.createElement('span', { className: 'dsh-cron-cost-tag' }, '$' + task.totalCostUsd.toFixed(4)) : null,
3212
- task.totalTokens > 0 ? React.createElement('span', { className: 'dsh-cron-tokens-tag' }, (task.totalTokens > 1000 ? Math.round(task.totalTokens / 1000) + 'k' : task.totalTokens) + ' tok') : null,
3213
- task.status === 'paused' && task.pausedReason ? React.createElement('span', { className: 'dsh-cron-type-tag dsh-cron-tag-failure', title: task.pausedReason }, '🛑 ' + task.pausedReason) : null
3214
- ),
3215
- React.createElement('div', { className: 'dsh-cron-task-sched' },
3272
+ task.heartbeatIntervalSeconds > 0 ? h('span', { className: 'dsh-cron-type-tag dsh-cron-tag-heartbeat', title: 'Heartbeat: every ' + task.heartbeatIntervalSeconds + 's' }, '💓 ' + task.heartbeatIntervalSeconds + 's') : null,
3273
+ task.targetSessionId ? h('span', { className: 'dsh-cron-type-tag dsh-cron-tag-session', title: 'Target session: ' + task.targetSessionId + (task.targetSessionReset && task.targetSessionReset !== 'never' ? ' (' + task.targetSessionReset + ')' : '') }, '🧵 ' + task.targetSessionId) : null,
3274
+ task.preflightType && task.preflightType !== 'none' ? h('span', { className: 'dsh-cron-type-tag dsh-cron-tag-preflight', title: 'Preflight: ' + task.preflightType }, '🛡️ ' + task.preflightType) : null,
3275
+ task.totalCostUsd > 0 ? h('span', { className: 'dsh-cron-cost-tag' }, '$' + task.totalCostUsd.toFixed(4)) : null,
3276
+ task.totalTokens > 0 ? h('span', { className: 'dsh-cron-tokens-tag' }, (task.totalTokens > 1000 ? Math.round(task.totalTokens / 1000) + 'k' : task.totalTokens) + ' tok') : null,
3277
+ task.status === 'paused' && task.pausedReason ? h('span', { className: 'dsh-cron-type-tag dsh-cron-tag-failure', title: task.pausedReason }, '🛑 ' + task.pausedReason) : null
3278
+ ),
3279
+ h('div', { className: 'dsh-cron-task-sched' },
3216
3280
  task.scheduleText || task.schedule,
3217
3281
  task.nextRunAt ? T_KEY(t, 'list.next', { time: new Date(task.nextRunAt).toLocaleTimeString([], { hour: '2-digit', minute: '2-digit' }) }) : '',
3218
3282
  task.running && task.runningSince
3219
3283
  ? ' · ' + T_KEY(t, 'list.runningNow') + ' ' + Math.max(0, Math.round((Date.now() - task.runningSince) / 1000)) + 's'
3220
3284
  : ''
3221
3285
  ),
3222
- task.prompt ? React.createElement('div', {
3286
+ task.prompt ? h('div', {
3223
3287
  className: 'dsh-cron-task-prompt-preview',
3224
3288
  title: task.prompt
3225
3289
  }, task.prompt.slice(0, 140) + (task.prompt.length > 140 ? '…' : '')) : null
3226
3290
  ),
3227
- React.createElement('div', {
3291
+ h('div', {
3228
3292
  className: 'dsh-cron-task-actions',
3229
3293
  onClick: (e) => e.stopPropagation()
3230
3294
  },
3231
- React.createElement('button', {
3295
+ h('button', {
3232
3296
  type: 'button',
3233
3297
  className: 'dsh-cron-icon-btn',
3234
3298
  title: T_KEY(t, 'actions.dryRunTitle'),
3235
3299
  onClick: () => handleDryRun(task.id)
3236
3300
  }, '🧪'),
3237
- React.createElement('button', {
3301
+ h('button', {
3238
3302
  type: 'button',
3239
3303
  className: 'dsh-cron-icon-btn' + (task.running ? ' dsh-cron-pulse' : ''),
3240
3304
  title: T_KEY(t, 'liveLog.viewLog'),
3241
3305
  onClick: () => handleOpenLiveLogs(task)
3242
3306
  }, '📺'),
3243
- React.createElement('button', {
3307
+ h('button', {
3244
3308
  type: 'button',
3245
3309
  className: 'dsh-cron-icon-btn',
3246
3310
  title: T_KEY(t, 'actions.archiveTitle'),
3247
3311
  onClick: () => openArchiveModal(task, 0)
3248
3312
  }, '📜'),
3249
- (task.onSuccess || task.onFailure || (task.dependsOn && (Array.isArray(task.dependsOn) ? task.dependsOn.length > 0 : Boolean(task.dependsOn)))) ? React.createElement('button', {
3313
+ (task.onSuccess || task.onFailure || (task.dependsOn && (Array.isArray(task.dependsOn) ? task.dependsOn.length > 0 : Boolean(task.dependsOn)))) ? h('button', {
3250
3314
  type: 'button',
3251
3315
  className: 'dsh-cron-icon-btn',
3252
3316
  title: T_KEY(t, 'chainGraph.viewGraph'),
3253
3317
  onClick: () => openChainGraphModal(task)
3254
3318
  }, '🕸️') : null,
3255
- React.createElement('button', {
3319
+ h('button', {
3256
3320
  type: 'button',
3257
3321
  className: 'dsh-cron-icon-btn',
3258
3322
  title: T_KEY(t, 'actions.runNow'),
3259
3323
  onClick: () => handleRunNow(task.id)
3260
3324
  }, T_KEY(t, 'actions.runNowShort')),
3261
- isConfigManaged(task) ? null : React.createElement('button', {
3325
+ isConfigManaged(task) ? null : h('button', {
3262
3326
  type: 'button',
3263
3327
  className: 'dsh-cron-icon-btn',
3264
3328
  title: T_KEY(t, 'actions.edit'),
3265
3329
  'aria-label': T_KEY(t, 'actions.edit'),
3266
3330
  onClick: () => openEditModal(task)
3267
- }, React.createElement('span', svgProps(ICON_EDIT))),
3268
- isConfigManaged(task) ? null : React.createElement('button', {
3331
+ }, h('span', svgProps(ICON_EDIT))),
3332
+ isConfigManaged(task) ? null : h('button', {
3269
3333
  type: 'button',
3270
3334
  className: 'dsh-cron-icon-btn',
3271
3335
  title: T_KEY(t, 'actions.tuneWithDsh'),
3272
3336
  'aria-label': T_KEY(t, 'actions.tuneWithDsh'),
3273
3337
  onClick: () => handleTuneWithDsh(task)
3274
- }, React.createElement('span', svgProps(ICON_TUNE))),
3275
- isConfigManaged(task) ? null : React.createElement('button', {
3338
+ }, h('span', svgProps(ICON_TUNE))),
3339
+ isConfigManaged(task) ? null : h('button', {
3276
3340
  type: 'button',
3277
3341
  className: 'dsh-cron-icon-btn',
3278
3342
  title: T_KEY(t, 'actions.duplicate'),
3279
3343
  'aria-label': T_KEY(t, 'actions.duplicate'),
3280
3344
  onClick: () => handleDuplicate(task)
3281
- }, React.createElement('span', svgProps(ICON_COPY))),
3282
- isConfigManaged(task) ? null : React.createElement('button', {
3345
+ }, h('span', svgProps(ICON_COPY))),
3346
+ isConfigManaged(task) ? null : h('button', {
3283
3347
  type: 'button',
3284
3348
  className: 'dsh-cron-icon-btn dsh-cron-danger',
3285
3349
  title: T_KEY(t, 'actions.delete'),
3286
3350
  'aria-label': T_KEY(t, 'actions.delete'),
3287
3351
  onClick: () => handleDelete(task.id)
3288
- }, React.createElement('span', svgProps(ICON_TRASH)))
3352
+ }, h('span', svgProps(ICON_TRASH)))
3289
3353
  )
3290
3354
  )
3291
3355
  )
3292
3356
  ),
3293
- React.createElement('div', { className: 'dsh-cron-recs-title' }, T_KEY(t, 'recs.title')),
3294
- React.createElement('div', { className: 'dsh-cron-hint', style: { marginBottom: '8px' } }, T_KEY(t, 'recs.hint')),
3295
- React.createElement('div', { className: 'dsh-cron-recs-list' },
3357
+ h('div', { className: 'dsh-cron-recs-title' }, T_KEY(t, 'recs.title')),
3358
+ h('div', { className: 'dsh-cron-hint', style: { marginBottom: '8px' } }, T_KEY(t, 'recs.hint')),
3359
+ h('div', { className: 'dsh-cron-recs-list' },
3296
3360
  recs.map((rec) =>
3297
- React.createElement('div', {
3361
+ h('div', {
3298
3362
  key: rec.id,
3299
3363
  className: 'dsh-cron-rec-card',
3300
3364
  role: 'button',
@@ -3307,36 +3371,36 @@ openManualModal(rec);
3307
3371
  }
3308
3372
  }
3309
3373
  },
3310
- React.createElement('div', { className: 'dsh-cron-rec-icon' },
3311
- React.createElement('span', iconHtml(rec.icon === 'bell' ? ICON_BELL : rec.icon === 'clipboard' ? ICON_CLIPBOARD : ICON_ACTIVITY))
3374
+ h('div', { className: 'dsh-cron-rec-icon' },
3375
+ h('span', iconHtml(rec.icon === 'bell' ? ICON_BELL : rec.icon === 'clipboard' ? ICON_CLIPBOARD : ICON_ACTIVITY))
3312
3376
  ),
3313
- React.createElement('div', { className: 'dsh-cron-rec-content' },
3314
- React.createElement('div', { className: 'dsh-cron-rec-title' },
3377
+ h('div', { className: 'dsh-cron-rec-content' },
3378
+ h('div', { className: 'dsh-cron-rec-title' },
3315
3379
  rec.title,
3316
- React.createElement('span', { className: 'dsh-cron-rec-time' }, rec.scheduleText)
3380
+ h('span', { className: 'dsh-cron-rec-time' }, rec.scheduleText)
3317
3381
  ),
3318
- React.createElement('div', { className: 'dsh-cron-rec-desc' }, rec.description)
3382
+ h('div', { className: 'dsh-cron-rec-desc' }, rec.description)
3319
3383
  )
3320
3384
  )
3321
3385
  )
3322
3386
  )
3323
3387
  ),
3324
- manualModalOpen && React.createElement('div', {
3388
+ manualModalOpen && h('div', {
3325
3389
  className: 'dsh-cron-modal-overlay',
3326
3390
  onClick: (e) => {
3327
3391
  if (e.target === e.currentTarget) closeManualModalWithConfirm();
3328
3392
  }
3329
3393
  },
3330
- React.createElement('div', {
3394
+ h('div', {
3331
3395
  className: 'dsh-cron-modal dsh-cron-modal-scroll',
3332
3396
  style: { maxWidth: '640px' },
3333
3397
  role: 'dialog',
3334
3398
  'aria-modal': 'true',
3335
3399
  onClick: (e) => e.stopPropagation()
3336
3400
  },
3337
- React.createElement('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: formId ? '12px' : '18px' } },
3338
- React.createElement('div', { className: 'dsh-cron-modal-title', style: { margin: 0 } }, formId ? T_KEY(t, 'modal.editTitle') : T_KEY(t, 'modal.newTitle')),
3339
- selectedTaskMeta && React.createElement('span', {
3401
+ h('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: formId ? '12px' : '18px' } },
3402
+ h('div', { className: 'dsh-cron-modal-title', style: { margin: 0 } }, formId ? T_KEY(t, 'modal.editTitle') : T_KEY(t, 'modal.newTitle')),
3403
+ selectedTaskMeta && h('span', {
3340
3404
  style: {
3341
3405
  fontSize: '12px',
3342
3406
  padding: '3px 8px',
@@ -3346,65 +3410,65 @@ color: selectedTaskMeta.status === 'active' ? 'var(--dsh-cron-success)' : 'var(-
3346
3410
  }
3347
3411
  }, selectedTaskMeta.status === 'active' ? T_KEY(t, 'modal.statusActive') : T_KEY(t, 'modal.statusPaused'))
3348
3412
  ),
3349
- formId && React.createElement('div', { className: 'dsh-cron-modal-nav' },
3350
- React.createElement('button', {
3413
+ formId && h('div', { className: 'dsh-cron-modal-nav' },
3414
+ h('button', {
3351
3415
  type: 'button',
3352
3416
  className: 'dsh-cron-modal-tab',
3353
3417
  'data-active': modalTab === 'params' ? 'true' : undefined,
3354
3418
  onClick: () => setModalTab('params')
3355
3419
  }, T_KEY(t, 'modal.params')),
3356
- React.createElement('button', {
3420
+ h('button', {
3357
3421
  type: 'button',
3358
3422
  className: 'dsh-cron-modal-tab',
3359
3423
  'data-active': modalTab === 'history' ? 'true' : undefined,
3360
3424
  onClick: () => { setModalTab('history'); if (formId) loadTaskHistory(formId); }
3361
3425
  }, T_KEY(t, 'modal.history', { count: taskHistory.length || 0 }))
3362
3426
  ),
3363
- modalTab === 'history' && formId ? React.createElement('div', null,
3364
- historyLoading ? React.createElement('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'history.loading')) :
3365
- taskHistory.length === 0 ? React.createElement('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'history.empty')) :
3366
- React.createElement('div', { className: 'dsh-cron-history-list' },
3367
- taskHistory.map((run) => React.createElement('div', { key: run.id, className: 'dsh-cron-history-item' },
3368
- React.createElement('div', { className: 'dsh-cron-history-head' },
3369
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
3370
- React.createElement('span', {
3427
+ modalTab === 'history' && formId ? h('div', null,
3428
+ historyLoading ? h('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'history.loading')) :
3429
+ taskHistory.length === 0 ? h('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'history.empty')) :
3430
+ h('div', { className: 'dsh-cron-history-list' },
3431
+ taskHistory.map((run) => h('div', { key: run.id, className: 'dsh-cron-history-item' },
3432
+ h('div', { className: 'dsh-cron-history-head' },
3433
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
3434
+ h('span', {
3371
3435
  className: 'dsh-cron-history-status',
3372
3436
  'data-status': run.status
3373
3437
  }, statusLabel(t, run.status)),
3374
- React.createElement('span', { className: 'dsh-cron-history-time' }, run.at ? new Date(run.at).toLocaleString() : '')
3438
+ h('span', { className: 'dsh-cron-history-time' }, run.at ? new Date(run.at).toLocaleString() : '')
3375
3439
  ),
3376
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
3377
- run.costUsd > 0 && React.createElement('span', { className: 'dsh-cron-cost-tag' }, '$' + run.costUsd.toFixed(5)),
3378
- run.usage && (run.usage.inputTokens > 0 || run.usage.outputTokens > 0) && React.createElement('span', { className: 'dsh-cron-tokens-tag' }, (run.usage.inputTokens + run.usage.outputTokens) + ' tok'),
3379
- React.createElement('span', { style: { color: 'var(--dsw-alias-label-tertiary, #888)', fontSize: '11.5px' } }, (run.durationMs || 0) + ' ms')
3440
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '8px' } },
3441
+ run.costUsd > 0 && h('span', { className: 'dsh-cron-cost-tag' }, '$' + run.costUsd.toFixed(5)),
3442
+ run.usage && (run.usage.inputTokens > 0 || run.usage.outputTokens > 0) && h('span', { className: 'dsh-cron-tokens-tag' }, (run.usage.inputTokens + run.usage.outputTokens) + ' tok'),
3443
+ h('span', { style: { color: 'var(--dsw-alias-label-tertiary, #888)', fontSize: '11.5px' } }, (run.durationMs || 0) + ' ms')
3380
3444
  )
3381
3445
  ),
3382
- run.stoppedReason && React.createElement('div', {
3446
+ run.stoppedReason && h('div', {
3383
3447
  className: 'dsh-cron-hint',
3384
3448
  style: { display: 'flex', gap: '6px', alignItems: 'center', marginTop: '6px' }
3385
3449
  },
3386
- React.createElement('span', { className: 'dsh-cron-badge-ref' }, T_KEY(t, 'history.stoppedReasonTitle')),
3387
- React.createElement('span', null, run.stoppedReason)
3450
+ h('span', { className: 'dsh-cron-badge-ref' }, T_KEY(t, 'history.stoppedReasonTitle')),
3451
+ h('span', null, run.stoppedReason)
3388
3452
  ),
3389
- Array.isArray(run.stages) && run.stages.length > 0 && React.createElement('div', {
3453
+ Array.isArray(run.stages) && run.stages.length > 0 && h('div', {
3390
3454
  className: 'dsh-cron-stages-flow',
3391
3455
  style: { display: 'flex', gap: '6px', flexWrap: 'wrap', marginTop: '6px' }
3392
3456
  },
3393
- run.stages.map((st) => React.createElement('span', {
3457
+ run.stages.map((st) => h('span', {
3394
3458
  key: st.name,
3395
3459
  className: 'dsh-cron-stage-pill',
3396
3460
  'data-status': st.status || 'unknown',
3397
3461
  title: st.error ? (st.name + ': ' + st.error) : (st.name + (st.durationMs !== undefined ? ' (' + st.durationMs + 'ms)' : ''))
3398
3462
  }, (T_KEY(t, 'history.stage_' + st.name) || st.name) + (st.durationMs !== undefined ? ' ' + st.durationMs + 'ms' : '')))
3399
3463
  ),
3400
- run.delivery && React.createElement('div', {
3464
+ run.delivery && h('div', {
3401
3465
  style: { display: 'flex', alignItems: 'center', gap: '8px', marginTop: '6px' }
3402
3466
  },
3403
- React.createElement('span', {
3467
+ h('span', {
3404
3468
  className: 'dsh-cron-badge-ref',
3405
3469
  'data-status': run.delivery.status
3406
3470
  }, 'Delivery: ' + run.delivery.status),
3407
- (run.delivery.status === 'failed' || run.delivery.status === 'partial') && React.createElement('button', {
3471
+ (run.delivery.status === 'failed' || run.delivery.status === 'partial') && h('button', {
3408
3472
  type: 'button',
3409
3473
  className: 'dsh-cron-btn-secondary',
3410
3474
  style: { padding: '2px 8px', fontSize: '11px' },
@@ -3412,11 +3476,11 @@ disabled: retryingDeliveryId === run.id,
3412
3476
  onClick: () => handleRetryDelivery(formId, run.id)
3413
3477
  }, retryingDeliveryId === run.id ? T_KEY(t, 'history.retryingDelivery') : T_KEY(t, 'history.retryDelivery'))
3414
3478
  ),
3415
- run.artifacts && run.artifacts.length > 0 && React.createElement('div', {
3479
+ run.artifacts && run.artifacts.length > 0 && h('div', {
3416
3480
  style: { display: 'flex', flexWrap: 'wrap', gap: '6px', marginTop: '6px', alignItems: 'center' }
3417
3481
  },
3418
- React.createElement('span', { className: 'dsh-cron-hint', style: { fontSize: '11px' } }, '📦 ' + T_KEY(t, 'history.artifacts') + ':'),
3419
- run.artifacts.map((art) => React.createElement('a', {
3482
+ h('span', { className: 'dsh-cron-hint', style: { fontSize: '11px' } }, '📦 ' + T_KEY(t, 'history.artifacts') + ':'),
3483
+ run.artifacts.map((art) => h('a', {
3420
3484
  key: art.name || art.id,
3421
3485
  href: '/dsh-cron/runs/' + encodeURIComponent(run.id) + '/artifacts/' + encodeURIComponent(art.name) + '/preview',
3422
3486
  target: '_blank',
@@ -3426,20 +3490,20 @@ style: { padding: '2px 8px', fontSize: '11px', textDecoration: 'none' },
3426
3490
  title: art.name + ' (' + Math.round((art.size || 0) / 1024 * 10) / 10 + ' KB)'
3427
3491
  }, art.name))
3428
3492
  ),
3429
- run.status === 'uncertain' && React.createElement('div', {
3493
+ run.status === 'uncertain' && h('div', {
3430
3494
  className: 'dsh-cron-status-banner',
3431
3495
  'data-type': 'warning',
3432
3496
  style: { marginTop: '8px', display: 'flex', alignItems: 'center', justifyContent: 'space-between', gap: '8px' }
3433
3497
  },
3434
- React.createElement('span', null, '⚠️ ' + T_KEY(t, 'history.statusUncertainHint')),
3435
- React.createElement('div', { style: { display: 'flex', gap: '6px' } },
3436
- React.createElement('button', {
3498
+ h('span', null, '⚠️ ' + T_KEY(t, 'history.statusUncertainHint')),
3499
+ h('div', { style: { display: 'flex', gap: '6px' } },
3500
+ h('button', {
3437
3501
  type: 'button',
3438
3502
  className: 'dsh-cron-btn-secondary',
3439
3503
  style: { padding: '2px 8px', fontSize: '11px' },
3440
3504
  onClick: () => handleResolveUncertain(formId, run.id, 'completed')
3441
3505
  }, '✓ ' + T_KEY(t, 'history.resolveCompleted')),
3442
- React.createElement('button', {
3506
+ h('button', {
3443
3507
  type: 'button',
3444
3508
  className: 'dsh-cron-btn-secondary',
3445
3509
  style: { padding: '2px 8px', fontSize: '11px' },
@@ -3447,35 +3511,62 @@ onClick: () => handleResolveUncertain(formId, run.id, 'failed')
3447
3511
  }, '✕ ' + T_KEY(t, 'history.resolveFailed'))
3448
3512
  )
3449
3513
  ),
3450
- run.diagnosis && React.createElement('div', {
3514
+ (run.diagnosis || run.doctorReport) && h('div', {
3451
3515
  className: 'dsh-cron-status-banner',
3452
3516
  'data-type': 'info',
3453
3517
  style: { marginTop: '8px', display: 'flex', flexDirection: 'column', gap: '6px' }
3454
3518
  },
3455
- React.createElement('div', null,
3456
- React.createElement('strong', null, T_KEY(t, 'history.diagnosis')),
3457
- run.confidence ? ` (${run.confidence})` : ''
3519
+ h('div', { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center' } },
3520
+ h('strong', null, '🩺 ' + T_KEY(t, run.doctorReport ? 'history.doctorDiagnosis' : 'history.diagnosis')),
3521
+ h('div', { style: { display: 'flex', gap: '6px', alignItems: 'center' } },
3522
+ (run.autoHealed || run.doctorReport?.autoHealed) && h('span', {
3523
+ style: { fontSize: '10px', background: 'var(--dsh-cron-success-bg)', color: 'var(--dsh-cron-success)', padding: '1px 6px', borderRadius: '8px', fontWeight: '600' }
3524
+ }, '✨ ' + T_KEY(t, 'history.autoHealed')),
3525
+ (run.doctorReport?.category || run.category) && h('span', {
3526
+ style: { fontSize: '10px', background: 'var(--dsw-alias-bg-layer-3)', padding: '1px 6px', borderRadius: '4px' }
3527
+ }, run.doctorReport?.category || run.category),
3528
+ run.confidence ? h('span', { style: { fontSize: '10px', color: 'var(--dsw-alias-label-secondary)' } }, '(' + run.confidence + ')') : null
3529
+ )
3458
3530
  ),
3459
- React.createElement('div', null, run.diagnosis),
3460
- run.suggestion && React.createElement('div', null,
3461
- React.createElement('button', {
3531
+ h('div', null, run.doctorReport?.cause || run.diagnosis),
3532
+ run.doctorReport?.diff && h('div', {
3533
+ style: {
3534
+ background: 'var(--dsw-alias-bg-layer-2)',
3535
+ border: '1px solid var(--dsw-alias-border-l2)',
3536
+ borderRadius: '4px',
3537
+ padding: '6px',
3538
+ fontFamily: 'monospace',
3539
+ fontSize: '11px',
3540
+ maxHeight: '120px',
3541
+ overflowY: 'auto',
3542
+ whiteSpace: 'pre'
3543
+ }
3544
+ }, run.doctorReport.diff),
3545
+ (run.doctorReport?.suggestedFix || run.suggestion) && h('div', { style: { display: 'flex', gap: '8px', marginTop: '4px' } },
3546
+ typeof handleApplyDoctorFix === 'function' && h('button', {
3547
+ type: 'button',
3548
+ className: 'dsh-cron-btn-primary',
3549
+ style: { padding: '3px 10px', fontSize: '12px' },
3550
+ onClick: () => handleApplyDoctorFix(formId, run.doctorReport || { suggestedFix: run.suggestion })
3551
+ }, '⚡ ' + T_KEY(t, 'history.doctorApply')),
3552
+ h('button', {
3462
3553
  type: 'button',
3463
3554
  className: 'dsh-cron-btn-secondary',
3464
- style: { padding: '2px 8px', fontSize: '12px' },
3555
+ style: { padding: '3px 10px', fontSize: '12px' },
3465
3556
  onClick: () => openEditModal(selectedTaskMeta, { prompt: run.suggestion })
3466
3557
  }, T_KEY(t, 'history.applySuggestion'))
3467
3558
  )
3468
3559
  ),
3469
- run.silentSkip && React.createElement('div', {
3560
+ run.silentSkip && h('div', {
3470
3561
  className: 'dsh-cron-hint',
3471
3562
  style: { display: 'flex', gap: '6px', alignItems: 'center' }
3472
3563
  },
3473
- React.createElement('span', { className: 'dsh-cron-badge-ref' }, T_KEY(t, 'history.silentSkip')),
3474
- React.createElement('span', null, run.silentReason || '')
3564
+ h('span', { className: 'dsh-cron-badge-ref' }, T_KEY(t, 'history.silentSkip')),
3565
+ h('span', null, run.silentReason || '')
3475
3566
  ),
3476
- run.output && React.createElement('div', { className: 'dsh-cron-history-output' }, run.output),
3477
- run.error && React.createElement('div', { className: 'dsh-cron-history-output', style: { color: 'var(--dsh-cron-danger)', borderColor: 'var(--dsh-cron-danger-bg)' } }, run.error),
3478
- run.sessionId && React.createElement('button', {
3567
+ run.output && h('div', { className: 'dsh-cron-history-output' }, run.output),
3568
+ run.error && h('div', { className: 'dsh-cron-history-output', style: { color: 'var(--dsh-cron-danger)', borderColor: 'var(--dsh-cron-danger-bg)' } }, run.error),
3569
+ run.sessionId && h('button', {
3479
3570
  type: 'button',
3480
3571
  className: 'dsh-cron-btn-secondary',
3481
3572
  style: { marginTop: '8px', fontSize: '12px', padding: '4px 10px' },
@@ -3483,23 +3574,23 @@ onClick: () => openSession(ctx, run.sessionId)
3483
3574
  }, T_KEY(t, 'history.openSession'))
3484
3575
  ))
3485
3576
  ),
3486
- React.createElement('div', { className: 'dsh-cron-modal-foot', style: { marginTop: '18px' } },
3487
- React.createElement('button', {
3577
+ h('div', { className: 'dsh-cron-modal-foot', style: { marginTop: '18px' } },
3578
+ h('button', {
3488
3579
  type: 'button',
3489
3580
  className: 'dsh-cron-btn-secondary',
3490
3581
  onClick: () => { if (formId) loadTaskHistory(formId); }
3491
3582
  }, T_KEY(t, 'history.refresh')),
3492
- React.createElement('button', {
3583
+ h('button', {
3493
3584
  type: 'button',
3494
3585
  className: 'dsh-cron-btn-primary',
3495
3586
  onClick: closeManualModalWithConfirm
3496
3587
  }, T_KEY(t, 'modal.close'))
3497
3588
  )
3498
3589
  ) :
3499
- React.createElement('form', { onSubmit: handleSaveManual },
3500
- React.createElement('div', { className: 'dsh-cron-form-group' },
3501
- React.createElement('label', null, T_KEY(t, 'form.nameLabel')),
3502
- React.createElement('input', {
3590
+ h('form', { onSubmit: handleSaveManual },
3591
+ h('div', { className: 'dsh-cron-form-group' },
3592
+ h('label', null, T_KEY(t, 'form.nameLabel')),
3593
+ h('input', {
3503
3594
  required: true,
3504
3595
  autoFocus: true,
3505
3596
  value: formTitle,
@@ -3507,40 +3598,40 @@ placeholder: T_KEY(t, 'form.namePlaceholder'),
3507
3598
  onChange: (e) => setFormTitle(e.target.value)
3508
3599
  })
3509
3600
  ),
3510
- React.createElement('div', { className: 'dsh-cron-form-row' },
3511
- React.createElement('div', { className: 'dsh-cron-form-group' },
3512
- React.createElement('label', null, T_KEY(t, 'form.typeLabel')),
3513
- React.createElement('select', {
3601
+ h('div', { className: 'dsh-cron-form-row' },
3602
+ h('div', { className: 'dsh-cron-form-group' },
3603
+ h('label', null, T_KEY(t, 'form.typeLabel')),
3604
+ h('select', {
3514
3605
  value: formType,
3515
3606
  onChange: (e) => setFormType(e.target.value)
3516
3607
  },
3517
- React.createElement('option', { value: 'llm' }, T_KEY(t, 'form.typeLlm')),
3518
- React.createElement('option', { value: 'script' }, T_KEY(t, 'form.typeScript')),
3519
- React.createElement('option', { value: 'node' }, T_KEY(t, 'form.typeNode')),
3520
- React.createElement('option', { value: 'python' }, T_KEY(t, 'form.typePython')),
3521
- React.createElement('option', { value: 'http' }, T_KEY(t, 'form.typeHttp')),
3522
- React.createElement('option', { value: 'ssh' }, T_KEY(t, 'form.typeSsh')),
3523
- React.createElement('option', { value: 'docker' }, T_KEY(t, 'form.typeDocker')),
3524
- React.createElement('option', { value: 'skill' }, T_KEY(t, 'form.typeSkill')),
3525
- React.createElement('option', { value: 'workflow' }, T_KEY(t, 'form.typeWorkflow'))
3608
+ h('option', { value: 'llm' }, T_KEY(t, 'form.typeLlm')),
3609
+ h('option', { value: 'script' }, T_KEY(t, 'form.typeScript')),
3610
+ h('option', { value: 'node' }, T_KEY(t, 'form.typeNode')),
3611
+ h('option', { value: 'python' }, T_KEY(t, 'form.typePython')),
3612
+ h('option', { value: 'http' }, T_KEY(t, 'form.typeHttp')),
3613
+ h('option', { value: 'ssh' }, T_KEY(t, 'form.typeSsh')),
3614
+ h('option', { value: 'docker' }, T_KEY(t, 'form.typeDocker')),
3615
+ h('option', { value: 'skill' }, T_KEY(t, 'form.typeSkill')),
3616
+ h('option', { value: 'workflow' }, T_KEY(t, 'form.typeWorkflow'))
3526
3617
  )
3527
3618
  ),
3528
- React.createElement('div', { className: 'dsh-cron-form-group' },
3529
- React.createElement('label', null, T_KEY(t, 'form.scheduleLabel')),
3530
- React.createElement('input', {
3619
+ h('div', { className: 'dsh-cron-form-group' },
3620
+ h('label', null, T_KEY(t, 'form.scheduleLabel')),
3621
+ h('input', {
3531
3622
  required: true,
3532
3623
  value: formSchedule,
3533
3624
  placeholder: T_KEY(t, 'form.schedulePlaceholder'),
3534
3625
  onChange: (e) => setFormSchedule(e.target.value)
3535
3626
  }),
3536
- React.createElement('div', { style: { display: 'flex', gap: '5px', flexWrap: 'wrap', marginTop: '5px' } },
3627
+ h('div', { style: { display: 'flex', gap: '5px', flexWrap: 'wrap', marginTop: '5px' } },
3537
3628
  [
3538
3629
  { label: '15m', expr: '*/15 * * * *' },
3539
3630
  { label: '1h', expr: '0 * * * *' },
3540
3631
  { label: 'Daily 09:00', expr: '0 9 * * *' },
3541
3632
  { label: 'Weekdays', expr: '0 9 * * 1-5' },
3542
3633
  { label: 'Weekly Mon', expr: '0 9 * * 1' },
3543
- ].map((p) => React.createElement('button', {
3634
+ ].map((p) => h('button', {
3544
3635
  key: p.label,
3545
3636
  type: 'button',
3546
3637
  className: 'dsh-cron-btn-secondary',
@@ -3548,23 +3639,23 @@ style: { padding: '2px 7px', fontSize: '11px', borderRadius: '4px' },
3548
3639
  onClick: () => { setFormSchedule(p.expr); handlePreviewSchedule(p.expr); }
3549
3640
  }, p.label))
3550
3641
  ),
3551
- React.createElement('div', { style: { display: 'flex', gap: '8px', alignItems: 'center', marginTop: '6px' } },
3552
- React.createElement('button', {
3642
+ h('div', { style: { display: 'flex', gap: '8px', alignItems: 'center', marginTop: '6px' } },
3643
+ h('button', {
3553
3644
  type: 'button',
3554
3645
  className: 'dsh-cron-btn-secondary',
3555
3646
  style: { padding: '3px 8px', fontSize: '11.5px' },
3556
3647
  onClick: () => handlePreviewSchedule(formSchedule)
3557
3648
  }, T_KEY(t, 'form.previewSchedule')),
3558
- schedulePreviewRuns && schedulePreviewRuns.length > 0 && React.createElement('div', { style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #999)' } },
3649
+ schedulePreviewRuns && schedulePreviewRuns.length > 0 && h('div', { style: { fontSize: '11px', color: 'var(--dsw-alias-label-secondary, #999)' } },
3559
3650
  T_KEY(t, 'form.previewScheduleTitle') + ' ' + schedulePreviewRuns.slice(0, 3).map(r => new Date(r).toLocaleTimeString()).join(', ')
3560
3651
  )
3561
3652
  )
3562
3653
  )
3563
3654
  ),
3564
- React.createElement('div', { className: 'dsh-cron-form-row' },
3565
- React.createElement('div', { className: 'dsh-cron-form-group' },
3566
- React.createElement('label', null, T_KEY(t, 'form.timeoutLabel')),
3567
- React.createElement('input', {
3655
+ h('div', { className: 'dsh-cron-form-row' },
3656
+ h('div', { className: 'dsh-cron-form-group' },
3657
+ h('label', null, T_KEY(t, 'form.timeoutLabel')),
3658
+ h('input', {
3568
3659
  type: 'number',
3569
3660
  min: 1,
3570
3661
  value: formTimeoutSeconds,
@@ -3572,44 +3663,44 @@ placeholder: '1800',
3572
3663
  onChange: (e) => setFormTimeoutSeconds(e.target.value)
3573
3664
  })
3574
3665
  ),
3575
- React.createElement('div', { className: 'dsh-cron-form-group' },
3576
- React.createElement('label', null, T_KEY(t, 'form.overlapLabel')),
3577
- React.createElement('select', {
3666
+ h('div', { className: 'dsh-cron-form-group' },
3667
+ h('label', null, T_KEY(t, 'form.overlapLabel')),
3668
+ h('select', {
3578
3669
  value: formOverlapPolicy,
3579
3670
  onChange: (e) => setFormOverlapPolicy(e.target.value)
3580
3671
  },
3581
- React.createElement('option', { value: 'skip' }, T_KEY(t, 'form.overlapSkip')),
3582
- React.createElement('option', { value: 'queue' }, T_KEY(t, 'form.overlapQueue')),
3583
- React.createElement('option', { value: 'replace' }, T_KEY(t, 'form.overlapReplace'))
3672
+ h('option', { value: 'skip' }, T_KEY(t, 'form.overlapSkip')),
3673
+ h('option', { value: 'queue' }, T_KEY(t, 'form.overlapQueue')),
3674
+ h('option', { value: 'replace' }, T_KEY(t, 'form.overlapReplace'))
3584
3675
  )
3585
3676
  )
3586
3677
  ),
3587
- React.createElement('div', { className: 'dsh-cron-form-row' },
3588
- React.createElement('div', { className: 'dsh-cron-form-group' },
3589
- React.createElement('label', null, T_KEY(t, 'form.timezoneLabel')),
3590
- React.createElement('input', {
3678
+ h('div', { className: 'dsh-cron-form-row' },
3679
+ h('div', { className: 'dsh-cron-form-group' },
3680
+ h('label', null, T_KEY(t, 'form.timezoneLabel')),
3681
+ h('input', {
3591
3682
  value: formTimezone,
3592
3683
  placeholder: T_KEY(t, 'form.timezonePlaceholder'),
3593
3684
  onChange: (e) => setFormTimezone(e.target.value)
3594
3685
  })
3595
3686
  ),
3596
- React.createElement('div', { className: 'dsh-cron-form-group' },
3597
- React.createElement('label', null, T_KEY(t, 'form.misfireLabel')),
3598
- React.createElement('select', {
3687
+ h('div', { className: 'dsh-cron-form-group' },
3688
+ h('label', null, T_KEY(t, 'form.misfireLabel')),
3689
+ h('select', {
3599
3690
  value: formMisfirePolicy,
3600
3691
  onChange: (e) => setFormMisfirePolicy(e.target.value)
3601
3692
  },
3602
- React.createElement('option', { value: 'skip' }, T_KEY(t, 'form.misfireSkip')),
3603
- React.createElement('option', { value: 'runOnce' }, T_KEY(t, 'form.misfireRunOnce')),
3604
- React.createElement('option', { value: 'catchUpAll' }, T_KEY(t, 'form.misfireCatchUp'))
3693
+ h('option', { value: 'skip' }, T_KEY(t, 'form.misfireSkip')),
3694
+ h('option', { value: 'runOnce' }, T_KEY(t, 'form.misfireRunOnce')),
3695
+ h('option', { value: 'catchUpAll' }, T_KEY(t, 'form.misfireCatchUp'))
3605
3696
  )
3606
3697
  )
3607
3698
  ),
3608
3699
  AGENT_FORM_TYPES.includes(formType) ? (
3609
- React.createElement('div', { className: 'dsh-cron-form-row' },
3610
- React.createElement('div', { className: 'dsh-cron-form-group' },
3611
- React.createElement('label', null, T_KEY(t, 'form.retriesLabel')),
3612
- React.createElement('input', {
3700
+ h('div', { className: 'dsh-cron-form-row' },
3701
+ h('div', { className: 'dsh-cron-form-group' },
3702
+ h('label', null, T_KEY(t, 'form.retriesLabel')),
3703
+ h('input', {
3613
3704
  type: 'number',
3614
3705
  min: 0,
3615
3706
  value: formMaxRetries,
@@ -3617,23 +3708,23 @@ placeholder: '0',
3617
3708
  onChange: (e) => setFormMaxRetries(e.target.value)
3618
3709
  })
3619
3710
  ),
3620
- React.createElement('div', { className: 'dsh-cron-form-group' },
3621
- React.createElement('label', null, T_KEY(t, 'form.permissionLabel')),
3622
- React.createElement('select', {
3711
+ h('div', { className: 'dsh-cron-form-group' },
3712
+ h('label', null, T_KEY(t, 'form.permissionLabel')),
3713
+ h('select', {
3623
3714
  value: formPermissionPreset,
3624
3715
  onChange: (e) => setFormPermissionPreset(e.target.value)
3625
3716
  },
3626
- React.createElement('option', { value: 'default' }, T_KEY(t, 'form.permissionDefault')),
3627
- React.createElement('option', { value: 'read-only' }, T_KEY(t, 'form.permissionReadonly')),
3628
- React.createElement('option', { value: 'workspace-write' }, T_KEY(t, 'form.permissionWrite')),
3629
- React.createElement('option', { value: 'full' }, T_KEY(t, 'form.permissionFull'))
3717
+ h('option', { value: 'default' }, T_KEY(t, 'form.permissionDefault')),
3718
+ h('option', { value: 'read-only' }, T_KEY(t, 'form.permissionReadonly')),
3719
+ h('option', { value: 'workspace-write' }, T_KEY(t, 'form.permissionWrite')),
3720
+ h('option', { value: 'full' }, T_KEY(t, 'form.permissionFull'))
3630
3721
  )
3631
3722
  )
3632
3723
  )
3633
3724
  ) : (
3634
- React.createElement('div', { className: 'dsh-cron-form-group' },
3635
- React.createElement('label', null, T_KEY(t, 'form.retriesLabel')),
3636
- React.createElement('input', {
3725
+ h('div', { className: 'dsh-cron-form-group' },
3726
+ h('label', null, T_KEY(t, 'form.retriesLabel')),
3727
+ h('input', {
3637
3728
  type: 'number',
3638
3729
  min: 0,
3639
3730
  value: formMaxRetries,
@@ -3642,114 +3733,114 @@ onChange: (e) => setFormMaxRetries(e.target.value)
3642
3733
  })
3643
3734
  )
3644
3735
  ),
3645
- React.createElement('div', { className: 'dsh-cron-form-group' },
3646
- React.createElement('label', null, T_KEY(t, 'form.kanbanLabel')),
3647
- React.createElement('select', {
3736
+ h('div', { className: 'dsh-cron-form-group' },
3737
+ h('label', null, T_KEY(t, 'form.kanbanLabel')),
3738
+ h('select', {
3648
3739
  value: formKanbanMode,
3649
3740
  onChange: (e) => setFormKanbanMode(e.target.value)
3650
3741
  },
3651
- React.createElement('option', { value: 'none' }, T_KEY(t, 'form.kanbanNone')),
3652
- React.createElement('option', { value: 'on_failure' }, T_KEY(t, 'form.kanbanOnFailure')),
3653
- React.createElement('option', { value: 'always' }, T_KEY(t, 'form.kanbanAlways'))
3742
+ h('option', { value: 'none' }, T_KEY(t, 'form.kanbanNone')),
3743
+ h('option', { value: 'on_failure' }, T_KEY(t, 'form.kanbanOnFailure')),
3744
+ h('option', { value: 'always' }, T_KEY(t, 'form.kanbanAlways'))
3654
3745
  )
3655
3746
  ),
3656
- AGENT_FORM_TYPES.includes(formType) && React.createElement('div', { className: 'dsh-cron-form-group' },
3657
- React.createElement('label', null, T_KEY(t, 'form.agentPresetLabel')),
3658
- React.createElement('input', {
3747
+ AGENT_FORM_TYPES.includes(formType) && h('div', { className: 'dsh-cron-form-group' },
3748
+ h('label', null, T_KEY(t, 'form.agentPresetLabel')),
3749
+ h('input', {
3659
3750
  type: 'text',
3660
3751
  value: formAgentPreset,
3661
3752
  placeholder: T_KEY(t, 'form.agentPresetPlaceholder'),
3662
3753
  onChange: (e) => setFormAgentPreset(e.target.value)
3663
3754
  }),
3664
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.agentPresetHint'))
3755
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.agentPresetHint'))
3665
3756
  ),
3666
- AGENT_FORM_TYPES.includes(formType) && React.createElement('div', { className: 'dsh-cron-form-row' },
3667
- React.createElement('div', { className: 'dsh-cron-form-group' },
3668
- React.createElement('label', null, T_KEY(t, 'form.targetSessionIdLabel')),
3669
- React.createElement('input', {
3757
+ AGENT_FORM_TYPES.includes(formType) && h('div', { className: 'dsh-cron-form-row' },
3758
+ h('div', { className: 'dsh-cron-form-group' },
3759
+ h('label', null, T_KEY(t, 'form.targetSessionIdLabel')),
3760
+ h('input', {
3670
3761
  type: 'text',
3671
3762
  value: formTargetSessionId,
3672
3763
  placeholder: T_KEY(t, 'form.targetSessionIdPlaceholder'),
3673
3764
  onChange: (e) => setFormTargetSessionId(e.target.value)
3674
3765
  }),
3675
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.targetSessionIdHint'))
3766
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.targetSessionIdHint'))
3676
3767
  ),
3677
- React.createElement('div', { className: 'dsh-cron-form-group' },
3678
- React.createElement('label', null, T_KEY(t, 'form.targetSessionResetLabel')),
3679
- React.createElement('select', {
3768
+ h('div', { className: 'dsh-cron-form-group' },
3769
+ h('label', null, T_KEY(t, 'form.targetSessionResetLabel')),
3770
+ h('select', {
3680
3771
  value: formTargetSessionReset,
3681
3772
  onChange: (e) => setFormTargetSessionReset(e.target.value)
3682
3773
  },
3683
- React.createElement('option', { value: 'never' }, T_KEY(t, 'form.targetSessionResetNever')),
3684
- React.createElement('option', { value: 'daily' }, T_KEY(t, 'form.targetSessionResetDaily')),
3685
- React.createElement('option', { value: 'weekly' }, T_KEY(t, 'form.targetSessionResetWeekly'))
3774
+ h('option', { value: 'never' }, T_KEY(t, 'form.targetSessionResetNever')),
3775
+ h('option', { value: 'daily' }, T_KEY(t, 'form.targetSessionResetDaily')),
3776
+ h('option', { value: 'weekly' }, T_KEY(t, 'form.targetSessionResetWeekly'))
3686
3777
  ),
3687
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.targetSessionResetHint'))
3778
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.targetSessionResetHint'))
3688
3779
  )
3689
3780
  ),
3690
- AGENT_FORM_TYPES.includes(formType) && React.createElement('div', { className: 'dsh-cron-form-row' },
3691
- React.createElement('div', { className: 'dsh-cron-form-group' },
3692
- React.createElement('label', null, T_KEY(t, 'form.providerLabel')),
3693
- React.createElement('select', {
3781
+ AGENT_FORM_TYPES.includes(formType) && h('div', { className: 'dsh-cron-form-row' },
3782
+ h('div', { className: 'dsh-cron-form-group' },
3783
+ h('label', null, T_KEY(t, 'form.providerLabel')),
3784
+ h('select', {
3694
3785
  value: formProvider,
3695
3786
  onChange: handleProviderChange
3696
3787
  },
3697
- React.createElement('option', { value: '' }, T_KEY(t, 'form.providerDefault')),
3698
- providers.map((p) => React.createElement('option', { key: p.id, value: p.id }, p.name || p.id))
3788
+ h('option', { value: '' }, T_KEY(t, 'form.providerDefault')),
3789
+ providers.map((p) => h('option', { key: p.id, value: p.id }, p.name || p.id))
3699
3790
  )
3700
3791
  ),
3701
- React.createElement('div', { className: 'dsh-cron-form-group' },
3702
- React.createElement('label', null, T_KEY(t, 'form.modelLabel')),
3703
- React.createElement('select', {
3792
+ h('div', { className: 'dsh-cron-form-group' },
3793
+ h('label', null, T_KEY(t, 'form.modelLabel')),
3794
+ h('select', {
3704
3795
  value: formModel,
3705
3796
  onChange: (e) => setFormModel(e.target.value)
3706
3797
  },
3707
- React.createElement('option', { value: '' }, T_KEY(t, 'form.modelDefault')),
3708
- models.map((m) => React.createElement('option', { key: m.id, value: m.id }, m.name || m.id))
3798
+ h('option', { value: '' }, T_KEY(t, 'form.modelDefault')),
3799
+ models.map((m) => h('option', { key: m.id, value: m.id }, m.name || m.id))
3709
3800
  )
3710
3801
  ),
3711
- React.createElement('div', { className: 'dsh-cron-form-group' },
3712
- React.createElement('label', null, T_KEY(t, 'form.fallbackModelLabel')),
3713
- React.createElement('input', {
3802
+ h('div', { className: 'dsh-cron-form-group' },
3803
+ h('label', null, T_KEY(t, 'form.fallbackModelLabel')),
3804
+ h('input', {
3714
3805
  type: 'text',
3715
3806
  value: formFallbackModel,
3716
3807
  placeholder: T_KEY(t, 'form.fallbackModelPlaceholder'),
3717
3808
  onChange: (e) => setFormFallbackModel(e.target.value)
3718
3809
  }),
3719
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.fallbackModelHint'))
3810
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.fallbackModelHint'))
3720
3811
  ),
3721
- React.createElement('label', { className: 'dsh-cron-checkbox-row', style: { marginTop: '4px' } },
3722
- React.createElement('input', {
3812
+ h('label', { className: 'dsh-cron-checkbox-row', style: { marginTop: '4px' } },
3813
+ h('input', {
3723
3814
  type: 'checkbox',
3724
3815
  checked: formInspectOnFailure,
3725
3816
  onChange: (e) => setFormInspectOnFailure(e.target.checked)
3726
3817
  }),
3727
- React.createElement('span', null, T_KEY(t, 'form.inspectOnFailureLabel'))
3818
+ h('span', null, T_KEY(t, 'form.inspectOnFailureLabel'))
3728
3819
  ),
3729
- formInspectOnFailure && React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.inspectOnFailureHint')),
3730
- React.createElement('label', { className: 'dsh-cron-checkbox-row', style: { marginTop: '8px' } },
3731
- React.createElement('input', {
3820
+ formInspectOnFailure && h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.inspectOnFailureHint')),
3821
+ h('label', { className: 'dsh-cron-checkbox-row', style: { marginTop: '8px' } },
3822
+ h('input', {
3732
3823
  type: 'checkbox',
3733
3824
  checked: formRequireApproval,
3734
3825
  onChange: (e) => setFormRequireApproval(e.target.checked)
3735
3826
  }),
3736
- React.createElement('span', null, T_KEY(t, 'form.requireApprovalLabel'))
3827
+ h('span', null, T_KEY(t, 'form.requireApprovalLabel'))
3737
3828
  ),
3738
- formRequireApproval && React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.requireApprovalHint'))
3829
+ formRequireApproval && h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.requireApprovalHint'))
3739
3830
  ),
3740
- formType === 'http' && React.createElement('div', { className: 'dsh-cron-form-row' },
3741
- React.createElement('div', { className: 'dsh-cron-form-group' },
3742
- React.createElement('label', null, T_KEY(t, 'form.httpMethodLabel')),
3743
- React.createElement('select', {
3831
+ formType === 'http' && h('div', { className: 'dsh-cron-form-row' },
3832
+ h('div', { className: 'dsh-cron-form-group' },
3833
+ h('label', null, T_KEY(t, 'form.httpMethodLabel')),
3834
+ h('select', {
3744
3835
  value: formHttpMethod,
3745
3836
  onChange: (e) => setFormHttpMethod(e.target.value)
3746
3837
  },
3747
- ['GET', 'POST', 'PUT', 'PATCH', 'DELETE', 'HEAD'].map((m) => React.createElement('option', { key: m, value: m }, m))
3838
+ ['GET', 'POST', 'PUT', 'PATCH', 'DELETE', 'HEAD'].map((m) => h('option', { key: m, value: m }, m))
3748
3839
  )
3749
3840
  ),
3750
- React.createElement('div', { className: 'dsh-cron-form-group' },
3751
- React.createElement('label', null, T_KEY(t, 'form.httpUrlLabel')),
3752
- React.createElement('input', {
3841
+ h('div', { className: 'dsh-cron-form-group' },
3842
+ h('label', null, T_KEY(t, 'form.httpUrlLabel')),
3843
+ h('input', {
3753
3844
  required: true,
3754
3845
  value: formHttpUrl,
3755
3846
  placeholder: 'https://example.test/webhook',
@@ -3757,41 +3848,41 @@ onChange: (e) => setFormHttpUrl(e.target.value)
3757
3848
  })
3758
3849
  )
3759
3850
  ),
3760
- formType === 'http' && React.createElement('div', { className: 'dsh-cron-form-row' },
3761
- React.createElement('div', { className: 'dsh-cron-form-group' },
3762
- React.createElement('label', null, T_KEY(t, 'form.httpHeadersLabel')),
3763
- React.createElement('input', {
3851
+ formType === 'http' && h('div', { className: 'dsh-cron-form-row' },
3852
+ h('div', { className: 'dsh-cron-form-group' },
3853
+ h('label', null, T_KEY(t, 'form.httpHeadersLabel')),
3854
+ h('input', {
3764
3855
  value: formHttpHeaders,
3765
3856
  placeholder: '{"Authorization":"Bearer ..."}',
3766
3857
  onChange: (e) => setFormHttpHeaders(e.target.value)
3767
3858
  })
3768
3859
  ),
3769
- React.createElement('div', { className: 'dsh-cron-form-group' },
3770
- React.createElement('label', null, T_KEY(t, 'form.httpBodyLabel')),
3771
- React.createElement('input', {
3860
+ h('div', { className: 'dsh-cron-form-group' },
3861
+ h('label', null, T_KEY(t, 'form.httpBodyLabel')),
3862
+ h('input', {
3772
3863
  value: formHttpBody,
3773
3864
  onChange: (e) => setFormHttpBody(e.target.value)
3774
3865
  })
3775
3866
  )
3776
3867
  ),
3777
- formType === 'ssh' && React.createElement('div', { className: 'dsh-cron-form-row' },
3778
- React.createElement('div', { className: 'dsh-cron-form-group' },
3779
- React.createElement('label', null, T_KEY(t, 'form.sshProfileLabel')),
3780
- React.createElement('input', {
3868
+ formType === 'ssh' && h('div', { className: 'dsh-cron-form-row' },
3869
+ h('div', { className: 'dsh-cron-form-group' },
3870
+ h('label', null, T_KEY(t, 'form.sshProfileLabel')),
3871
+ h('input', {
3781
3872
  value: formSshProfileId,
3782
3873
  placeholder: 'prod-web',
3783
3874
  onChange: (e) => setFormSshProfileId(e.target.value)
3784
3875
  }),
3785
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.sshProfileHint'))
3876
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.sshProfileHint'))
3786
3877
  ),
3787
- React.createElement('div', { className: 'dsh-cron-form-group' },
3788
- React.createElement('label', null, T_KEY(t, 'form.sshTargetLabel')),
3789
- React.createElement('input', {
3878
+ h('div', { className: 'dsh-cron-form-group' },
3879
+ h('label', null, T_KEY(t, 'form.sshTargetLabel')),
3880
+ h('input', {
3790
3881
  value: formSshTarget,
3791
3882
  placeholder: 'user@example.com',
3792
3883
  onChange: (e) => setFormSshTarget(e.target.value)
3793
3884
  }),
3794
- React.createElement('input', {
3885
+ h('input', {
3795
3886
  style: { marginTop: '6px' },
3796
3887
  value: formSshKeyPath,
3797
3888
  placeholder: '~/.ssh/id_ed25519',
@@ -3799,93 +3890,93 @@ onChange: (e) => setFormSshKeyPath(e.target.value)
3799
3890
  })
3800
3891
  )
3801
3892
  ),
3802
- formType === 'docker' && React.createElement('div', { className: 'dsh-cron-form-group' },
3803
- React.createElement('label', null, T_KEY(t, 'form.dockerImageLabel')),
3804
- React.createElement('input', {
3893
+ formType === 'docker' && h('div', { className: 'dsh-cron-form-group' },
3894
+ h('label', null, T_KEY(t, 'form.dockerImageLabel')),
3895
+ h('input', {
3805
3896
  required: true,
3806
3897
  value: formDockerImage,
3807
3898
  placeholder: 'alpine:3.20',
3808
3899
  onChange: (e) => setFormDockerImage(e.target.value)
3809
3900
  })
3810
3901
  ),
3811
- formType === 'skill' && React.createElement('div', { className: 'dsh-cron-form-group' },
3812
- React.createElement('label', null, T_KEY(t, 'form.skillNameLabel')),
3813
- React.createElement('input', {
3902
+ formType === 'skill' && h('div', { className: 'dsh-cron-form-group' },
3903
+ h('label', null, T_KEY(t, 'form.skillNameLabel')),
3904
+ h('input', {
3814
3905
  value: formSkillName,
3815
3906
  placeholder: 'gitea',
3816
3907
  onChange: (e) => setFormSkillName(e.target.value)
3817
3908
  })
3818
3909
  ),
3819
- formType === 'workflow' && React.createElement('div', { className: 'dsh-cron-form-group' },
3820
- React.createElement('label', null, T_KEY(t, 'form.workflowNameLabel')),
3821
- React.createElement('input', {
3910
+ formType === 'workflow' && h('div', { className: 'dsh-cron-form-group' },
3911
+ h('label', null, T_KEY(t, 'form.workflowNameLabel')),
3912
+ h('input', {
3822
3913
  value: formWorkflowName,
3823
3914
  placeholder: 'nightly-release',
3824
3915
  onChange: (e) => setFormWorkflowName(e.target.value)
3825
3916
  })
3826
3917
  ),
3827
- (formType === 'node' || formType === 'python') && React.createElement('div', { className: 'dsh-cron-form-group' },
3828
- React.createElement('label', null, formType === 'node' ? 'Node.js binary (optional)' : 'Python interpreter (optional)'),
3829
- React.createElement('input', {
3918
+ (formType === 'node' || formType === 'python') && h('div', { className: 'dsh-cron-form-group' },
3919
+ h('label', null, formType === 'node' ? 'Node.js binary (optional)' : 'Python interpreter (optional)'),
3920
+ h('input', {
3830
3921
  value: formType === 'node' ? formNodePath : formPythonPath,
3831
3922
  placeholder: formType === 'node' ? 'auto' : '.venv/bin/python',
3832
3923
  onChange: (e) => (formType === 'node' ? setFormNodePath(e.target.value) : setFormPythonPath(e.target.value))
3833
3924
  })
3834
3925
  ),
3835
- !AGENT_FORM_TYPES.includes(formType) && React.createElement('div', { className: 'dsh-cron-form-group' },
3836
- React.createElement('label', null, T_KEY(t, 'form.envLabel')),
3837
- React.createElement('textarea', {
3926
+ !AGENT_FORM_TYPES.includes(formType) && h('div', { className: 'dsh-cron-form-group' },
3927
+ h('label', null, T_KEY(t, 'form.envLabel')),
3928
+ h('textarea', {
3838
3929
  rows: 3,
3839
3930
  style: { fontFamily: 'monospace', fontSize: '12.5px' },
3840
3931
  value: formEnv,
3841
3932
  placeholder: T_KEY(t, 'form.envPlaceholder'),
3842
3933
  onChange: (e) => setFormEnv(e.target.value)
3843
3934
  }),
3844
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.envHint'))
3935
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.envHint'))
3845
3936
  ),
3846
- React.createElement('div', { className: 'dsh-cron-form-row' },
3847
- React.createElement('div', { className: 'dsh-cron-form-group' },
3848
- React.createElement('label', null, T_KEY(t, 'form.cwdLabel')),
3849
- React.createElement('input', {
3937
+ h('div', { className: 'dsh-cron-form-row' },
3938
+ h('div', { className: 'dsh-cron-form-group' },
3939
+ h('label', null, T_KEY(t, 'form.cwdLabel')),
3940
+ h('input', {
3850
3941
  value: formCwd,
3851
3942
  placeholder: '/srv/app',
3852
3943
  onChange: (e) => setFormCwd(e.target.value)
3853
3944
  })
3854
3945
  ),
3855
- React.createElement('div', { className: 'dsh-cron-form-group' },
3856
- React.createElement('label', null, T_KEY(t, 'form.workspaceLabel')),
3857
- React.createElement('input', {
3946
+ h('div', { className: 'dsh-cron-form-group' },
3947
+ h('label', null, T_KEY(t, 'form.workspaceLabel')),
3948
+ h('input', {
3858
3949
  value: formWorkspaceId,
3859
3950
  onChange: (e) => setFormWorkspaceId(e.target.value)
3860
3951
  })
3861
3952
  )
3862
3953
  ),
3863
- AGENT_FORM_TYPES.includes(formType) && React.createElement('div', { className: 'dsh-cron-form-group' },
3864
- React.createElement('label', { className: 'dsh-cron-checkbox-row' },
3865
- React.createElement('input', {
3954
+ AGENT_FORM_TYPES.includes(formType) && h('div', { className: 'dsh-cron-form-group' },
3955
+ h('label', { className: 'dsh-cron-checkbox-row' },
3956
+ h('input', {
3866
3957
  type: 'checkbox',
3867
3958
  checked: formWorktree,
3868
3959
  onChange: (e) => setFormWorktree(e.target.checked)
3869
3960
  }),
3870
- React.createElement('span', null, T_KEY(t, 'form.worktreeLabel'))
3961
+ h('span', null, T_KEY(t, 'form.worktreeLabel'))
3871
3962
  ),
3872
- formWorktree && React.createElement('label', { className: 'dsh-cron-checkbox-row', style: { marginLeft: '24px', marginTop: '6px' } },
3873
- React.createElement('input', {
3963
+ formWorktree && h('label', { className: 'dsh-cron-checkbox-row', style: { marginLeft: '24px', marginTop: '6px' } },
3964
+ h('input', {
3874
3965
  type: 'checkbox',
3875
3966
  checked: formKeepWorktree,
3876
3967
  onChange: (e) => setFormKeepWorktree(e.target.checked)
3877
3968
  }),
3878
- React.createElement('span', null, T_KEY(t, 'form.keepWorktreeLabel'))
3969
+ h('span', null, T_KEY(t, 'form.keepWorktreeLabel'))
3879
3970
  )
3880
3971
  ),
3881
- formType !== 'http' && React.createElement('div', { className: 'dsh-cron-form-group' },
3882
- React.createElement('div', { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '4px' } },
3883
- React.createElement('label', { style: { margin: 0 } }, AGENT_FORM_TYPES.includes(formType) ? T_KEY(t, 'form.promptLabelLlm') : T_KEY(t, 'form.promptLabelScript')),
3884
- (selectedTaskMeta && selectedTaskMeta.promptHistory && selectedTaskMeta.promptHistory.length > 0) ? React.createElement('div', { style: { display: 'flex', gap: '6px', alignItems: 'center' } },
3885
- React.createElement('span', {
3972
+ formType !== 'http' && h('div', { className: 'dsh-cron-form-group' },
3973
+ h('div', { style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '4px' } },
3974
+ h('label', { style: { margin: 0 } }, AGENT_FORM_TYPES.includes(formType) ? T_KEY(t, 'form.promptLabelLlm') : T_KEY(t, 'form.promptLabelScript')),
3975
+ (selectedTaskMeta && selectedTaskMeta.promptHistory && selectedTaskMeta.promptHistory.length > 0) ? h('div', { style: { display: 'flex', gap: '6px', alignItems: 'center' } },
3976
+ h('span', {
3886
3977
  style: { fontSize: '11px', padding: '1px 6px', borderRadius: '4px', background: 'var(--dsw-alias-bg-layer-3, #222)', color: 'var(--dsh-cron-info, #4af)', border: '1px solid var(--dsw-alias-border-l2, #333)' }
3887
3978
  }, 'v' + (selectedTaskMeta.promptVersion || 1) + ' (' + (selectedTaskMeta.promptHistory[selectedTaskMeta.promptHistory.length - 1]?.successRate !== undefined ? Math.round(selectedTaskMeta.promptHistory[selectedTaskMeta.promptHistory.length - 1].successRate * 100) : 100) + '% SR)'),
3888
- React.createElement('select', {
3979
+ h('select', {
3889
3980
  style: { fontSize: '11px', padding: '1px 4px', background: 'var(--dsw-alias-bg-base, #111)', color: 'var(--dsw-alias-label-primary, #ddd)', border: '1px solid var(--dsw-alias-border-l2, #333)', borderRadius: '4px' },
3890
3981
  onChange: (e) => {
3891
3982
  const targetV = Number(e.target.value);
@@ -3895,11 +3986,11 @@ setFormPrompt(entry.prompt);
3895
3986
  }
3896
3987
  }
3897
3988
  },
3898
- selectedTaskMeta.promptHistory.map((h) => React.createElement('option', { key: h.version, value: h.version }, 'v' + h.version + ' (' + Math.round((h.successRate || 1) * 100) + '%)'))
3989
+ selectedTaskMeta.promptHistory.map((h) => h('option', { key: h.version, value: h.version }, 'v' + h.version + ' (' + Math.round((h.successRate || 1) * 100) + '%)'))
3899
3990
  )
3900
3991
  ) : null
3901
3992
  ),
3902
- React.createElement('textarea', {
3993
+ h('textarea', {
3903
3994
  required: true,
3904
3995
  rows: 9,
3905
3996
  style: { fontFamily: 'monospace', fontSize: '12.5px', lineHeight: '1.45' },
@@ -3918,7 +4009,7 @@ placeholder: AGENT_FORM_TYPES.includes(formType)
3918
4009
  onChange: (e) => setFormPrompt(e.target.value)
3919
4010
  })
3920
4011
  ),
3921
- React.createElement('div', {
4012
+ h('div', {
3922
4013
  style: {
3923
4014
  background: 'var(--dsw-alias-bg-layer-3, color-mix(in srgb, var(--dsw-alias-label-primary) 2%, transparent))',
3924
4015
  border: '1px solid var(--dsw-alias-border-l2)',
@@ -3927,31 +4018,31 @@ padding: '12px 14px',
3927
4018
  marginBottom: '16px'
3928
4019
  }
3929
4020
  },
3930
- React.createElement('div', { style: { fontWeight: 500, fontSize: '13px', color: 'var(--dsw-alias-label-primary, #eee)', marginBottom: '8px', display: 'flex', alignItems: 'center', gap: '6px' } },
3931
- React.createElement('span', { style: { display: 'flex', alignItems: 'center', color: 'var(--dsh-cron-info)' }, ...iconHtml(ICON_TELEGRAM) }),
4021
+ h('div', { style: { fontWeight: 500, fontSize: '13px', color: 'var(--dsw-alias-label-primary, #eee)', marginBottom: '8px', display: 'flex', alignItems: 'center', gap: '6px' } },
4022
+ h('span', { style: { display: 'flex', alignItems: 'center', color: 'var(--dsh-cron-info)' }, ...iconHtml(ICON_TELEGRAM) }),
3932
4023
  T_KEY(t, 'form.notifyTitle')
3933
4024
  ),
3934
- React.createElement('label', { className: 'dsh-cron-checkbox-row', style: { marginBottom: formNotifyTelegram ? '8px' : '0' } },
3935
- React.createElement('input', {
4025
+ h('label', { className: 'dsh-cron-checkbox-row', style: { marginBottom: formNotifyTelegram ? '8px' : '0' } },
4026
+ h('input', {
3936
4027
  type: 'checkbox',
3937
4028
  checked: formNotifyTelegram,
3938
4029
  onChange: (e) => setFormNotifyTelegram(e.target.checked)
3939
4030
  }),
3940
- React.createElement('span', null, T_KEY(t, 'form.notifyTelegram'))
4031
+ h('span', null, T_KEY(t, 'form.notifyTelegram'))
3941
4032
  ),
3942
- (formNotifyTelegram || formChannels.length > 0) && React.createElement('label', { className: 'dsh-cron-checkbox-row', style: { marginLeft: '24px', marginTop: '6px' } },
3943
- React.createElement('input', {
4033
+ (formNotifyTelegram || formChannels.length > 0) && h('label', { className: 'dsh-cron-checkbox-row', style: { marginLeft: '24px', marginTop: '6px' } },
4034
+ h('input', {
3944
4035
  type: 'checkbox',
3945
4036
  checked: formOnlyOnFailure,
3946
4037
  onChange: (e) => setFormOnlyOnFailure(e.target.checked)
3947
4038
  }),
3948
- React.createElement('span', null, T_KEY(t, 'form.notifyOnlyFailure'))
4039
+ h('span', null, T_KEY(t, 'form.notifyOnlyFailure'))
3949
4040
  ),
3950
- React.createElement('div', { style: { marginTop: '12px', paddingTop: '10px', borderTop: '1px solid var(--dsw-alias-border-l2)' } },
3951
- React.createElement('div', { style: { fontWeight: 500, fontSize: '12.5px', color: 'var(--dsw-alias-label-secondary, #aaa)', marginBottom: '8px' } }, T_KEY(t, 'form.channelsTitle')),
3952
- React.createElement('div', { className: 'dsh-cron-channel-grid' },
3953
- ...DELIVERY_CHANNELS.map((id) => React.createElement('label', { key: id, className: 'dsh-cron-checkbox-row' },
3954
- React.createElement('input', {
4041
+ h('div', { style: { marginTop: '12px', paddingTop: '10px', borderTop: '1px solid var(--dsw-alias-border-l2)' } },
4042
+ h('div', { style: { fontWeight: 500, fontSize: '12.5px', color: 'var(--dsw-alias-label-secondary, #aaa)', marginBottom: '8px' } }, T_KEY(t, 'form.channelsTitle')),
4043
+ h('div', { className: 'dsh-cron-channel-grid' },
4044
+ ...DELIVERY_CHANNELS.map((id) => h('label', { key: id, className: 'dsh-cron-checkbox-row' },
4045
+ h('input', {
3955
4046
  type: 'checkbox',
3956
4047
  checked: formChannels.indexOf(id) >= 0,
3957
4048
  onChange: (e) => {
@@ -3962,56 +4053,56 @@ return DELIVERY_CHANNELS.filter((c) => set.has(c));
3962
4053
  });
3963
4054
  }
3964
4055
  }),
3965
- React.createElement('span', null, T_KEY(t, CHANNEL_LABEL_KEYS[id]))
4056
+ h('span', null, T_KEY(t, CHANNEL_LABEL_KEYS[id]))
3966
4057
  ))
3967
4058
  ),
3968
- React.createElement('div', { className: 'dsh-cron-hint', style: { marginTop: '6px' } }, T_KEY(t, 'form.channelsHint'))
4059
+ h('div', { className: 'dsh-cron-hint', style: { marginTop: '6px' } }, T_KEY(t, 'form.channelsHint'))
3969
4060
  ),
3970
- React.createElement('div', { className: 'dsh-cron-form-group', style: { marginTop: '12px', marginBottom: 0 } },
3971
- React.createElement('label', null, T_KEY(t, 'form.templateLabel')),
3972
- React.createElement('input', {
4061
+ h('div', { className: 'dsh-cron-form-group', style: { marginTop: '12px', marginBottom: 0 } },
4062
+ h('label', null, T_KEY(t, 'form.templateLabel')),
4063
+ h('input', {
3973
4064
  type: 'text',
3974
4065
  value: formTemplate,
3975
4066
  placeholder: T_KEY(t, 'form.templatePlaceholder'),
3976
4067
  onChange: (e) => setFormTemplate(e.target.value)
3977
4068
  }),
3978
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.templateHint'))
4069
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.templateHint'))
3979
4070
  ),
3980
- !AGENT_FORM_TYPES.includes(formType) && React.createElement('div', { className: 'dsh-cron-form-group', style: { marginTop: '12px', marginBottom: 0 } },
3981
- React.createElement('label', null, T_KEY(t, 'form.silentRuleLabel')),
3982
- React.createElement('input', {
4071
+ !AGENT_FORM_TYPES.includes(formType) && h('div', { className: 'dsh-cron-form-group', style: { marginTop: '12px', marginBottom: 0 } },
4072
+ h('label', null, T_KEY(t, 'form.silentRuleLabel')),
4073
+ h('input', {
3983
4074
  type: 'text',
3984
4075
  value: formSilentRule,
3985
4076
  placeholder: T_KEY(t, 'form.silentRulePlaceholder'),
3986
4077
  onChange: (e) => setFormSilentRule(e.target.value)
3987
4078
  }),
3988
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.silentRuleHint'))
4079
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.silentRuleHint'))
3989
4080
  )
3990
4081
  ),
3991
- React.createElement('div', {
4082
+ h('div', {
3992
4083
  style: {
3993
4084
  marginTop: '16px',
3994
4085
  paddingTop: '14px',
3995
4086
  borderTop: '1px solid var(--dsw-alias-border-l2)'
3996
4087
  }
3997
4088
  },
3998
- React.createElement('div', { style: { fontWeight: '600', fontSize: '13px', marginBottom: '10px' } }, T_KEY(t, 'form.reliabilityTitle')),
3999
- React.createElement('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4000
- React.createElement('div', { className: 'dsh-cron-form-group' },
4001
- React.createElement('label', null, T_KEY(t, 'form.preflightLabel')),
4002
- React.createElement('select', {
4089
+ h('div', { style: { fontWeight: '600', fontSize: '13px', marginBottom: '10px' } }, T_KEY(t, 'form.reliabilityTitle')),
4090
+ h('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4091
+ h('div', { className: 'dsh-cron-form-group' },
4092
+ h('label', null, T_KEY(t, 'form.preflightLabel')),
4093
+ h('select', {
4003
4094
  value: formPreflightType,
4004
4095
  onChange: (e) => setFormPreflightType(e.target.value)
4005
4096
  },
4006
- React.createElement('option', { value: 'none' }, T_KEY(t, 'form.preflightNone')),
4007
- React.createElement('option', { value: 'http' }, T_KEY(t, 'form.preflightHttp')),
4008
- React.createElement('option', { value: 'shell' }, T_KEY(t, 'form.preflightShell')),
4009
- React.createElement('option', { value: 'disk' }, T_KEY(t, 'form.preflightDisk'))
4097
+ h('option', { value: 'none' }, T_KEY(t, 'form.preflightNone')),
4098
+ h('option', { value: 'http' }, T_KEY(t, 'form.preflightHttp')),
4099
+ h('option', { value: 'shell' }, T_KEY(t, 'form.preflightShell')),
4100
+ h('option', { value: 'disk' }, T_KEY(t, 'form.preflightDisk'))
4010
4101
  )
4011
4102
  ),
4012
- formPreflightType !== 'none' && React.createElement('div', { className: 'dsh-cron-form-group' },
4013
- React.createElement('label', null, T_KEY(t, 'form.preflightTargetLabel')),
4014
- React.createElement('input', {
4103
+ formPreflightType !== 'none' && h('div', { className: 'dsh-cron-form-group' },
4104
+ h('label', null, T_KEY(t, 'form.preflightTargetLabel')),
4105
+ h('input', {
4015
4106
  type: 'text',
4016
4107
  value: formPreflightTarget,
4017
4108
  placeholder: T_KEY(t, 'form.preflightTargetPlaceholder'),
@@ -4019,19 +4110,19 @@ onChange: (e) => setFormPreflightTarget(e.target.value)
4019
4110
  })
4020
4111
  )
4021
4112
  ),
4022
- React.createElement('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4023
- React.createElement('div', { className: 'dsh-cron-form-group' },
4024
- React.createElement('label', null, T_KEY(t, 'form.heartbeatIntervalLabel')),
4025
- React.createElement('input', {
4113
+ h('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4114
+ h('div', { className: 'dsh-cron-form-group' },
4115
+ h('label', null, T_KEY(t, 'form.heartbeatIntervalLabel')),
4116
+ h('input', {
4026
4117
  type: 'number',
4027
4118
  value: formHeartbeatIntervalSeconds,
4028
4119
  min: 0,
4029
4120
  onChange: (e) => setFormHeartbeatIntervalSeconds(Number(e.target.value))
4030
4121
  })
4031
4122
  ),
4032
- formHeartbeatIntervalSeconds > 0 && React.createElement('div', { className: 'dsh-cron-form-group' },
4033
- React.createElement('label', null, T_KEY(t, 'form.gracePeriodLabel')),
4034
- React.createElement('input', {
4123
+ formHeartbeatIntervalSeconds > 0 && h('div', { className: 'dsh-cron-form-group' },
4124
+ h('label', null, T_KEY(t, 'form.gracePeriodLabel')),
4125
+ h('input', {
4035
4126
  type: 'number',
4036
4127
  value: formGracePeriodSeconds,
4037
4128
  min: 1,
@@ -4039,10 +4130,10 @@ onChange: (e) => setFormGracePeriodSeconds(Number(e.target.value))
4039
4130
  })
4040
4131
  )
4041
4132
  ),
4042
- React.createElement('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4043
- React.createElement('div', { className: 'dsh-cron-form-group' },
4044
- React.createElement('label', null, T_KEY(t, 'form.priorityLabel')),
4045
- React.createElement('input', {
4133
+ h('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4134
+ h('div', { className: 'dsh-cron-form-group' },
4135
+ h('label', null, T_KEY(t, 'form.priorityLabel')),
4136
+ h('input', {
4046
4137
  type: 'number',
4047
4138
  value: formPriority,
4048
4139
  min: 1,
@@ -4050,117 +4141,138 @@ max: 10,
4050
4141
  onChange: (e) => setFormPriority(Number(e.target.value))
4051
4142
  })
4052
4143
  ),
4053
- React.createElement('div', { className: 'dsh-cron-form-group' },
4054
- React.createElement('label', null, T_KEY(t, 'form.concurrencyGroupLabel')),
4055
- React.createElement('input', {
4144
+ h('div', { className: 'dsh-cron-form-group' },
4145
+ h('label', null, T_KEY(t, 'form.concurrencyGroupLabel')),
4146
+ h('input', {
4056
4147
  type: 'text',
4057
4148
  value: formConcurrencyGroup,
4058
4149
  onChange: (e) => setFormConcurrencyGroup(e.target.value)
4059
4150
  })
4060
4151
  )
4061
4152
  ),
4062
- React.createElement('div', { className: 'dsh-cron-form-group' },
4063
- React.createElement('label', null, T_KEY(t, 'form.selfHealingLabel')),
4064
- React.createElement('input', {
4153
+ h('div', { className: 'dsh-cron-form-group' },
4154
+ h('label', null, T_KEY(t, 'form.selfHealingLabel')),
4155
+ h('input', {
4065
4156
  type: 'text',
4066
4157
  value: formSelfHealingCommand,
4067
4158
  placeholder: T_KEY(t, 'form.selfHealingPlaceholder'),
4068
4159
  onChange: (e) => setFormSelfHealingCommand(e.target.value)
4069
4160
  })
4070
4161
  ),
4071
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', gap: '8px', marginTop: '6px' } },
4072
- React.createElement('input', {
4162
+ h('div', { style: { display: 'flex', alignItems: 'center', gap: '8px', marginTop: '6px' } },
4163
+ h('input', {
4073
4164
  type: 'checkbox',
4074
4165
  id: 'formAutoDiagnoseCheckbox',
4075
4166
  checked: formAutoDiagnose,
4076
4167
  onChange: (e) => setFormAutoDiagnose(e.target.checked)
4077
4168
  }),
4078
- React.createElement('label', { htmlFor: 'formAutoDiagnoseCheckbox', style: { margin: 0, fontSize: '12.5px', cursor: 'pointer' } }, T_KEY(t, 'form.autoDiagnoseLabel'))
4169
+ h('label', { htmlFor: 'formAutoDiagnoseCheckbox', style: { margin: 0, fontSize: '12.5px', cursor: 'pointer' } }, T_KEY(t, 'form.autoDiagnoseLabel'))
4079
4170
  )
4080
4171
  ),
4081
- React.createElement('div', {
4172
+ h('div', {
4082
4173
  style: {
4083
4174
  marginTop: '16px',
4084
4175
  paddingTop: '14px',
4085
4176
  borderTop: '1px solid var(--dsw-alias-border-l2)'
4086
4177
  }
4087
4178
  },
4088
- React.createElement('div', { style: { fontWeight: '600', fontSize: '13px', marginBottom: '10px' } }, '⛓️ ' + T_KEY(t, 'form.chainingTitle')),
4089
- React.createElement('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4090
- React.createElement('div', { className: 'dsh-cron-form-group' },
4091
- React.createElement('label', null, T_KEY(t, 'form.onSuccessLabel')),
4092
- React.createElement('input', {
4179
+ h('div', { style: { fontWeight: '600', fontSize: '13px', marginBottom: '10px' } }, '⛓️ ' + T_KEY(t, 'form.chainingTitle')),
4180
+ h('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr', gap: '10px' } },
4181
+ h('div', { className: 'dsh-cron-form-group' },
4182
+ h('label', null, T_KEY(t, 'form.onSuccessLabel')),
4183
+ h('input', {
4093
4184
  type: 'text',
4094
4185
  value: formOnSuccess,
4095
4186
  placeholder: 'task-build, task-test',
4096
4187
  onChange: (e) => setFormOnSuccess(e.target.value)
4097
4188
  }),
4098
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.onSuccessHint'))
4189
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.onSuccessHint'))
4099
4190
  ),
4100
- React.createElement('div', { className: 'dsh-cron-form-group' },
4101
- React.createElement('label', null, T_KEY(t, 'form.onFailureLabel')),
4102
- React.createElement('input', {
4191
+ h('div', { className: 'dsh-cron-form-group' },
4192
+ h('label', null, T_KEY(t, 'form.onFailureLabel')),
4193
+ h('input', {
4103
4194
  type: 'text',
4104
4195
  value: formOnFailure,
4105
4196
  placeholder: 'task-alert',
4106
4197
  onChange: (e) => setFormOnFailure(e.target.value)
4107
4198
  }),
4108
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.onFailureHint'))
4199
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.onFailureHint'))
4109
4200
  )
4110
4201
  ),
4111
- React.createElement('div', { style: { display: 'grid', gridTemplateColumns: '2fr 1fr', gap: '10px', marginTop: '8px' } },
4112
- React.createElement('div', { className: 'dsh-cron-form-group' },
4113
- React.createElement('label', null, T_KEY(t, 'form.dependsOnLabel')),
4114
- React.createElement('input', {
4202
+ h('div', { style: { display: 'grid', gridTemplateColumns: '2fr 1fr', gap: '10px', marginTop: '8px' } },
4203
+ h('div', { className: 'dsh-cron-form-group' },
4204
+ h('label', null, T_KEY(t, 'form.dependsOnLabel')),
4205
+ h('input', {
4115
4206
  type: 'text',
4116
4207
  value: formDependsOn,
4117
4208
  placeholder: 'task-build, task-lint',
4118
4209
  onChange: (e) => setFormDependsOn(e.target.value)
4119
4210
  }),
4120
- React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.dependsOnHint'))
4211
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.dependsOnHint'))
4121
4212
  ),
4122
- React.createElement('div', { className: 'dsh-cron-form-group' },
4123
- React.createElement('label', null, T_KEY(t, 'form.joinPolicyLabel')),
4124
- React.createElement('select', {
4213
+ h('div', { className: 'dsh-cron-form-group' },
4214
+ h('label', null, T_KEY(t, 'form.joinPolicyLabel')),
4215
+ h('select', {
4125
4216
  value: formJoinPolicy,
4126
4217
  onChange: (e) => setFormJoinPolicy(e.target.value)
4127
4218
  },
4128
- React.createElement('option', { value: 'all_success' }, T_KEY(t, 'form.joinPolicyAll')),
4129
- React.createElement('option', { value: 'any_success' }, T_KEY(t, 'form.joinPolicyAny'))
4219
+ h('option', { value: 'all_success' }, T_KEY(t, 'form.joinPolicyAll')),
4220
+ h('option', { value: 'any_success' }, T_KEY(t, 'form.joinPolicyAny'))
4130
4221
  )
4131
4222
  )
4132
4223
  ),
4133
- React.createElement('div', { style: { marginTop: '12px', padding: '10px', background: 'var(--dsw-alias-bg-layer-2)', borderRadius: '6px' } },
4134
- React.createElement('label', { style: { display: 'flex', alignItems: 'center', gap: '8px', cursor: 'pointer', fontWeight: '500' } },
4135
- React.createElement('input', {
4224
+ h('div', { className: 'dsh-cron-form-group', style: { marginTop: '8px' } },
4225
+ h('label', null, T_KEY(t, 'form.elseTaskLabel')),
4226
+ h('input', {
4227
+ type: 'text',
4228
+ value: formElseTask || '',
4229
+ placeholder: T_KEY(t, 'form.elseTaskPlaceholder'),
4230
+ onChange: (e) => setFormElseTask(e.target.value)
4231
+ }),
4232
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.elseTaskHint'))
4233
+ ),
4234
+ h('div', { className: 'dsh-cron-form-group', style: { marginTop: '8px' } },
4235
+ h('label', { style: { display: 'flex', alignItems: 'center', gap: '8px', cursor: 'pointer' } },
4236
+ h('input', {
4237
+ type: 'checkbox',
4238
+ checked: Boolean(formAutoHeal),
4239
+ onChange: (e) => setFormAutoHeal(e.target.checked)
4240
+ }),
4241
+ h('span', { style: { fontWeight: '600' } }, '🩺 ' + T_KEY(t, 'form.autoHealLabel'))
4242
+ ),
4243
+ h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'form.autoHealHint'))
4244
+ ),
4245
+ h('div', { style: { marginTop: '12px', padding: '10px', background: 'var(--dsw-alias-bg-layer-2)', borderRadius: '6px' } },
4246
+ h('label', { style: { display: 'flex', alignItems: 'center', gap: '8px', cursor: 'pointer', fontWeight: '500' } },
4247
+ h('input', {
4136
4248
  type: 'checkbox',
4137
4249
  checked: formAdaptiveEnabled,
4138
4250
  onChange: (e) => setFormAdaptiveEnabled(e.target.checked)
4139
4251
  }),
4140
4252
  T_KEY(t, 'form.adaptiveEnabled')
4141
4253
  ),
4142
- React.createElement('div', { className: 'dsh-cron-hint', style: { marginLeft: '24px' } }, T_KEY(t, 'form.adaptiveHint')),
4143
- formAdaptiveEnabled && React.createElement('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr 1fr 1fr', gap: '8px', marginTop: '8px', marginLeft: '24px' } },
4144
- React.createElement('div', null,
4145
- React.createElement('label', { style: { fontSize: '11px' } }, 'Min'),
4146
- React.createElement('input', { type: 'text', value: formAdaptiveMinInterval, placeholder: '5m', onChange: (e) => setFormAdaptiveMinInterval(e.target.value) })
4254
+ h('div', { className: 'dsh-cron-hint', style: { marginLeft: '24px' } }, T_KEY(t, 'form.adaptiveHint')),
4255
+ formAdaptiveEnabled && h('div', { style: { display: 'grid', gridTemplateColumns: '1fr 1fr 1fr 1fr', gap: '8px', marginTop: '8px', marginLeft: '24px' } },
4256
+ h('div', null,
4257
+ h('label', { style: { fontSize: '11px' } }, 'Min'),
4258
+ h('input', { type: 'text', value: formAdaptiveMinInterval, placeholder: '5m', onChange: (e) => setFormAdaptiveMinInterval(e.target.value) })
4147
4259
  ),
4148
- React.createElement('div', null,
4149
- React.createElement('label', { style: { fontSize: '11px' } }, 'Max'),
4150
- React.createElement('input', { type: 'text', value: formAdaptiveMaxInterval, placeholder: '2h', onChange: (e) => setFormAdaptiveMaxInterval(e.target.value) })
4260
+ h('div', null,
4261
+ h('label', { style: { fontSize: '11px' } }, 'Max'),
4262
+ h('input', { type: 'text', value: formAdaptiveMaxInterval, placeholder: '2h', onChange: (e) => setFormAdaptiveMaxInterval(e.target.value) })
4151
4263
  ),
4152
- React.createElement('div', null,
4153
- React.createElement('label', { style: { fontSize: '11px' } }, 'Factor'),
4154
- React.createElement('input', { type: 'number', step: '0.1', value: formAdaptiveBackoffFactor, placeholder: '1.5', onChange: (e) => setFormAdaptiveBackoffFactor(e.target.value) })
4264
+ h('div', null,
4265
+ h('label', { style: { fontSize: '11px' } }, 'Factor'),
4266
+ h('input', { type: 'number', step: '0.1', value: formAdaptiveBackoffFactor, placeholder: '1.5', onChange: (e) => setFormAdaptiveBackoffFactor(e.target.value) })
4155
4267
  ),
4156
- React.createElement('div', null,
4157
- React.createElement('label', { style: { fontSize: '11px' } }, 'Idle Runs'),
4158
- React.createElement('input', { type: 'number', value: formAdaptiveIdleThreshold, placeholder: '3', onChange: (e) => setFormAdaptiveIdleThreshold(e.target.value) })
4268
+ h('div', null,
4269
+ h('label', { style: { fontSize: '11px' } }, 'Idle Runs'),
4270
+ h('input', { type: 'number', value: formAdaptiveIdleThreshold, placeholder: '3', onChange: (e) => setFormAdaptiveIdleThreshold(e.target.value) })
4159
4271
  )
4160
4272
  )
4161
4273
  )
4162
4274
  ),
4163
- selectedTaskMeta && React.createElement('div', {
4275
+ selectedTaskMeta && h('div', {
4164
4276
  style: {
4165
4277
  background: 'var(--dsw-alias-bg-layer-3, color-mix(in srgb, var(--dsw-alias-label-primary) 3%, transparent))',
4166
4278
  border: '1px solid var(--dsw-alias-border-l2)',
@@ -4174,11 +4286,11 @@ justifyContent: 'space-between',
4174
4286
  alignItems: 'center'
4175
4287
  }
4176
4288
  },
4177
- React.createElement('div', null,
4178
- React.createElement('span', null, T_KEY(t, 'form.nextRunLabel')),
4179
- React.createElement('strong', { style: { color: 'var(--dsw-alias-label-primary, #eee)' } }, selectedTaskMeta.nextRunAt ? new Date(selectedTaskMeta.nextRunAt).toLocaleString() : T_KEY(t, 'form.notScheduled'))
4289
+ h('div', null,
4290
+ h('span', null, T_KEY(t, 'form.nextRunLabel')),
4291
+ h('strong', { style: { color: 'var(--dsw-alias-label-primary, #eee)' } }, selectedTaskMeta.nextRunAt ? new Date(selectedTaskMeta.nextRunAt).toLocaleString() : T_KEY(t, 'form.notScheduled'))
4180
4292
  ),
4181
- React.createElement('button', {
4293
+ h('button', {
4182
4294
  type: 'button',
4183
4295
  className: 'dsh-cron-btn-secondary',
4184
4296
  style: { padding: '4px 10px', fontSize: '12px' },
@@ -4188,13 +4300,13 @@ if (formId) loadTaskHistory(formId);
4188
4300
  }
4189
4301
  }, T_KEY(t, 'actions.runNow'))
4190
4302
  ),
4191
- React.createElement('div', { className: 'dsh-cron-modal-foot' },
4192
- React.createElement('button', {
4303
+ h('div', { className: 'dsh-cron-modal-foot' },
4304
+ h('button', {
4193
4305
  type: 'button',
4194
4306
  className: 'dsh-cron-btn-secondary',
4195
4307
  onClick: closeManualModalWithConfirm
4196
4308
  }, T_KEY(t, 'modal.cancel')),
4197
- React.createElement('button', {
4309
+ h('button', {
4198
4310
  type: 'submit',
4199
4311
  className: 'dsh-cron-btn-primary'
4200
4312
  }, formId ? T_KEY(t, 'modal.save') : T_KEY(t, 'modal.create'))
@@ -4202,28 +4314,28 @@ className: 'dsh-cron-btn-primary'
4202
4314
  )
4203
4315
  )
4204
4316
  ),
4205
- dryRunResult && React.createElement('div', { className: 'dsh-cron-modal-overlay', onClick: () => setDryRunResult(null) },
4206
- React.createElement('div', {
4317
+ dryRunResult && h('div', { className: 'dsh-cron-modal-overlay', onClick: () => setDryRunResult(null) },
4318
+ h('div', {
4207
4319
  className: 'dsh-cron-modal',
4208
4320
  style: { maxWidth: '580px' },
4209
4321
  role: 'dialog',
4210
4322
  'aria-modal': 'true',
4211
4323
  onClick: (e) => e.stopPropagation()
4212
4324
  },
4213
- React.createElement('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center' } },
4214
- React.createElement('div', { className: 'dsh-cron-modal-title', style: { margin: 0 } }, T_KEY(t, 'dryRun.title')),
4215
- React.createElement('button', {
4325
+ h('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center' } },
4326
+ h('div', { className: 'dsh-cron-modal-title', style: { margin: 0 } }, T_KEY(t, 'dryRun.title')),
4327
+ h('button', {
4216
4328
  type: 'button',
4217
4329
  className: 'dsh-cron-icon-btn',
4218
4330
  onClick: () => setDryRunResult(null)
4219
4331
  }, '✕')
4220
4332
  ),
4221
- React.createElement('div', { style: { marginTop: '12px', display: 'flex', flexDirection: 'column', gap: '8px', fontSize: '13px' } },
4222
- React.createElement('div', null, React.createElement('strong', null, T_KEY(t, 'dryRun.status') + ': '), React.createElement('span', { style: { color: dryRunResult.ok ? 'var(--dsh-cron-success)' : 'var(--dsh-cron-danger)' } }, dryRunResult.ok ? ((dryRunResult.result && dryRunResult.result.status) || dryRunResult.status || 'success') : 'failed')),
4223
- ((dryRunResult.result && dryRunResult.result.preflight) || dryRunResult.preflight) && React.createElement('div', null, React.createElement('strong', null, T_KEY(t, 'dryRun.preflight') + ': '), React.createElement('span', null, (((dryRunResult.result && dryRunResult.result.preflight) || dryRunResult.preflight).passed) ? '✓ Passed' : '✗ Failed (' + ((((dryRunResult.result && dryRunResult.result.preflight) || dryRunResult.preflight).reason) || '') + ')')),
4224
- React.createElement('div', null, React.createElement('strong', null, T_KEY(t, 'dryRun.duration') + ': '), React.createElement('span', null, (((dryRunResult.result && dryRunResult.result.durationMs) !== undefined ? dryRunResult.result.durationMs : dryRunResult.durationMs) || 0) + 'ms')),
4225
- React.createElement('div', { style: { marginTop: '6px' } }, React.createElement('strong', null, T_KEY(t, 'dryRun.output') + ':')),
4226
- React.createElement('pre', {
4333
+ h('div', { style: { marginTop: '12px', display: 'flex', flexDirection: 'column', gap: '8px', fontSize: '13px' } },
4334
+ h('div', null, h('strong', null, T_KEY(t, 'dryRun.status') + ': '), h('span', { style: { color: dryRunResult.ok ? 'var(--dsh-cron-success)' : 'var(--dsh-cron-danger)' } }, dryRunResult.ok ? ((dryRunResult.result && dryRunResult.result.status) || dryRunResult.status || 'success') : 'failed')),
4335
+ ((dryRunResult.result && dryRunResult.result.preflight) || dryRunResult.preflight) && h('div', null, h('strong', null, T_KEY(t, 'dryRun.preflight') + ': '), h('span', null, (((dryRunResult.result && dryRunResult.result.preflight) || dryRunResult.preflight).passed) ? '✓ Passed' : '✗ Failed (' + ((((dryRunResult.result && dryRunResult.result.preflight) || dryRunResult.preflight).reason) || '') + ')')),
4336
+ h('div', null, h('strong', null, T_KEY(t, 'dryRun.duration') + ': '), h('span', null, (((dryRunResult.result && dryRunResult.result.durationMs) !== undefined ? dryRunResult.result.durationMs : dryRunResult.durationMs) || 0) + 'ms')),
4337
+ h('div', { style: { marginTop: '6px' } }, h('strong', null, T_KEY(t, 'dryRun.output') + ':')),
4338
+ h('pre', {
4227
4339
  style: {
4228
4340
  background: 'var(--dsw-alias-bg-layer-2)',
4229
4341
  border: '1px solid var(--dsw-alias-border-l2)',
@@ -4238,8 +4350,8 @@ color: 'var(--dsw-alias-label-primary)'
4238
4350
  }
4239
4351
  }, ((dryRunResult.result && dryRunResult.result.output) !== undefined ? dryRunResult.result.output : (dryRunResult.output !== undefined ? dryRunResult.output : ((dryRunResult.result && dryRunResult.result.error) || dryRunResult.error || '(no output)'))))
4240
4352
  ),
4241
- React.createElement('div', { className: 'dsh-cron-modal-foot', style: { marginTop: '16px' } },
4242
- React.createElement('button', {
4353
+ h('div', { className: 'dsh-cron-modal-foot', style: { marginTop: '16px' } },
4354
+ h('button', {
4243
4355
  type: 'button',
4244
4356
  className: 'dsh-cron-btn-primary',
4245
4357
  onClick: () => setDryRunResult(null)
@@ -4247,29 +4359,29 @@ onClick: () => setDryRunResult(null)
4247
4359
  )
4248
4360
  )
4249
4361
  ),
4250
- archiveModalOpen && React.createElement('div', { className: 'dsh-cron-modal-overlay', onClick: () => setArchiveModalOpen(false) },
4251
- React.createElement('div', {
4362
+ archiveModalOpen && h('div', { className: 'dsh-cron-modal-overlay', onClick: () => setArchiveModalOpen(false) },
4363
+ h('div', {
4252
4364
  className: 'dsh-cron-modal',
4253
4365
  style: { maxWidth: '700px' },
4254
4366
  role: 'dialog',
4255
4367
  'aria-modal': 'true',
4256
4368
  onClick: (e) => e.stopPropagation()
4257
4369
  },
4258
- React.createElement('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center' } },
4259
- React.createElement('div', { className: 'dsh-cron-modal-title', style: { margin: 0 } }, T_KEY(t, 'archive.title') + (archiveTask ? ' - ' + archiveTask.title : '')),
4260
- React.createElement('button', {
4370
+ h('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center' } },
4371
+ h('div', { className: 'dsh-cron-modal-title', style: { margin: 0 } }, T_KEY(t, 'archive.title') + (archiveTask ? ' - ' + archiveTask.title : '')),
4372
+ h('button', {
4261
4373
  type: 'button',
4262
4374
  className: 'dsh-cron-icon-btn',
4263
4375
  onClick: () => setArchiveModalOpen(false)
4264
4376
  }, '✕')
4265
4377
  ),
4266
- React.createElement('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #999)', margin: '4px 0 12px 0' } },
4378
+ h('div', { style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #999)', margin: '4px 0 12px 0' } },
4267
4379
  T_KEY(t, 'archive.totalRuns', { total: archiveTotal })
4268
4380
  ),
4269
- archiveLoading ? React.createElement('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'history.loading')) :
4270
- archiveRuns.length === 0 ? React.createElement('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'archive.empty')) :
4271
- React.createElement('div', { style: { display: 'flex', flexDirection: 'column', gap: '8px', maxHeight: '380px', overflowY: 'auto' } },
4272
- archiveRuns.map((r, idx) => React.createElement('div', {
4381
+ archiveLoading ? h('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'history.loading')) :
4382
+ archiveRuns.length === 0 ? h('div', { className: 'dsh-cron-history-empty' }, T_KEY(t, 'archive.empty')) :
4383
+ h('div', { style: { display: 'flex', flexDirection: 'column', gap: '8px', maxHeight: '380px', overflowY: 'auto' } },
4384
+ archiveRuns.map((r, idx) => h('div', {
4273
4385
  key: idx,
4274
4386
  style: {
4275
4387
  background: 'var(--dsw-alias-bg-layer-2)',
@@ -4279,21 +4391,21 @@ padding: '8px 12px',
4279
4391
  fontSize: '12px'
4280
4392
  }
4281
4393
  },
4282
- React.createElement('div', { style: { display: 'flex', justifyContent: 'space-between', marginBottom: '4px' } },
4283
- React.createElement('span', { style: { fontWeight: '600', color: r.status === 'success' ? 'var(--dsh-cron-success)' : 'var(--dsh-cron-danger)' } }, (r.status || 'unknown').toUpperCase()),
4284
- React.createElement('span', { style: { color: 'var(--dsw-alias-label-secondary, #888)' } }, (r.at || r.timestamp || r.startedAt) ? new Date(r.at || r.timestamp || r.startedAt).toLocaleString() : "")
4394
+ h('div', { style: { display: 'flex', justifyContent: 'space-between', marginBottom: '4px' } },
4395
+ h('span', { style: { fontWeight: '600', color: r.status === 'success' ? 'var(--dsh-cron-success)' : 'var(--dsh-cron-danger)' } }, (r.status || 'unknown').toUpperCase()),
4396
+ h('span', { style: { color: 'var(--dsw-alias-label-secondary, #888)' } }, (r.at || r.timestamp || r.startedAt) ? new Date(r.at || r.timestamp || r.startedAt).toLocaleString() : "")
4285
4397
  ),
4286
- r.durationMs > 0 && React.createElement('div', { style: { color: 'var(--dsw-alias-label-secondary, #888)', marginBottom: '4px' } }, 'Duration: ' + r.durationMs + 'ms'),
4287
- r.chainRunId && React.createElement('div', { style: { marginBottom: '4px' } },
4288
- React.createElement('button', {
4398
+ r.durationMs > 0 && h('div', { style: { color: 'var(--dsw-alias-label-secondary, #888)', marginBottom: '4px' } }, 'Duration: ' + r.durationMs + 'ms'),
4399
+ r.chainRunId && h('div', { style: { marginBottom: '4px' } },
4400
+ h('button', {
4289
4401
  type: 'button',
4290
4402
  className: 'dsh-cron-btn-secondary',
4291
4403
  style: { padding: '2px 8px', fontSize: '11px', display: 'inline-flex', alignItems: 'center', gap: '4px' },
4292
4404
  onClick: () => openChainGraphModal(null, r.chainRunId)
4293
4405
  }, '🕸️ ' + T_KEY(t, 'chainGraph.viewGraph'))
4294
4406
  ),
4295
- r.error && React.createElement('div', { style: { color: 'var(--dsh-cron-danger)', marginBottom: '4px' } }, 'Error: ' + r.error),
4296
- r.output && React.createElement('div', {
4407
+ r.error && h('div', { style: { color: 'var(--dsh-cron-danger)', marginBottom: '4px' } }, 'Error: ' + r.error),
4408
+ r.output && h('div', {
4297
4409
  style: {
4298
4410
  color: 'var(--dsw-alias-label-primary, #ccc)',
4299
4411
  whiteSpace: 'pre-wrap',
@@ -4304,16 +4416,16 @@ overflowY: 'auto'
4304
4416
  }, r.output.slice(0, 300) + (r.output.length > 300 ? '...' : ''))
4305
4417
  ))
4306
4418
  ),
4307
- React.createElement('div', { className: 'dsh-cron-modal-foot', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginTop: '16px' } },
4308
- archiveRuns.length < archiveTotal ? React.createElement('button', {
4419
+ h('div', { className: 'dsh-cron-modal-foot', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginTop: '16px' } },
4420
+ archiveRuns.length < archiveTotal ? h('button', {
4309
4421
  type: 'button',
4310
4422
  className: 'dsh-cron-btn-secondary',
4311
4423
  onClick: () => {
4312
4424
  const nextOffset = archiveRuns.length;
4313
4425
  if (archiveTask) openArchiveModal(archiveTask, nextOffset);
4314
4426
  }
4315
- }, T_KEY(t, 'archive.loadMore', { shown: archiveRuns.length, total: archiveTotal })) : React.createElement('div', null),
4316
- React.createElement('button', {
4427
+ }, T_KEY(t, 'archive.loadMore', { shown: archiveRuns.length, total: archiveTotal })) : h('div', null),
4428
+ h('button', {
4317
4429
  type: 'button',
4318
4430
  className: 'dsh-cron-btn-primary',
4319
4431
  onClick: () => setArchiveModalOpen(false)
@@ -4321,54 +4433,54 @@ onClick: () => setArchiveModalOpen(false)
4321
4433
  )
4322
4434
  )
4323
4435
  ),
4324
- settingsModalOpen && React.createElement('div', { className: 'dsh-cron-modal-overlay', onClick: () => setSettingsModalOpen(false) },
4325
- React.createElement('div', { className: 'dsh-cron-modal dsh-cron-modal-scroll', role: 'dialog', 'aria-modal': 'true', onClick: (e) => e.stopPropagation() },
4326
- React.createElement('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '18px' } },
4327
- React.createElement('div', { className: 'dsh-cron-modal-title', style: { margin: 0, display: 'flex', alignItems: 'center', gap: '8px' } },
4328
- React.createElement('span', { style: { display: 'flex', alignItems: 'center', color: 'var(--dsh-cron-info)' }, ...iconHtml(ICON_TELEGRAM) }),
4436
+ settingsModalOpen && h('div', { className: 'dsh-cron-modal-overlay', onClick: () => setSettingsModalOpen(false) },
4437
+ h('div', { className: 'dsh-cron-modal dsh-cron-modal-scroll', role: 'dialog', 'aria-modal': 'true', onClick: (e) => e.stopPropagation() },
4438
+ h('div', { className: 'dsh-cron-modal-head', style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '18px' } },
4439
+ h('div', { className: 'dsh-cron-modal-title', style: { margin: 0, display: 'flex', alignItems: 'center', gap: '8px' } },
4440
+ h('span', { style: { display: 'flex', alignItems: 'center', color: 'var(--dsh-cron-info)' }, ...iconHtml(ICON_TELEGRAM) }),
4329
4441
  T_KEY(t, 'settings.modalTitle')
4330
4442
  ),
4331
- React.createElement('button', {
4443
+ h('button', {
4332
4444
  type: 'button',
4333
4445
  style: { background: 'none', border: 'none', color: 'var(--dsw-alias-label-tertiary, #888)', cursor: 'pointer', fontSize: '18px' },
4334
4446
  onClick: () => setSettingsModalOpen(false)
4335
4447
  }, '✕')
4336
4448
  ),
4337
- React.createElement('form', { onSubmit: handleSaveSettings },
4338
- React.createElement('div', { className: 'dsh-cron-form-group' },
4339
- React.createElement('label', null, T_KEY(t, 'settings.tokenLabel')),
4340
- React.createElement('input', {
4449
+ h('form', { onSubmit: handleSaveSettings },
4450
+ h('div', { className: 'dsh-cron-form-group' },
4451
+ h('label', null, T_KEY(t, 'settings.tokenLabel')),
4452
+ h('input', {
4341
4453
  type: 'password',
4342
4454
  value: settingsBotToken,
4343
4455
  placeholder: settingsHasDefault ? T_KEY(t, 'settings.tokenPlaceholderDefault') : T_KEY(t, 'settings.tokenPlaceholder'),
4344
4456
  onChange: (e) => setSettingsBotToken(e.target.value)
4345
4457
  }),
4346
- settingsHasDefault && React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'settings.defaultHint'))
4458
+ settingsHasDefault && h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'settings.defaultHint'))
4347
4459
  ),
4348
- React.createElement('div', { className: 'dsh-cron-form-group' },
4349
- React.createElement('label', null, T_KEY(t, 'settings.chatIdLabel')),
4350
- React.createElement('input', {
4460
+ h('div', { className: 'dsh-cron-form-group' },
4461
+ h('label', null, T_KEY(t, 'settings.chatIdLabel')),
4462
+ h('input', {
4351
4463
  value: settingsChatId,
4352
4464
  placeholder: T_KEY(t, 'settings.chatIdPlaceholder'),
4353
4465
  onChange: (e) => setSettingsChatId(e.target.value)
4354
4466
  })
4355
4467
  ),
4356
- React.createElement('div', { style: { background: 'var(--dsw-alias-bg-layer-3, color-mix(in srgb, var(--dsw-alias-label-primary) 2%, transparent))', border: '1px solid var(--dsw-alias-border-l2)', borderRadius: '8px', padding: '12px 14px', marginBottom: '16px' } },
4357
- React.createElement('label', { className: 'dsh-cron-checkbox-row', style: { marginBottom: '8px' } },
4358
- React.createElement('input', {
4468
+ h('div', { style: { background: 'var(--dsw-alias-bg-layer-3, color-mix(in srgb, var(--dsw-alias-label-primary) 2%, transparent))', border: '1px solid var(--dsw-alias-border-l2)', borderRadius: '8px', padding: '12px 14px', marginBottom: '16px' } },
4469
+ h('label', { className: 'dsh-cron-checkbox-row', style: { marginBottom: '8px' } },
4470
+ h('input', {
4359
4471
  type: 'checkbox',
4360
4472
  checked: settingsNotifyGlobal,
4361
4473
  onChange: (e) => setSettingsNotifyGlobal(e.target.checked)
4362
4474
  }),
4363
- React.createElement('span', null, T_KEY(t, 'settings.globalNotify'))
4475
+ h('span', null, T_KEY(t, 'settings.globalNotify'))
4364
4476
  ),
4365
- React.createElement('label', { className: 'dsh-cron-checkbox-row' },
4366
- React.createElement('input', {
4477
+ h('label', { className: 'dsh-cron-checkbox-row' },
4478
+ h('input', {
4367
4479
  type: 'checkbox',
4368
4480
  checked: settingsOnlyOnFailureGlobal,
4369
4481
  onChange: (e) => setSettingsOnlyOnFailureGlobal(e.target.checked)
4370
4482
  }),
4371
- React.createElement('span', null, T_KEY(t, 'settings.globalOnlyFailure'))
4483
+ h('span', null, T_KEY(t, 'settings.globalOnlyFailure'))
4372
4484
  )
4373
4485
  ),
4374
4486
  ...renderDeliverySettings({
@@ -4379,8 +4491,8 @@ onChannelTemplate: updateChannelTemplate,
4379
4491
  sections: settingsSections,
4380
4492
  onToggleSection: toggleDeliverySection,
4381
4493
  }),
4382
- React.createElement('div', { style: { display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: '14px' } },
4383
- React.createElement('button', {
4494
+ h('div', { style: { display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: '14px' } },
4495
+ h('button', {
4384
4496
  type: 'button',
4385
4497
  className: 'dsh-cron-btn-secondary',
4386
4498
  style: { display: 'inline-flex', alignItems: 'center', gap: '6px' },
@@ -4388,17 +4500,17 @@ disabled: testStatus?.loading,
4388
4500
  onClick: handleTestTelegram
4389
4501
  }, testStatus?.loading ? T_KEY(t, 'settings.sending') : T_KEY(t, 'settings.testTelegram'))
4390
4502
  ),
4391
- testStatus && testStatus.message && React.createElement('div', {
4503
+ testStatus && testStatus.message && h('div', {
4392
4504
  className: 'dsh-cron-status-banner',
4393
4505
  'data-type': testStatus.success ? 'success' : 'error'
4394
4506
  }, testStatus.message),
4395
- React.createElement('div', { className: 'dsh-cron-modal-foot' },
4396
- React.createElement('button', {
4507
+ h('div', { className: 'dsh-cron-modal-foot' },
4508
+ h('button', {
4397
4509
  type: 'button',
4398
4510
  className: 'dsh-cron-btn-secondary',
4399
4511
  onClick: () => setSettingsModalOpen(false)
4400
4512
  }, T_KEY(t, 'modal.cancel')),
4401
- React.createElement('button', {
4513
+ h('button', {
4402
4514
  type: 'submit',
4403
4515
  className: 'dsh-cron-btn-primary'
4404
4516
  }, T_KEY(t, 'settings.save'))
@@ -4406,12 +4518,12 @@ className: 'dsh-cron-btn-primary'
4406
4518
  )
4407
4519
  )
4408
4520
  ),
4409
- importDoc && React.createElement('div', { className: 'dsh-cron-modal-overlay', onClick: () => !transferBusy && setImportDoc(null) },
4410
- React.createElement('div', { className: 'dsh-cron-modal', role: 'dialog', 'aria-modal': 'true', onClick: (e) => e.stopPropagation() },
4411
- React.createElement('div', { className: 'dsh-cron-modal-title' }, T_KEY(t, 'transfer.importTitleModal')),
4412
- React.createElement('div', { className: 'dsh-cron-hint', style: { marginBottom: '10px' } }, T_KEY(t, 'transfer.importHint')),
4413
- importSummary && React.createElement('div', null,
4414
- React.createElement('div', { style: { fontSize: '13px', marginBottom: '12px' } },
4521
+ importDoc && h('div', { className: 'dsh-cron-modal-overlay', onClick: () => !transferBusy && setImportDoc(null) },
4522
+ h('div', { className: 'dsh-cron-modal', role: 'dialog', 'aria-modal': 'true', onClick: (e) => e.stopPropagation() },
4523
+ h('div', { className: 'dsh-cron-modal-title' }, T_KEY(t, 'transfer.importTitleModal')),
4524
+ h('div', { className: 'dsh-cron-hint', style: { marginBottom: '10px' } }, T_KEY(t, 'transfer.importHint')),
4525
+ importSummary && h('div', null,
4526
+ h('div', { style: { fontSize: '13px', marginBottom: '12px' } },
4415
4527
  T_KEY(t, 'transfer.summary', {
4416
4528
  total: (importSummary.add || 0) + (importSummary.replace || 0) + (importSummary.skip || 0),
4417
4529
  add: importSummary.add || 0,
@@ -4419,26 +4531,26 @@ replace: importSummary.replace || 0,
4419
4531
  skip: importSummary.skip || 0
4420
4532
  })
4421
4533
  ),
4422
- React.createElement('div', { style: { display: 'flex', flexDirection: 'column', gap: '8px', marginBottom: '14px' } },
4423
- ...['add', 'replace', 'skip'].map((mode) => React.createElement('label', { key: mode, className: 'dsh-cron-checkbox-row' },
4424
- React.createElement('input', {
4534
+ h('div', { style: { display: 'flex', flexDirection: 'column', gap: '8px', marginBottom: '14px' } },
4535
+ ...['add', 'replace', 'skip'].map((mode) => h('label', { key: mode, className: 'dsh-cron-checkbox-row' },
4536
+ h('input', {
4425
4537
  type: 'radio',
4426
4538
  name: 'dsh-cron-import-strategy',
4427
4539
  checked: importStrategy === mode,
4428
4540
  onChange: () => setImportStrategy(mode)
4429
4541
  }),
4430
- React.createElement('span', null, T_KEY(t, mode === 'add' ? 'transfer.strategyAdd' : mode === 'replace' ? 'transfer.strategyReplace' : 'transfer.strategySkip'))
4542
+ h('span', null, T_KEY(t, mode === 'add' ? 'transfer.strategyAdd' : mode === 'replace' ? 'transfer.strategyReplace' : 'transfer.strategySkip'))
4431
4543
  ))
4432
4544
  )
4433
4545
  ),
4434
- React.createElement('div', { className: 'dsh-cron-modal-foot' },
4435
- React.createElement('button', {
4546
+ h('div', { className: 'dsh-cron-modal-foot' },
4547
+ h('button', {
4436
4548
  type: 'button',
4437
4549
  className: 'dsh-cron-btn-secondary',
4438
4550
  disabled: transferBusy,
4439
4551
  onClick: () => setImportDoc(null)
4440
4552
  }, T_KEY(t, 'modal.cancel')),
4441
- React.createElement('button', {
4553
+ h('button', {
4442
4554
  type: 'button',
4443
4555
  className: 'dsh-cron-btn-primary',
4444
4556
  disabled: transferBusy || !importSummary,
@@ -4447,13 +4559,13 @@ onClick: handleImportConfirm
4447
4559
  )
4448
4560
  )
4449
4561
  ),
4450
- dshModalOpen && React.createElement('div', { className: 'dsh-cron-modal-overlay', onClick: () => !dshLoading && setDshModalOpen(false) },
4451
- React.createElement('div', { className: 'dsh-cron-modal', role: 'dialog', 'aria-modal': 'true', onClick: (e) => e.stopPropagation() },
4452
- React.createElement('div', { className: 'dsh-cron-modal-title' }, T_KEY(t, 'dsh.modalTitle')),
4453
- React.createElement('div', { className: 'dsh-cron-form-group' },
4454
- React.createElement('label', null, T_KEY(t, 'dsh.descLabel')),
4455
- React.createElement('div', { className: 'dsh-cron-chat-box' },
4456
- React.createElement('textarea', {
4562
+ dshModalOpen && h('div', { className: 'dsh-cron-modal-overlay', onClick: () => !dshLoading && setDshModalOpen(false) },
4563
+ h('div', { className: 'dsh-cron-modal', role: 'dialog', 'aria-modal': 'true', onClick: (e) => e.stopPropagation() },
4564
+ h('div', { className: 'dsh-cron-modal-title' }, T_KEY(t, 'dsh.modalTitle')),
4565
+ h('div', { className: 'dsh-cron-form-group' },
4566
+ h('label', null, T_KEY(t, 'dsh.descLabel')),
4567
+ h('div', { className: 'dsh-cron-chat-box' },
4568
+ h('textarea', {
4457
4569
  className: 'dsh-cron-chat-input',
4458
4570
  rows: 4,
4459
4571
  autoFocus: true,
@@ -4468,22 +4580,22 @@ handleStartWithDSH();
4468
4580
  },
4469
4581
  onChange: (e) => setDshPrompt(e.target.value)
4470
4582
  }),
4471
- React.createElement('div', { className: 'dsh-cron-chat-foot' },
4472
- React.createElement('span', { className: 'dsh-cron-chat-hint' }, T_KEY(t, 'dsh.sendHint')),
4473
- React.createElement('button', {
4583
+ h('div', { className: 'dsh-cron-chat-foot' },
4584
+ h('span', { className: 'dsh-cron-chat-hint' }, T_KEY(t, 'dsh.sendHint')),
4585
+ h('button', {
4474
4586
  type: 'button',
4475
4587
  className: 'dsh-cron-send-btn',
4476
4588
  disabled: dshLoading || !dshPrompt.trim(),
4477
4589
  title: T_KEY(t, 'dsh.sendTitle'),
4478
4590
  onClick: handleStartWithDSH
4479
4591
  },
4480
- React.createElement('span', svgProps(ICON_SEND))
4592
+ h('span', svgProps(ICON_SEND))
4481
4593
  )
4482
4594
  )
4483
4595
  )
4484
4596
  ),
4485
- React.createElement('div', { className: 'dsh-cron-modal-foot' },
4486
- React.createElement('button', {
4597
+ h('div', { className: 'dsh-cron-modal-foot' },
4598
+ h('button', {
4487
4599
  type: 'button',
4488
4600
  className: 'dsh-cron-btn-secondary',
4489
4601
  disabled: dshLoading,
@@ -4694,15 +4806,15 @@ setTestInfo({ success: false, message: T_KEY(t, 'settings.kanbanFail', { error:
4694
4806
  }
4695
4807
  };
4696
4808
  if (loadState !== 'ready') {
4697
- return React.createElement('div', { className: 'dsh-cron-card' },
4698
- React.createElement('div', { className: 'dsh-cron-card-title' }, T_KEY(t, 'settings.cardTitle')),
4699
- React.createElement('div', {
4809
+ return h('div', { className: 'dsh-cron-card' },
4810
+ h('div', { className: 'dsh-cron-card-title' }, T_KEY(t, 'settings.cardTitle')),
4811
+ h('div', {
4700
4812
  className: 'dsh-cron-status-banner',
4701
4813
  'data-type': loadState === 'error' ? 'error' : 'info',
4702
4814
  style: { marginTop: '10px', display: 'flex', justifyContent: 'space-between', alignItems: 'center', gap: '10px' }
4703
4815
  },
4704
- React.createElement('span', null, loadState === 'error' ? T_KEY(t, 'settings.unavailable') : T_KEY(t, 'settings.loading')),
4705
- loadState === 'error' && React.createElement('button', {
4816
+ h('span', null, loadState === 'error' ? T_KEY(t, 'settings.unavailable') : T_KEY(t, 'settings.loading')),
4817
+ loadState === 'error' && h('button', {
4706
4818
  type: 'button',
4707
4819
  className: 'dsh-cron-btn-secondary',
4708
4820
  onClick: () => setReloadTick(x => x + 1)
@@ -4711,88 +4823,88 @@ onClick: () => setReloadTick(x => x + 1)
4711
4823
  );
4712
4824
  }
4713
4825
  if (props && props.view === 'summary') {
4714
- return React.createElement('span', { className: 'dsh-cron-card-desc' }, T_KEY(t, 'settings.cardDesc'));
4826
+ return h('span', { className: 'dsh-cron-card-desc' }, T_KEY(t, 'settings.cardDesc'));
4715
4827
  }
4716
4828
  const page = !!(props && props.view === 'page');
4717
- return React.createElement('div', { className: page ? 'dsh-cron-page' : 'dsh-cron-card' },
4718
- React.createElement('button', {
4829
+ return h('div', { className: page ? 'dsh-cron-page' : 'dsh-cron-card' },
4830
+ h('button', {
4719
4831
  type: 'button',
4720
4832
  className: 'dsh-cron-card-head-btn',
4721
4833
  style: page ? { display: 'none' } : undefined,
4722
4834
  'aria-expanded': (page || cardOpen) ? 'true' : 'false',
4723
4835
  onClick: () => setCardOpen(!cardOpen)
4724
4836
  },
4725
- React.createElement('span', { className: 'dsh-cron-card-title' }, T_KEY(t, 'settings.cardTitle')),
4726
- React.createElement('span', { className: 'dsh-cron-chev' + (cardOpen ? ' dsh-cron-chev-open' : '') }, chevronNode())
4837
+ h('span', { className: 'dsh-cron-card-title' }, T_KEY(t, 'settings.cardTitle')),
4838
+ h('span', { className: 'dsh-cron-chev' + (cardOpen ? ' dsh-cron-chev-open' : '') }, chevronNode())
4727
4839
  ),
4728
- (page || cardOpen) && React.createElement('div', { className: 'dsh-cron-card-body' },
4729
- React.createElement('div', { className: 'dsh-cron-card-desc' }, T_KEY(t, 'settings.cardDesc')),
4730
- React.createElement('div', { style: { display: 'flex', justifyContent: 'flex-end', marginBottom: '12px' } },
4731
- React.createElement('button', {
4840
+ (page || cardOpen) && h('div', { className: 'dsh-cron-card-body' },
4841
+ h('div', { className: 'dsh-cron-card-desc' }, T_KEY(t, 'settings.cardDesc')),
4842
+ h('div', { style: { display: 'flex', justifyContent: 'flex-end', marginBottom: '12px' } },
4843
+ h('button', {
4732
4844
  type: 'button',
4733
4845
  className: 'dsh-cron-btn-primary',
4734
4846
  onClick: () => { if (toggle) toggle.set(true); }
4735
4847
  }, T_KEY(t, 'settings.openPanel'))
4736
4848
  ),
4737
- React.createElement('form', { onSubmit: saveSettings, style: { display: 'flex', flexDirection: 'column', gap: '12px' } },
4738
- React.createElement('div', { className: 'dsh-cron-form-group', style: { marginBottom: 0 } },
4739
- React.createElement('label', null, T_KEY(t, 'settings.tokenLabel')),
4740
- React.createElement('input', {
4849
+ h('form', { onSubmit: saveSettings, style: { display: 'flex', flexDirection: 'column', gap: '12px' } },
4850
+ h('div', { className: 'dsh-cron-form-group', style: { marginBottom: 0 } },
4851
+ h('label', null, T_KEY(t, 'settings.tokenLabel')),
4852
+ h('input', {
4741
4853
  type: 'password',
4742
4854
  value: token,
4743
4855
  placeholder: hasDefault ? T_KEY(t, 'settings.tokenPlaceholderDefault') : T_KEY(t, 'settings.tokenPlaceholder'),
4744
4856
  onChange: (e) => setToken(e.target.value)
4745
4857
  }),
4746
- hasDefault && React.createElement('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'settings.defaultHint'))
4858
+ hasDefault && h('div', { className: 'dsh-cron-hint' }, T_KEY(t, 'settings.defaultHint'))
4747
4859
  ),
4748
- React.createElement('div', { className: 'dsh-cron-form-group', style: { marginBottom: 0 } },
4749
- React.createElement('label', null, T_KEY(t, 'settings.chatIdLabel')),
4750
- React.createElement('input', {
4860
+ h('div', { className: 'dsh-cron-form-group', style: { marginBottom: 0 } },
4861
+ h('label', null, T_KEY(t, 'settings.chatIdLabel')),
4862
+ h('input', {
4751
4863
  value: chatId,
4752
4864
  placeholder: T_KEY(t, 'settings.chatIdPlaceholder'),
4753
4865
  onChange: (e) => setChatId(e.target.value)
4754
4866
  })
4755
4867
  ),
4756
- React.createElement('div', { className: 'dsh-cron-form-group', style: { marginBottom: 0 } },
4757
- React.createElement('label', null, T_KEY(t, 'settings.kanbanUrlLabel')),
4758
- React.createElement('input', {
4868
+ h('div', { className: 'dsh-cron-form-group', style: { marginBottom: 0 } },
4869
+ h('label', null, T_KEY(t, 'settings.kanbanUrlLabel')),
4870
+ h('input', {
4759
4871
  value: kanbanUrl,
4760
4872
  placeholder: 'http://127.0.0.1:3000',
4761
4873
  onChange: (e) => setKanbanUrl(e.target.value)
4762
4874
  })
4763
4875
  ),
4764
- React.createElement('div', { style: { background: 'var(--dsw-alias-bg-layer-3, color-mix(in srgb, var(--dsw-alias-label-primary) 2%, transparent))', border: '1px solid var(--dsw-alias-border-l2)', borderRadius: '6px', padding: '10px 12px', display: 'flex', flexDirection: 'column', gap: '8px' } },
4765
- React.createElement('label', { className: 'dsh-cron-checkbox-row' },
4766
- React.createElement('input', {
4876
+ h('div', { style: { background: 'var(--dsw-alias-bg-layer-3, color-mix(in srgb, var(--dsw-alias-label-primary) 2%, transparent))', border: '1px solid var(--dsw-alias-border-l2)', borderRadius: '6px', padding: '10px 12px', display: 'flex', flexDirection: 'column', gap: '8px' } },
4877
+ h('label', { className: 'dsh-cron-checkbox-row' },
4878
+ h('input', {
4767
4879
  type: 'checkbox',
4768
4880
  checked: notify,
4769
4881
  onChange: (e) => setNotify(e.target.checked)
4770
4882
  }),
4771
- React.createElement('span', null, T_KEY(t, 'settings.globalNotify'))
4883
+ h('span', null, T_KEY(t, 'settings.globalNotify'))
4772
4884
  ),
4773
- React.createElement('label', { className: 'dsh-cron-checkbox-row' },
4774
- React.createElement('input', {
4885
+ h('label', { className: 'dsh-cron-checkbox-row' },
4886
+ h('input', {
4775
4887
  type: 'checkbox',
4776
4888
  checked: onlyFailure,
4777
4889
  onChange: (e) => setOnlyFailure(e.target.checked)
4778
4890
  }),
4779
- React.createElement('span', null, T_KEY(t, 'settings.globalOnlyFailure'))
4891
+ h('span', null, T_KEY(t, 'settings.globalOnlyFailure'))
4780
4892
  ),
4781
- React.createElement('label', { className: 'dsh-cron-checkbox-row' },
4782
- React.createElement('input', {
4893
+ h('label', { className: 'dsh-cron-checkbox-row' },
4894
+ h('input', {
4783
4895
  type: 'checkbox',
4784
4896
  checked: llmActionsEnabled,
4785
4897
  onChange: (e) => setLlmActionsEnabled(e.target.checked)
4786
4898
  }),
4787
- React.createElement('span', null, 'Enable Structured LLM Actions (trigger tasks, notify, create issues)')
4899
+ h('span', null, 'Enable Structured LLM Actions (trigger tasks, notify, create issues)')
4788
4900
  ),
4789
- React.createElement('label', { className: 'dsh-cron-checkbox-row' },
4790
- React.createElement('input', {
4901
+ h('label', { className: 'dsh-cron-checkbox-row' },
4902
+ h('input', {
4791
4903
  type: 'checkbox',
4792
4904
  checked: enableDynamicCredentials,
4793
4905
  onChange: (e) => setEnableDynamicCredentials(e.target.checked)
4794
4906
  }),
4795
- React.createElement('span', null, T_KEY(t, 'settings.dynamicCredentials'))
4907
+ h('span', null, T_KEY(t, 'settings.dynamicCredentials'))
4796
4908
  )
4797
4909
  ),
4798
4910
  ...renderDeliverySettings({
@@ -4813,12 +4925,12 @@ return Object.assign({}, prev, { channelTemplates: templates });
4813
4925
  sections,
4814
4926
  onToggleSection: (key) => setSections((prev) => Object.assign({}, prev, { [key]: !prev[key] })),
4815
4927
  }),
4816
- testInfo && testInfo.message && React.createElement('div', {
4928
+ testInfo && testInfo.message && h('div', {
4817
4929
  className: 'dsh-cron-status-banner',
4818
4930
  'data-type': testInfo.success ? 'success' : 'error',
4819
4931
  style: { margin: 0, padding: '8px 12px' }
4820
4932
  }, testInfo.message),
4821
- React.createElement('div', {
4933
+ h('div', {
4822
4934
  className: 'dsh-cron-form-group',
4823
4935
  style: {
4824
4936
  background: 'var(--dsw-alias-bg-layer-2, color-mix(in srgb, var(--dsw-alias-label-primary) 3%, transparent))',
@@ -4828,19 +4940,19 @@ padding: '14px',
4828
4940
  marginBottom: '16px'
4829
4941
  }
4830
4942
  },
4831
- React.createElement('div', {
4943
+ h('div', {
4832
4944
  style: { display: 'flex', justifyContent: 'space-between', alignItems: 'center', marginBottom: '8px' }
4833
4945
  },
4834
- React.createElement('div', { style: { fontWeight: '600', fontSize: '14px' } }, `🚀 ${T_KEY(t, 'updater.title')}`),
4835
- React.createElement('div', { style: { display: 'flex', gap: '8px' } },
4836
- React.createElement('button', {
4946
+ h('div', { style: { fontWeight: '600', fontSize: '14px' } }, `🚀 ${T_KEY(t, 'updater.title')}`),
4947
+ h('div', { style: { display: 'flex', gap: '8px' } },
4948
+ h('button', {
4837
4949
  type: 'button',
4838
4950
  className: 'dsh-cron-btn-secondary',
4839
4951
  style: { padding: '4px 10px', fontSize: '12px' },
4840
4952
  disabled: updateState.checking || updateState.updating,
4841
4953
  onClick: checkUpdates
4842
4954
  }, updateState.checking ? T_KEY(t, 'updater.checking') : T_KEY(t, 'updater.btnCheck')),
4843
- updateState.updateAvailable ? React.createElement('button', {
4955
+ updateState.updateAvailable ? h('button', {
4844
4956
  type: 'button',
4845
4957
  className: 'dsh-cron-btn-primary',
4846
4958
  style: { padding: '4px 10px', fontSize: '12px' },
@@ -4849,39 +4961,39 @@ onClick: runUpdate
4849
4961
  }, updateState.updating ? T_KEY(t, 'updater.updating') : T_KEY(t, 'updater.btnUpdate', { version: updateState.latestVersion })) : null
4850
4962
  )
4851
4963
  ),
4852
- React.createElement('div', {
4964
+ h('div', {
4853
4965
  style: { fontSize: '12px', color: 'var(--dsw-alias-label-secondary, #999)', marginBottom: '8px' }
4854
4966
  }, T_KEY(t, 'updater.desc')),
4855
- React.createElement('div', {
4967
+ h('div', {
4856
4968
  style: { display: 'flex', alignItems: 'center', gap: '12px', fontSize: '13px' }
4857
4969
  },
4858
- React.createElement('span', { style: { color: 'var(--dsw-alias-label-secondary, #aaa)' } },
4970
+ h('span', { style: { color: 'var(--dsw-alias-label-secondary, #aaa)' } },
4859
4971
  updateState.currentVersion ? T_KEY(t, 'updater.current', { version: updateState.currentVersion }) : ''
4860
4972
  ),
4861
- updateState.checking ? React.createElement('span', { className: 'dsh-cron-badge dsh-cron-badge-info' }, T_KEY(t, 'updater.checking')) :
4862
- updateState.updateAvailable ? React.createElement('span', { className: 'dsh-cron-badge dsh-cron-badge-warn' }, T_KEY(t, 'updater.available', { version: updateState.latestVersion })) :
4863
- updateState.currentVersion && !updateState.error && !updateState.checking ? React.createElement('span', { className: 'dsh-cron-badge dsh-cron-badge-ok' }, `✓ ${T_KEY(t, 'updater.upToDate')}`) : null
4973
+ updateState.checking ? h('span', { className: 'dsh-cron-badge dsh-cron-badge-info' }, T_KEY(t, 'updater.checking')) :
4974
+ updateState.updateAvailable ? h('span', { className: 'dsh-cron-badge dsh-cron-badge-warn' }, T_KEY(t, 'updater.available', { version: updateState.latestVersion })) :
4975
+ updateState.currentVersion && !updateState.error && !updateState.checking ? h('span', { className: 'dsh-cron-badge dsh-cron-badge-ok' }, `✓ ${T_KEY(t, 'updater.upToDate')}`) : null
4864
4976
  ),
4865
- updateState.notice ? React.createElement('div', {
4977
+ updateState.notice ? h('div', {
4866
4978
  style: { marginTop: '8px', color: 'var(--dsw-alias-success)', fontSize: '12px' }
4867
4979
  }, updateState.notice) : null,
4868
- updateState.error ? React.createElement('div', {
4980
+ updateState.error ? h('div', {
4869
4981
  style: { marginTop: '8px', color: 'var(--dsw-alias-error)', fontSize: '12px' }
4870
4982
  }, updateState.error) : null
4871
4983
  ),
4872
- React.createElement('div', { style: { display: 'flex', gap: '8px', alignItems: 'center', flexWrap: 'wrap', marginTop: '4px' } },
4873
- React.createElement('button', {
4984
+ h('div', { style: { display: 'flex', gap: '8px', alignItems: 'center', flexWrap: 'wrap', marginTop: '4px' } },
4985
+ h('button', {
4874
4986
  type: 'submit',
4875
4987
  className: 'dsh-cron-btn-primary',
4876
4988
  style: { minWidth: '140px' }
4877
4989
  }, saved ? T_KEY(t, 'settings.saved') : T_KEY(t, 'settings.save')),
4878
- React.createElement('button', {
4990
+ h('button', {
4879
4991
  type: 'button',
4880
4992
  className: 'dsh-cron-btn-secondary',
4881
4993
  onClick: testTelegram,
4882
4994
  disabled: testInfo?.loading
4883
4995
  }, T_KEY(t, 'settings.testTelegram')),
4884
- React.createElement('button', {
4996
+ h('button', {
4885
4997
  type: 'button',
4886
4998
  className: 'dsh-cron-btn-secondary',
4887
4999
  onClick: testKanban,
@@ -5106,9 +5218,9 @@ container.setAttribute('data-dsh-plugin', 'dsh-cron');
5106
5218
  column.appendChild(container);
5107
5219
  if (ReactDOM && typeof ReactDOM.createRoot === 'function') {
5108
5220
  root = ReactDOM.createRoot(container);
5109
- root.render(React.createElement(ErrorBoundary, null, React.createElement(CronScreen, { ctx, toggle, onClose: () => toggle.set(false), t: translate })));
5221
+ root.render(h(ErrorBoundary, null, h(CronScreen, { ctx, toggle, onClose: () => toggle.set(false), t: translate })));
5110
5222
  } else if (ReactDOM && typeof ReactDOM.render === 'function') {
5111
- ReactDOM.render(React.createElement(CronScreen, { ctx, toggle, onClose: () => toggle.set(false), t: translate }), container);
5223
+ ReactDOM.render(h(CronScreen, { ctx, toggle, onClose: () => toggle.set(false), t: translate }), container);
5112
5224
  }
5113
5225
  };
5114
5226
  const applyActive = () => {
@@ -5176,7 +5288,7 @@ translate = ctx.locale.bind(NS);
5176
5288
  }
5177
5289
  const toggle = createToggle();
5178
5290
  function SettingsCardWithBoundary(props) {
5179
- return React.createElement(ErrorBoundary, null, CronSettingsCard(props));
5291
+ return h(ErrorBoundary, null, CronSettingsCard(props));
5180
5292
  }
5181
5293
  const itemOk = registerIntoMount(ctx, 'plugins.item', {
5182
5294
  name: 'plugins.item',
@@ -5215,7 +5327,7 @@ const cardSlot = cardOk ? 'settings.plugin.item' : undefined;
5215
5327
  const chipSlot = chipOk ? 'conversation.session.header.utilities' : undefined;
5216
5328
  function CronChip(props) {
5217
5329
  const chipT = props.t || translate;
5218
- return React.createElement('button', {
5330
+ return h('button', {
5219
5331
  type: 'button',
5220
5332
  style: { background: 'none', border: 'none', color: 'var(--dsw-alias-label-secondary, #999)', cursor: 'pointer', padding: '4px', display: 'inline-flex', alignItems: 'center' },
5221
5333
  title: T_KEY(chipT, 'chip.title'),