@@ -6,7 +6,7 @@ import type { BIDSContext } from './context.ts'
66import { loadJSON } from '../files/json.ts'
77import { loadTSV } from '../files/tsv.ts'
88import { parseBvalBvec } from '../files/dwi.ts'
9- import { walkBack } from '../files/inheritance.ts'
9+ import { readSidecars , walkBack } from '../files/inheritance.ts'
1010import { evalCheck } from './applyRules.ts'
1111import { expressionFunctions } from './expressionLanguage.ts'
1212import { readEntities } from './entities.ts'
@@ -15,11 +15,20 @@ import { readText } from '../files/access.ts'
1515
1616type LoadFunction = ( file : BIDSFile , options : any ) => Promise < any >
1717type MultiLoadFunction = ( files : BIDSFile [ ] , options : any ) => Promise < any >
18+ interface WithSidecar {
19+ sidecar : Record < string , unknown >
20+ }
1821
1922function defaultAssociation ( file : BIDSFile , _options : any ) : Promise < { path : string } > {
2023 return Promise . resolve ( { path : file . path } )
2124}
2225
26+ async function constructSidecar ( file : BIDSFile ) : Promise < Record < string , unknown > > {
27+ const sidecars = await readSidecars ( file )
28+ // Note ordering here gives precedence to the more specific sidecar
29+ return sidecars . values ( ) . reduce ( ( acc , json ) => ( { ...json , ...acc } ) , { } )
30+ }
31+
2332/**
2433 * This object describes lookup functions for files associated to data files in a bids dataset.
2534 * For any given data file we iterate over the associations defined schema.meta.associations.
@@ -29,14 +38,15 @@ function defaultAssociation(file: BIDSFile, _options: any): Promise<{ path: stri
2938 * Many associations only consist of a path; this object is for more complex associations.
3039 */
3140const associationLookup : Record < string , LoadFunction > = {
32- events : async ( file : BIDSFile , options : { maxRows : number } ) : Promise < Events > => {
41+ events : async ( file : BIDSFile , options : { maxRows : number } ) : Promise < Events & WithSidecar > => {
3342 const columns = await loadTSV ( file , options . maxRows )
3443 . catch ( ( e ) => {
3544 return new Map ( )
3645 } )
3746 return {
3847 path : file . path ,
3948 onset : columns . get ( 'onset' ) || [ ] ,
49+ sidecar : await constructSidecar ( file ) ,
4050 }
4151 } ,
4252 aslcontext : async (
@@ -90,6 +100,12 @@ const associationLookup: Record<string, LoadFunction> = {
90100 sampling_frequency : columns . get ( 'sampling_frequency' ) ,
91101 }
92102 } ,
103+ physio : async ( file : BIDSFile , options : any ) : Promise < { path : string } & WithSidecar > => {
104+ return {
105+ path : file . path ,
106+ sidecar : await constructSidecar ( file ) ,
107+ }
108+ } ,
93109}
94110const multiAssociationLookup : Record < string , MultiLoadFunction > = {
95111 coordsystems : async (
@@ -116,18 +132,12 @@ export async function buildAssociations(
116132 const associations : Associations = { }
117133
118134 const schema : MetaSchema = context . dataset . schema as MetaSchema
119- // Augment rule type with an entities field that should be present in BIDS 1.10.1+
120- type ruleType = MetaSchema [ 'meta' ] [ 'associations' ] [ keyof MetaSchema [ 'meta' ] [ 'associations' ] ]
121- type AugmentedRuleType = ruleType & {
122- target : ruleType [ 'target' ] & { entities ?: string [ ] }
123- }
124135
125136 Object . assign ( context , expressionFunctions )
126137 // @ts -expect-error
127138 context . exists . bind ( context )
128139
129- for ( const key of Object . keys ( schema . meta . associations ) ) {
130- const rule = schema . meta . associations [ key ] as AugmentedRuleType
140+ for ( const [ key , rule ] of Object . entries ( schema . meta . associations ) ) {
131141 if ( ! rule . selectors ! . every ( ( x ) => evalCheck ( x , context ) ) ) {
132142 continue
133143 }
0 commit comments