@adriansteffan/reactive 0.0.37 → 0.0.40
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/.claude/settings.local.json +10 -0
- package/dist/{mod-B9pn3CIt.js → mod-atv0jMSt.js} +2262 -2241
- package/dist/mod.d.ts +1 -1
- package/dist/reactive.es.js +1 -1
- package/dist/reactive.umd.js +28 -28
- package/dist/{web-wJPoJ8Wb.js → web-B_iADh05.js} +1 -1
- package/dist/{web-B5ojRUs4.js → web-WH3nbOGp.js} +1 -1
- package/package.json +1 -1
- package/src/components/upload.tsx +84 -27
- package/template/src/index.css +4 -1
package/package.json
CHANGED
|
@@ -108,27 +108,80 @@ function combineTrialsToCsv(
|
|
|
108
108
|
data: any[],
|
|
109
109
|
filename: string,
|
|
110
110
|
names: string[],
|
|
111
|
-
flatteningFunctions: Record<string, (item: any) => any[]
|
|
111
|
+
flatteningFunctions: Record<string, (item: any) => any[] | Record<string, any[]>>,
|
|
112
112
|
fun?: (obj: any) => any,
|
|
113
|
-
) {
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
113
|
+
): FileUpload | FileUpload[] {
|
|
114
|
+
|
|
115
|
+
// Collect all flattener results first
|
|
116
|
+
const allResults: (any[] | Record<string, any[]>)[] = names.flatMap((name) => {
|
|
117
|
+
const matchingItems = data.filter((d) => d.name === name);
|
|
118
|
+
|
|
119
|
+
return matchingItems.map((item) => {
|
|
120
|
+
const flattener = item.type && flatteningFunctions[item.type];
|
|
121
|
+
return flattener ? flattener(item) : [transform(item)];
|
|
122
|
+
});
|
|
123
|
+
});
|
|
124
|
+
|
|
125
|
+
// Check if any result is a multi-table object (has string keys with array values)
|
|
126
|
+
const hasMultiTable = allResults.some((result) =>
|
|
127
|
+
result &&
|
|
128
|
+
typeof result === 'object' &&
|
|
129
|
+
!Array.isArray(result) &&
|
|
130
|
+
Object.keys(result).some(key => Array.isArray(result[key]))
|
|
131
|
+
);
|
|
132
|
+
|
|
133
|
+
if (!hasMultiTable) {
|
|
134
|
+
// Original behavior: all results are arrays, combine them into one CSV
|
|
135
|
+
const processedData = allResults
|
|
136
|
+
.flatMap((result) => Array.isArray(result) ? result : [])
|
|
137
|
+
.map((x) => (fun ? fun(x) : x));
|
|
138
|
+
|
|
139
|
+
return {
|
|
140
|
+
filename,
|
|
141
|
+
encoding: 'utf8' as const,
|
|
142
|
+
content: convertArrayOfObjectsToCSV(processedData),
|
|
143
|
+
};
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
// New behavior: handle multi-table results
|
|
147
|
+
// Collect all table keys from all results
|
|
148
|
+
const allTableKeys = new Set<string>();
|
|
149
|
+
allResults.forEach((result) => {
|
|
150
|
+
if (result && typeof result === 'object' && !Array.isArray(result)) {
|
|
151
|
+
Object.keys(result).forEach(key => {
|
|
152
|
+
if (Array.isArray(result[key])) {
|
|
153
|
+
allTableKeys.add(key);
|
|
154
|
+
}
|
|
123
155
|
});
|
|
124
|
-
}
|
|
125
|
-
|
|
156
|
+
}
|
|
157
|
+
});
|
|
126
158
|
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
159
|
+
// Create separate CSV files for each table key
|
|
160
|
+
const files: FileUpload[] = [];
|
|
161
|
+
|
|
162
|
+
for (const tableKey of allTableKeys) {
|
|
163
|
+
const tableData = allResults.flatMap((result) => {
|
|
164
|
+
if (Array.isArray(result)) {
|
|
165
|
+
// If this result is a simple array, include it in all tables for backward compatibility
|
|
166
|
+
return result;
|
|
167
|
+
} else if (result && typeof result === 'object' && result[tableKey]) {
|
|
168
|
+
// If this result has data for this table key, include it
|
|
169
|
+
return result[tableKey];
|
|
170
|
+
}
|
|
171
|
+
return [];
|
|
172
|
+
}).map((x) => (fun ? fun(x) : x));
|
|
173
|
+
|
|
174
|
+
// Remove file extension from filename and add table key
|
|
175
|
+
const baseFilename = filename.replace(/\.csv$/, '');
|
|
176
|
+
|
|
177
|
+
files.push({
|
|
178
|
+
filename: `${baseFilename}_${tableKey}.csv`,
|
|
179
|
+
encoding: 'utf8' as const,
|
|
180
|
+
content: convertArrayOfObjectsToCSV(tableData),
|
|
181
|
+
});
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
return files.length === 1 ? files[0] : files;
|
|
132
185
|
}
|
|
133
186
|
|
|
134
187
|
interface FileBackend {
|
|
@@ -281,7 +334,7 @@ export default function Upload({
|
|
|
281
334
|
sessionID?: string | null;
|
|
282
335
|
generateFiles: (sessionID: string, data: TrialData[], store?: Store) => FileUpload[];
|
|
283
336
|
sessionCSVBuilder: CSVBuilder;
|
|
284
|
-
trialCSVBuilder: {flatteners: Record<string, ((item: TrialData) => Record<string, any>[])>, builders: CSVBuilder[]};
|
|
337
|
+
trialCSVBuilder: {flatteners: Record<string, ((item: TrialData) => Record<string, any>[] | Record<string, Record<string, any>[]>)>, builders: CSVBuilder[]};
|
|
285
338
|
uploadRaw: boolean;
|
|
286
339
|
autoUpload: boolean;
|
|
287
340
|
androidFolderName?: string;
|
|
@@ -415,15 +468,19 @@ export default function Upload({
|
|
|
415
468
|
|
|
416
469
|
if (trialCSVBuilder) {
|
|
417
470
|
for (const builder of trialCSVBuilder.builders) {
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
builder.fun,
|
|
425
|
-
),
|
|
471
|
+
const result = combineTrialsToCsv(
|
|
472
|
+
data,
|
|
473
|
+
`${sessionIDUpload}${builder.filename}.csv`,
|
|
474
|
+
builder.trials ?? [],
|
|
475
|
+
{...defaultFlatteningFunctions, ...trialCSVBuilder.flatteners},
|
|
476
|
+
builder.fun,
|
|
426
477
|
);
|
|
478
|
+
|
|
479
|
+
if (Array.isArray(result)) {
|
|
480
|
+
files.push(...result);
|
|
481
|
+
} else {
|
|
482
|
+
files.push(result);
|
|
483
|
+
}
|
|
427
484
|
}
|
|
428
485
|
}
|
|
429
486
|
|
package/template/src/index.css
CHANGED