@@ -115,57 +115,56 @@ function formatSubBlockValue(value: unknown): string {
115115}
116116
117117/**
118- * Get display label for a subblock type.
118+ * Evaluate whether a subblock's condition is met based on current values.
119+ * Returns true if the subblock should be visible.
119120 */
120- function getSubBlockTypeLabel ( type : string ) : string {
121- const typeLabels : Record < string , string > = {
122- 'short-input' : 'Text' ,
123- 'long-input' : 'Text Area' ,
124- dropdown : 'Select' ,
125- combobox : 'Combobox' ,
126- slider : 'Slider' ,
127- table : 'Table' ,
128- code : 'Code' ,
129- switch : 'Toggle' ,
130- 'tool-input' : 'Tool' ,
131- 'checkbox-list' : 'Checkboxes' ,
132- 'grouped-checkbox-list' : 'Grouped Checkboxes' ,
133- 'condition-input' : 'Condition' ,
134- 'eval-input' : 'Evaluation' ,
135- 'time-input' : 'Time' ,
136- 'oauth-input' : 'OAuth' ,
137- 'webhook-config' : 'Webhook' ,
138- 'schedule-info' : 'Schedule' ,
139- 'file-selector' : 'File' ,
140- 'project-selector' : 'Project' ,
141- 'channel-selector' : 'Channel' ,
142- 'user-selector' : 'User' ,
143- 'folder-selector' : 'Folder' ,
144- 'knowledge-base-selector' : 'Knowledge Base' ,
145- 'knowledge-tag-filters' : 'Tag Filters' ,
146- 'document-selector' : 'Document' ,
147- 'document-tag-entry' : 'Document Tags' ,
148- 'mcp-server-selector' : 'MCP Server' ,
149- 'mcp-tool-selector' : 'MCP Tool' ,
150- 'mcp-dynamic-args' : 'MCP Args' ,
151- 'input-format' : 'Input Format' ,
152- 'response-format' : 'Response Format' ,
153- 'trigger-save' : 'Trigger' ,
154- 'file-upload' : 'File Upload' ,
155- 'input-mapping' : 'Input Mapping' ,
156- 'variables-input' : 'Variables' ,
157- 'messages-input' : 'Messages' ,
158- 'workflow-selector' : 'Workflow' ,
159- 'workflow-input-mapper' : 'Workflow Input' ,
160- text : 'Text' ,
121+ function evaluateCondition (
122+ condition : SubBlockConfig [ 'condition' ] ,
123+ subBlockValues : Record < string , { value : unknown } | unknown >
124+ ) : boolean {
125+ if ( ! condition ) return true
126+
127+ const actualCondition = typeof condition === 'function' ? condition ( ) : condition
128+
129+ const fieldValueObj = subBlockValues [ actualCondition . field ]
130+ const fieldValue =
131+ fieldValueObj && typeof fieldValueObj === 'object' && 'value' in fieldValueObj
132+ ? ( fieldValueObj as { value : unknown } ) . value
133+ : fieldValueObj
134+
135+ const conditionValues = Array . isArray ( actualCondition . value )
136+ ? actualCondition . value
137+ : [ actualCondition . value ]
138+
139+ let isMatch = conditionValues . some ( ( v ) => v === fieldValue )
140+
141+ if ( actualCondition . not ) {
142+ isMatch = ! isMatch
161143 }
162144
163- return typeLabels [ type ] || type
145+ if ( actualCondition . and && isMatch ) {
146+ const andFieldValueObj = subBlockValues [ actualCondition . and . field ]
147+ const andFieldValue =
148+ andFieldValueObj && typeof andFieldValueObj === 'object' && 'value' in andFieldValueObj
149+ ? ( andFieldValueObj as { value : unknown } ) . value
150+ : andFieldValueObj
151+
152+ const andConditionValues = Array . isArray ( actualCondition . and . value )
153+ ? actualCondition . and . value
154+ : [ actualCondition . and . value ]
155+
156+ let andMatch = andConditionValues . some ( ( v ) => v === andFieldValue )
157+
158+ if ( actualCondition . and . not ) {
159+ andMatch = ! andMatch
160+ }
161+
162+ isMatch = isMatch && andMatch
163+ }
164+
165+ return isMatch
164166}
165167
166- /**
167- * Individual subblock row showing label, type, and value.
168- */
169168function SubBlockRow ( {
170169 subBlockConfig,
171170 value,
@@ -174,17 +173,11 @@ function SubBlockRow({
174173 value : unknown
175174} ) {
176175 const title = subBlockConfig . title || subBlockConfig . id
177- const typeLabel = getSubBlockTypeLabel ( subBlockConfig . type )
178176 const hasValue = value !== null && value !== undefined && value !== ''
179177
180178 return (
181179 < div className = 'flex flex-col gap-[6px] border-[var(--border)] border-b py-[10px] last:border-b-0' >
182- < div className = 'flex items-center justify-between gap-[8px]' >
183- < span className = 'font-medium text-[13px] text-[var(--text-primary)]' > { title } </ span >
184- < Badge variant = 'gray-secondary' className = 'text-[10px]' >
185- { typeLabel }
186- </ Badge >
187- </ div >
180+ < span className = 'font-medium text-[13px] text-[var(--text-primary)]' > { title } </ span >
188181 { hasValue ? (
189182 < ExpandableValue title = { title } value = { value } />
190183 ) : (
@@ -231,14 +224,18 @@ export function PinnedSubBlocks({ block, onClose }: PinnedSubBlocksProps) {
231224 )
232225 }
233226
234- // Get visible subblocks (filter out hidden ones)
235- const visibleSubBlocks = blockConfig . subBlocks . filter (
236- ( subBlock ) => ! subBlock . hidden && ! subBlock . hideFromPreview
237- )
238-
239- // Get subblock values from block state
240227 const subBlockValues = block . subBlocks || { }
241228
229+ const visibleSubBlocks = blockConfig . subBlocks . filter ( ( subBlock ) => {
230+ if ( subBlock . hidden || subBlock . hideFromPreview ) return false
231+
232+ if ( subBlock . condition ) {
233+ return evaluateCondition ( subBlock . condition , subBlockValues )
234+ }
235+
236+ return true
237+ } )
238+
242239 return (
243240 < div className = 'absolute top-[16px] right-[16px] z-[100] flex max-h-[calc(100%-32px)] w-80 flex-col overflow-hidden rounded-[8px] border border-[var(--border)] bg-[var(--surface-1)] shadow-lg' >
244241 { /* Header */ }
0 commit comments