1
1
import { NamedImport } from '../../imports/NamedImport' ;
2
2
import { SymbolSpecifier } from '../../SymbolSpecifier' ;
3
3
import { stringTemplate } from '../../utilities/StringTemplate' ;
4
- import { TypescriptGenerationOptions } from '../TypescriptGenerationOptions' ;
4
+ import { MultiLineImportRule , TypescriptGenerationOptions } from '../TypescriptGenerationOptions' ;
5
5
import { generateSymbolSpecifier } from './symbolSpecifier' ;
6
6
7
- const importTemplate = stringTemplate `import ${ 0 } from ${ 1 } ` ;
7
+ const oneLinerImportTemplate = stringTemplate `import ${ 0 } from ${ 1 } ` ;
8
8
9
- const multiLineImport = stringTemplate `import ${ 3 } {
9
+ const multiLineImportTemplate = stringTemplate `import ${ 3 } {
10
10
${ 0 } ${ 1 }
11
11
} from ${ 2 } ` ;
12
12
13
+ const defaultAliasOnlyMultiLineImportTemplate = stringTemplate `import ${ 0 }
14
+ from ${ 1 } ` ;
15
+
13
16
/**
14
17
* Sort function for symbol specifiers. Does sort after the specifiers name (to lowercase).
15
18
*
@@ -23,7 +26,8 @@ function specifierSort(i1: SymbolSpecifier, i2: SymbolSpecifier): number {
23
26
24
27
if ( strA < strB ) {
25
28
return - 1 ;
26
- } else if ( strA > strB ) {
29
+ }
30
+ if ( strA > strB ) {
27
31
return 1 ;
28
32
}
29
33
return 0 ;
@@ -44,34 +48,61 @@ export function generateNamedImport(
44
48
stringQuoteStyle,
45
49
spaceBraces,
46
50
tabSize,
51
+ wrapMethod,
47
52
multiLineWrapThreshold,
48
53
multiLineTrailingComma,
54
+ insertSpaces = true ,
49
55
} : TypescriptGenerationOptions ,
50
56
) : string {
51
- const space = spaceBraces ? ' ' : '' ;
52
57
const lib = `${ stringQuoteStyle } ${ imp . libraryName } ${ stringQuoteStyle } ${ eol } ` ;
53
-
54
- const specifiers = imp . specifiers . sort ( specifierSort ) . map ( o => generateSymbolSpecifier ( o ) ) . join ( ', ' ) ;
55
- let importSpecifiers = `${ space } ${ specifiers } ${ space } ` ;
56
- if ( importSpecifiers . trim ( ) . length === 0 ) {
57
- importSpecifiers = ' ' ;
58
+ // const specifiers = imp.specifiers.sort(specifierSort).map(o => generateSymbolSpecifier(o)).join(', ');
59
+ const oneLinerImportStatement = oneLinerImportTemplate ( getImportSpecifiers ( imp , spaceBraces ) , lib ) ;
60
+ if ( oneLinerImportStatement . length <= multiLineWrapThreshold &&
61
+ ( wrapMethod !== MultiLineImportRule . strictlyOneImportPerLine ||
62
+ imp . specifiers . length <= 1 ) ) {
63
+ return oneLinerImportStatement ;
58
64
}
59
-
60
- const importString = importTemplate (
61
- getImportSpecifiers ( imp , spaceBraces ) ,
62
- lib ,
63
- ) ;
64
-
65
- if ( importString . length > multiLineWrapThreshold ) {
66
- const spacings = Array ( tabSize + 1 ) . join ( ' ' ) ;
67
- return multiLineImport (
68
- imp . specifiers . sort ( specifierSort ) . map ( o => `${ spacings } ${ generateSymbolSpecifier ( o ) } ` ) . join ( ',\n' ) ,
69
- multiLineTrailingComma ? ',' : '' ,
70
- `${ stringQuoteStyle } ${ imp . libraryName } ${ stringQuoteStyle } ${ eol } ` ,
65
+ const defaultAliasOnly : boolean = imp . specifiers . length === 0 ;
66
+ if ( defaultAliasOnly ) {
67
+ return defaultAliasOnlyMultiLineImportTemplate (
71
68
imp . defaultAlias ? `${ imp . defaultAlias } , ` : '' ,
69
+ `${ stringQuoteStyle } ${ imp . libraryName } ${ stringQuoteStyle } ${ eol } ` ,
72
70
) ;
73
71
}
74
- return importString ;
72
+
73
+ const sortedImportSpecifiers : SymbolSpecifier [ ] = imp . specifiers . sort ( specifierSort ) ;
74
+ let importSpecifierStrings : string = '' ;
75
+ const indent = insertSpaces ? Array ( tabSize + 1 ) . join ( ' ' ) : '\t' ;
76
+ if ( wrapMethod === MultiLineImportRule . strictlyOneImportPerLine ||
77
+ wrapMethod === MultiLineImportRule . oneImportPerLineOnlyAfterThreshold ) {
78
+ importSpecifierStrings = sortedImportSpecifiers . map ( o => `${ indent } ${ generateSymbolSpecifier ( o ) } ` ) . join ( ',\n' ) ;
79
+ } else if ( wrapMethod === MultiLineImportRule . multipleImportsPerLine ) {
80
+ importSpecifierStrings = sortedImportSpecifiers . reduce (
81
+ ( acc , curr ) => {
82
+ const symbolSpecifier : string = generateSymbolSpecifier ( curr ) ;
83
+ // const dist: number = acc.out.length - acc.lastWrapOffset + symbolSpecifier.length;
84
+ const importLines = acc . out . split ( '\n' ) ;
85
+ const lastImportLine = importLines [ importLines . length - 1 ] ;
86
+ const dist : number = lastImportLine . length + `, ` . length + symbolSpecifier . length ;
87
+ const needsWrap : boolean = dist >= multiLineWrapThreshold ;
88
+ return {
89
+ out : acc . out + ( needsWrap ? `,\n${ indent } ` : ( acc . out . length ? `, ` : `${ indent } ` ) ) +
90
+ symbolSpecifier ,
91
+ lastWrapOffset : acc . lastWrapOffset + ( needsWrap ? dist : 0 ) ,
92
+ } ;
93
+ } ,
94
+ {
95
+ out : '' ,
96
+ lastWrapOffset : 0 ,
97
+ } ,
98
+ ) . out ;
99
+ }
100
+ return multiLineImportTemplate (
101
+ importSpecifierStrings ,
102
+ multiLineTrailingComma ? ',' : '' ,
103
+ `${ stringQuoteStyle } ${ imp . libraryName } ${ stringQuoteStyle } ${ eol } ` ,
104
+ imp . defaultAlias ? `${ imp . defaultAlias } , ` : '' ,
105
+ ) ;
75
106
}
76
107
77
108
function getImportSpecifiers ( namedImport : NamedImport , spaceBraces : boolean ) : string {
0 commit comments