1*082815dcSEvan Baconimport assert from 'assert'; 2*082815dcSEvan Bacon 3*082815dcSEvan Baconexport type LanguageOptions = { 4*082815dcSEvan Bacon isTS: boolean; 5*082815dcSEvan Bacon isModern: boolean; 6*082815dcSEvan Bacon isReact: boolean; 7*082815dcSEvan Bacon}; 8*082815dcSEvan Bacon 9*082815dcSEvan Baconexport function getExtensions( 10*082815dcSEvan Bacon platforms: string[], 11*082815dcSEvan Bacon extensions: string[], 12*082815dcSEvan Bacon workflows: string[] 13*082815dcSEvan Bacon): string[] { 14*082815dcSEvan Bacon // In the past we used spread operators to collect the values so now we enforce type safety on them. 15*082815dcSEvan Bacon assert(Array.isArray(platforms), 'Expected: `platforms: string[]`'); 16*082815dcSEvan Bacon assert(Array.isArray(extensions), 'Expected: `extensions: string[]`'); 17*082815dcSEvan Bacon assert(Array.isArray(workflows), 'Expected: `workflows: string[]`'); 18*082815dcSEvan Bacon 19*082815dcSEvan Bacon const fileExtensions = []; 20*082815dcSEvan Bacon // support .expo files 21*082815dcSEvan Bacon for (const workflow of [...workflows, '']) { 22*082815dcSEvan Bacon // Ensure order is correct: [platformA.js, platformB.js, js] 23*082815dcSEvan Bacon for (const platform of [...platforms, '']) { 24*082815dcSEvan Bacon // Support both TypeScript and JavaScript 25*082815dcSEvan Bacon for (const extension of extensions) { 26*082815dcSEvan Bacon fileExtensions.push([platform, workflow, extension].filter(Boolean).join('.')); 27*082815dcSEvan Bacon } 28*082815dcSEvan Bacon } 29*082815dcSEvan Bacon } 30*082815dcSEvan Bacon return fileExtensions; 31*082815dcSEvan Bacon} 32*082815dcSEvan Bacon 33*082815dcSEvan Baconexport function getLanguageExtensionsInOrder({ 34*082815dcSEvan Bacon isTS, 35*082815dcSEvan Bacon isModern, 36*082815dcSEvan Bacon isReact, 37*082815dcSEvan Bacon}: LanguageOptions): string[] { 38*082815dcSEvan Bacon // @ts-ignore: filter removes false type 39*082815dcSEvan Bacon const addLanguage = (lang: string): string[] => [lang, isReact && `${lang}x`].filter(Boolean); 40*082815dcSEvan Bacon 41*082815dcSEvan Bacon // Support JavaScript 42*082815dcSEvan Bacon let extensions = addLanguage('js'); 43*082815dcSEvan Bacon 44*082815dcSEvan Bacon if (isModern) { 45*082815dcSEvan Bacon extensions.unshift('mjs'); 46*082815dcSEvan Bacon } 47*082815dcSEvan Bacon if (isTS) { 48*082815dcSEvan Bacon extensions = [...addLanguage('ts'), ...extensions]; 49*082815dcSEvan Bacon } 50*082815dcSEvan Bacon 51*082815dcSEvan Bacon return extensions; 52*082815dcSEvan Bacon} 53*082815dcSEvan Bacon 54*082815dcSEvan Baconexport function getBareExtensions( 55*082815dcSEvan Bacon platforms: string[], 56*082815dcSEvan Bacon languageOptions: LanguageOptions = { isTS: true, isModern: true, isReact: true } 57*082815dcSEvan Bacon): string[] { 58*082815dcSEvan Bacon const fileExtensions = getExtensions( 59*082815dcSEvan Bacon platforms, 60*082815dcSEvan Bacon getLanguageExtensionsInOrder(languageOptions), 61*082815dcSEvan Bacon [] 62*082815dcSEvan Bacon ); 63*082815dcSEvan Bacon // Always add these last 64*082815dcSEvan Bacon _addMiscellaneousExtensions(platforms, fileExtensions); 65*082815dcSEvan Bacon return fileExtensions; 66*082815dcSEvan Bacon} 67*082815dcSEvan Bacon 68*082815dcSEvan Baconfunction _addMiscellaneousExtensions(platforms: string[], fileExtensions: string[]): string[] { 69*082815dcSEvan Bacon // Always add these with no platform extension 70*082815dcSEvan Bacon // In the future we may want to add platform and workspace extensions to json. 71*082815dcSEvan Bacon fileExtensions.push('json'); 72*082815dcSEvan Bacon // Native doesn't currently support web assembly. 73*082815dcSEvan Bacon if (platforms.includes('web')) { 74*082815dcSEvan Bacon fileExtensions.push('wasm'); 75*082815dcSEvan Bacon } 76*082815dcSEvan Bacon return fileExtensions; 77*082815dcSEvan Bacon} 78