1+ <script >
2+ import { createEventDispatcher } from ' svelte' ;
3+ import { Input } from ' @sveltestrap/sveltestrap' ;
4+ import Markdown from ' $lib/common/markdown/Markdown.svelte' ;
5+ import CodeScript from ' $lib/common/shared/CodeScript.svelte' ;
6+ import BotsharpTooltip from ' $lib/common/tooltip/BotsharpTooltip.svelte' ;
7+ import { ADMIN_ROLES } from ' $lib/helpers/constants' ;
8+
9+ const svelteDispatch = createEventDispatcher ();
10+
11+ const textLimit = 1024 ;
12+
13+ /** @type {import('$agentTypes').AgentRule} */
14+ export let rule;
15+
16+ /** @type {number} */
17+ export let ruleIndex;
18+
19+ /** @type {boolean} */
20+ export let collapsed = true ;
21+
22+ /** @type {import('$userTypes').UserModel} */
23+ export let user;
24+
25+ /** @type {any[]} */
26+ export let ruleOptions = [];
27+
28+ /** @type {any[]} */
29+ export let criteriaOptions = [];
30+
31+ /** @type {any[]} */
32+ export let actionOptions = [];
33+
34+ /** @type {number} */
35+ export let windowWidth;
36+
37+
38+
39+ /**
40+ * @param {any} e
41+ * @param {string} field
42+ */
43+ function toggleRule (e , field ) {
44+ svelteDispatch (' toggle' , {
45+ ruleIdx: ruleIndex,
46+ field: field,
47+ checked: e .target .checked
48+ });
49+ }
50+
51+ /**
52+ * @param {any} e
53+ * @param {string} field
54+ */
55+ function changeRule (e , field ) {
56+ svelteDispatch (' changeOption' , {
57+ ruleIdx: ruleIndex,
58+ field: field,
59+ value: e .target .value
60+ });
61+ }
62+
63+ function deleteRule () {
64+ svelteDispatch (' delete' , {
65+ ruleIdx: ruleIndex
66+ });
67+ }
68+
69+ /**
70+ * @param {any} e
71+ * @param {string} field
72+ */
73+ function changeContent (e , field ) {
74+ svelteDispatch (' changeContent' , {
75+ ruleIdx: ruleIndex,
76+ field: field,
77+ value: e? .target ? .value || e? .detail ? .text || ' '
78+ });
79+ }
80+
81+
82+ function toggleCollapse () {
83+ svelteDispatch (' collapse' , {
84+ ruleIdx: ruleIndex,
85+ collapsed: collapsed
86+ });
87+ }
88+
89+ function compileCodeScript () {
90+ svelteDispatch (' compile' , {
91+ rule: rule
92+ });
93+ }
94+ < / script>
95+
96+ < div class = " utility-wrapper" >
97+ < div class = " utility-row utility-row-primary" >
98+ < div class = " utility-label fw-bold" >
99+ < div class = " line-align-center" >
100+ < i
101+ class = " bx clickable fs-6 collapse-toggle {collapsed ? 'bx-chevron-right' : 'bx-chevron-down'}"
102+ role= " button"
103+ tabindex= " 0"
104+ on: keydown= {() => {}}
105+ on: click= {() => toggleCollapse ()}
106+ / >
107+ < / div>
108+ < div class = " line-align-center" >
109+ {` Rule #${ ruleIndex + 1 } ` }
110+ < / div>
111+ < div class = " utility-tooltip" >
112+ < div class = " line-align-center" >
113+ < Input
114+ type= " checkbox"
115+ checked= {! rule .disabled }
116+ on: change= {e => toggleRule (e, ' rule' )}
117+ / >
118+ < / div>
119+ {#if rule .statement }
120+ < div class = " line-align-center" >
121+ < i
122+ class = " bx bx-info-circle text-primary fs-6"
123+ style= " padding-top: 2px;"
124+ id= {` rule-statement-${ ruleIndex} ` }
125+ data- bs- toggle= " tooltip"
126+ data- bs- placement= " top"
127+ title= " Rule arguments"
128+ / >
129+ < BotsharpTooltip
130+ containerClasses= " agent-utility-desc"
131+ style= {` min-width: ${ Math .floor (windowWidth* 0.3 )} px;` }
132+ target= {` rule-statement-${ ruleIndex} ` }
133+ placement= " top"
134+ persist
135+ >
136+ < Markdown
137+ rawText
138+ scrollable
139+ containerClasses= {' markdown-div' }
140+ containerStyles= {` max-width: ${ Math .floor (windowWidth* 0.3 )} px;` }
141+ text= {rule .statement }
142+ / >
143+ < / BotsharpTooltip>
144+ < / div>
145+ {/ if }
146+ < / div>
147+ < / div>
148+ < div class = " utility-value" >
149+ < div class = " utility-input line-align-center" >
150+ < Input
151+ type= " select"
152+ disabled= {rule .disabled }
153+ on: change= {e => changeRule (e, ' rule' )}
154+ >
155+ {#each [... ruleOptions] as option}
156+ < option value= {option .name } selected= {option .name == rule .trigger_name }>
157+ {option .displayName || option .name }
158+ < / option>
159+ {/ each}
160+ < / Input>
161+ < / div>
162+ < div class = " utility-delete line-align-center" >
163+ < i
164+ class = " bx bxs-no-entry text-danger clickable fs-6"
165+ role= " link"
166+ tabindex= " 0"
167+ on: keydown= {() => {}}
168+ on: click= {() => deleteRule ()}
169+ / >
170+ < / div>
171+ < / div>
172+ < / div>
173+
174+ {#if ! collapsed}
175+ < div class = " utility-row utility-row-secondary" >
176+ < div class = " utility-content" >
177+ < div class = " utility-list-item" >
178+ < div class = " utility-label line-align-center" >
179+ < div class = " d-flex gap-1" >
180+ < div class = " line-align-center" >
181+ {' Criteria' }
182+ < / div>
183+ < div class = " line-align-center" >
184+ < Input
185+ type= " checkbox"
186+ checked= {! rule .rule_criteria ? .disabled }
187+ on: change= {e => toggleRule (e, ' criteria' )}
188+ / >
189+ < / div>
190+ < / div>
191+ < / div>
192+ < div class = " utility-value" >
193+ < div class = " utility-input line-align-center" >
194+ < Input
195+ type= " select"
196+ disabled= {!! rule .rule_criteria ? .disabled }
197+ on: change= {e => changeRule (e, ' criteria' )}
198+ >
199+ {#each [... criteriaOptions] as option}
200+ < option value= {option .name } selected= {option .name == rule .rule_criteria ? .name }>
201+ {option .name }
202+ < / option>
203+ {/ each}
204+ < / Input>
205+ < / div>
206+ < div class = " utility-delete line-align-center" >< / div>
207+ < / div>
208+ < / div>
209+ < div class = " utility-list-item" >
210+ < div class = " utility-label line-align-center" >
211+ < div class = " d-flex gap-1" >
212+ < div class = " line-align-center" >
213+ {' Text' }
214+ < / div>
215+ {#if ADMIN_ROLES .includes (user? .role || ' ' ) && !! rule .trigger_name && !! rule .rule_criteria ? .criteria_text ? .trim ()}
216+ < div
217+ class = " line-align-center clickable text-primary fs-5"
218+ style= " padding-top: 3px;"
219+ data- bs- toggle= " tooltip"
220+ data- bs- placement= " top"
221+ title= " Compile code script"
222+ >
223+ < i
224+ class = " mdi mdi-play-circle"
225+ role= " link"
226+ tabindex= " 0"
227+ on: keydown= {() => {}}
228+ on: click= {() => compileCodeScript ()}
229+ / >
230+ < / div>
231+ {/ if }
232+ < / div>
233+ < / div>
234+ < div class = " utility-value" >
235+ < div class = " utility-input line-align-center" >
236+ < Input
237+ type= " textarea"
238+ style= " resize: none;"
239+ rows= {5 }
240+ disabled= {!! rule .rule_criteria ? .disabled }
241+ maxlength= {textLimit}
242+ value= {rule .rule_criteria ? .criteria_text }
243+ on: input= {e => changeContent (e, ' criteria-text' )}
244+ / >
245+ < / div>
246+ < div class = " utility-delete line-align-center" >
247+ {#if rule .json_args }
248+ < div class = " line-align-center" >
249+ < i
250+ class = " bx bxs-info-circle text-primary fs-5"
251+ id= {` rule-args-${ ruleIndex} ` }
252+ data- bs- toggle= " tooltip"
253+ data- bs- placement= " top"
254+ title= " Rule arguments"
255+ / >
256+ < BotsharpTooltip
257+ containerClasses= " agent-utility-desc"
258+ style= {` min-width: ${ Math .floor (windowWidth* 0.3 )} px;` }
259+ target= {` rule-args-${ ruleIndex} ` }
260+ placement= " right"
261+ persist
262+ >
263+ < Markdown
264+ rawText
265+ scrollable
266+ containerClasses= {' markdown-div' }
267+ containerStyles= {` max-width: ${ Math .floor (windowWidth* 0.3 )} px;` }
268+ text= {rule .json_args }
269+ / >
270+ < / BotsharpTooltip>
271+ < / div>
272+ {/ if }
273+ < / div>
274+ < / div>
275+ < / div>
276+ {#if rule .rule_criteria ? .name }
277+ < div class = " utility-list-item" >
278+ < div class = " utility-label line-align-center" >
279+ < div class = " d-flex gap-1" >
280+ < div class = " line-align-center" >
281+ {' Config' }
282+ < / div>
283+ < / div>
284+ < / div>
285+ < div class = " utility-value" >
286+ < div class = " utility-input line-align-center" >
287+ < CodeScript
288+ language= " json"
289+ containerClasses= " agent-rule-config"
290+ hideLineNumber= {true }
291+ editable= {! rule .rule_criteria ? .disabled }
292+ scriptText= {JSON .stringify (rule .rule_criteria ? .config || {}, null , 2 )}
293+ on: change= {(e ) => changeContent (e, ' criteria-config' )}
294+ / >
295+ < / div>
296+ < div class = " utility-delete line-align-center" >< / div>
297+ < / div>
298+ < / div>
299+ {/ if }
300+ < / div>
301+ < / div>
302+
303+ < div class = " utility-row utility-row-secondary" >
304+ < div class = " utility-content" >
305+ < div class = " utility-list-item" >
306+ < div class = " utility-label line-align-center" >
307+ < div class = " d-flex gap-1" >
308+ < div class = " line-align-center" >
309+ {' Action' }
310+ < / div>
311+ < div class = " line-align-center" >
312+ < Input
313+ type= " checkbox"
314+ checked= {! rule .rule_action ? .disabled }
315+ on: change= {e => toggleRule (e, ' action' )}
316+ / >
317+ < / div>
318+ < / div>
319+ < / div>
320+ < div class = " utility-value" >
321+ < div class = " utility-input line-align-center" >
322+ < Input
323+ type= " select"
324+ disabled= {!! rule .rule_action ? .disabled }
325+ on: change= {e => changeRule (e, ' action' )}
326+ >
327+ {#each [... actionOptions] as option}
328+ < option value= {option .name } selected= {option .name == rule .rule_action ? .name }>
329+ {option .name }
330+ < / option>
331+ {/ each}
332+ < / Input>
333+ < / div>
334+ < div class = " utility-delete line-align-center" >< / div>
335+ < / div>
336+ < / div>
337+ {#if rule .rule_action ? .name }
338+ < div class = " utility-list-item" >
339+ < div class = " utility-label line-align-center" >
340+ < div class = " d-flex gap-1" >
341+ < div class = " line-align-center" >
342+ {' Config' }
343+ < / div>
344+ < / div>
345+ < / div>
346+ < div class = " utility-value" >
347+ < div class = " utility-input line-align-center" >
348+ < CodeScript
349+ language= " json"
350+ containerClasses= " agent-rule-config"
351+ hideLineNumber= {true }
352+ editable= {! rule .rule_action ? .disabled }
353+ scriptText= {JSON .stringify (rule .rule_action ? .config || {}, null , 2 )}
354+ on: change= {(e ) => changeContent (e, ' action-config' )}
355+ / >
356+ < / div>
357+ < div class = " utility-delete line-align-center" >< / div>
358+ < / div>
359+ < / div>
360+ {/ if }
361+ < / div>
362+ < / div>
363+ {/ if }
364+ < / div>
0 commit comments