| 821 | }; |
| 822 | |
| 823 | const formatWorkflowParams = (workflow) => { |
| 824 | if (!workflow || typeof workflow !== 'object') return []; |
| 825 | const params = (workflow.params && typeof workflow.params === 'object') ? workflow.params : {}; |
| 826 | const rows = []; |
| 827 | const jobId = Number(workflow.jobId || 0); |
| 828 | if (jobId > 0) rows.push(`Job: #${jobId}`); |
| 829 | const visionEnabled = !!params.visionEnabled; |
| 830 | const ocrEnabled = !!params.ocrEnabled; |
| 831 | if (visionEnabled || ocrEnabled) { |
| 832 | const analysisMode = visionEnabled && ocrEnabled |
| 833 | ? 'Vision + OCR' |
| 834 | : (visionEnabled ? 'Vision only' : 'OCR only'); |
| 835 | rows.push(`Analysis: ${analysisMode}`); |
| 836 | } |
| 837 | const adapterStats = (workflow.adapterStats && typeof workflow.adapterStats === 'object') ? workflow.adapterStats : {}; |
| 838 | const adapterPairs = Object.entries(adapterStats) |
| 839 | .map(([name, count]) => { |
| 840 | const label = String(name || '').trim(); |
| 841 | const total = Number(count || 0); |
| 842 | if (!label || total <= 0) return ''; |
| 843 | return `${label} ${total}`; |
| 844 | }) |
| 845 | .filter((entry) => entry !== ''); |
| 846 | if (adapterPairs.length) { |
| 847 | rows.push(`Adapters: ${adapterPairs.join(' | ')}`); |
| 848 | } |
| 849 | const destination = String(params.destination || '').trim(); |
| 850 | if (destination) rows.push(`Destination: ${destination}`); |
| 851 | const schemaName = String(params.schemaName || params.schema?.name || '').trim(); |
| 852 | if (schemaName) rows.push(`Schema: ${schemaName}`); |
| 853 | const outputFormats = Array.isArray(params.outputFormats) |
| 854 | ? params.outputFormats.map((entry) => String(entry || '').trim()).filter((entry) => entry !== '') |
| 855 | : []; |
| 856 | if (outputFormats.length) rows.push(`Outputs: ${outputFormats.join(', ')}`); |
| 857 | const organizeMode = String(params.mode || '').trim(); |
| 858 | if (organizeMode) { |
| 859 | rows.push(`Organize by: ${organizeMode === 'by_year' ? 'Year' : 'Type'}`); |
| 860 | } |
| 861 | const match = String(params.match || '').trim(); |
| 862 | const replace = String(params.replace || '').trim(); |
| 863 | if (match || replace) { |
| 864 | rows.push(`Rule: replace "${match}" -> "${replace}"`); |
| 865 | } |
| 866 | const nameContains = String(params.nameContains || '').trim(); |
| 867 | if (nameContains) rows.push(`Filename contains: ${nameContains}`); |
| 868 | const extensions = Array.isArray(params.extensions) |
| 869 | ? params.extensions.map((entry) => String(entry || '').trim()).filter((entry) => entry !== '') |
| 870 | : []; |
| 871 | if (extensions.length) rows.push(`Extensions: ${extensions.join(', ')}`); |
| 872 | if (params.withoutTags) rows.push('Filter: without tags'); |
| 873 | const olderThanDays = Number(params.olderThanDays || 0); |
| 874 | if (olderThanDays > 0) rows.push(`Older than: ${olderThanDays} day(s)`); |
| 875 | const largestN = Number(params.largestN || 0); |
| 876 | if (largestN > 0) rows.push(`Largest: top ${largestN} file(s)`); |
| 877 | const tags = Array.isArray(params.tags) |
| 878 | ? params |
| 879 | .tags |
| 880 | .map((tag) => (tag && typeof tag === 'object') ? String(tag.name || '').trim() : '') |