@@ -1019,27 +1019,112 @@ export function getTokensAfter(
10191019
10201020/**
10211021 * Get all of the tokens between two non-overlapping nodes.
1022- * @param nodeOrToken1 - Node before the desired token range.
1023- * @param nodeOrToken2 - Node after the desired token range.
1022+ * @param left - Node before the desired token range.
1023+ * @param right - Node after the desired token range.
10241024 * @param countOptions? - Options object. If this is a function then it's `options.filter`.
1025- * @returns Array of `Token`s between `nodeOrToken1 ` and `nodeOrToken2 `.
1025+ * @returns Array of `Token`s between `left ` and `right `.
10261026 */
10271027/**
10281028 * Get all of the tokens between two non-overlapping nodes.
1029- * @param nodeOrToken1 - Node before the desired token range.
1030- * @param nodeOrToken2 - Node after the desired token range.
1029+ * @param left - Node before the desired token range.
1030+ * @param right - Node after the desired token range.
10311031 * @param padding - Number of extra tokens on either side of center.
1032- * @returns Array of `Token`s between `nodeOrToken1 ` and `nodeOrToken2 `.
1032+ * @returns Array of `Token`s between `left ` and `right `.
10331033 */
1034- /* oxlint-disable no-unused-vars */
10351034export function getTokensBetween (
1036- nodeOrToken1 : NodeOrToken | Comment ,
1037- nodeOrToken2 : NodeOrToken | Comment ,
1035+ left : NodeOrToken | Comment ,
1036+ right : NodeOrToken | Comment ,
10381037 countOptions ?: CountOptions | number | FilterFn | null ,
10391038) : Token [ ] {
1040- throw new Error ( '`sourceCode.getTokensBetween` not implemented yet' ) ; // TODO
1039+ if ( tokens === null ) initTokens ( ) ;
1040+ debugAssertIsNonNull ( tokens ) ;
1041+ debugAssertIsNonNull ( comments ) ;
1042+
1043+ const count = typeof countOptions === 'object' && countOptions !== null ? countOptions . count : null ;
1044+
1045+ const padding = typeof countOptions === 'number' ? countOptions : 0 ;
1046+
1047+ const filter =
1048+ typeof countOptions === 'function'
1049+ ? countOptions
1050+ : typeof countOptions === 'object' && countOptions !== null
1051+ ? countOptions . filter
1052+ : null ;
1053+
1054+ const includeComments =
1055+ typeof countOptions === 'object' &&
1056+ countOptions !== null &&
1057+ 'includeComments' in countOptions &&
1058+ countOptions . includeComments ;
1059+
1060+ let nodeTokens : Token [ ] ;
1061+ if ( includeComments ) {
1062+ if ( tokensWithComments === null ) initTokensWithComments ( ) ;
1063+ debugAssertIsNonNull ( tokensWithComments ) ;
1064+ nodeTokens = tokensWithComments ;
1065+ } else {
1066+ nodeTokens = tokens ;
1067+ }
1068+
1069+ const rangeStart = left . range [ 1 ] ,
1070+ rangeEnd = right . range [ 0 ] ,
1071+ tokensLength = nodeTokens . length ;
1072+
1073+ // Binary search for first token past the beginning of the `between` range
1074+ let sliceStart = tokensLength ;
1075+ for ( let lo = 0 ; lo < sliceStart ; ) {
1076+ const mid = ( lo + sliceStart ) >> 1 ;
1077+ if ( nodeTokens [ mid ] . range [ 0 ] < rangeStart ) {
1078+ lo = mid + 1 ;
1079+ } else {
1080+ sliceStart = mid ;
1081+ }
1082+ }
1083+
1084+ // Binary search for first token past the end of the `between` range
1085+ let sliceEnd = tokensLength ;
1086+ for ( let lo = sliceStart ; lo < sliceEnd ; ) {
1087+ const mid = ( lo + sliceEnd ) >> 1 ;
1088+ if ( nodeTokens [ mid ] . range [ 0 ] < rangeEnd ) {
1089+ lo = mid + 1 ;
1090+ } else {
1091+ sliceEnd = mid ;
1092+ }
1093+ }
1094+
1095+ // Apply padding
1096+ sliceStart = max ( 0 , sliceStart - padding ) ;
1097+ sliceEnd += padding ;
1098+
1099+ let tokensBetween : Token [ ] ;
1100+ if ( typeof filter !== 'function' ) {
1101+ if ( typeof count !== 'number' ) {
1102+ tokensBetween = nodeTokens . slice ( sliceStart , sliceEnd ) ;
1103+ } else {
1104+ tokensBetween = nodeTokens . slice ( sliceStart , min ( sliceStart + count , sliceEnd ) ) ;
1105+ }
1106+ } else {
1107+ if ( typeof count !== 'number' ) {
1108+ tokensBetween = [ ] ;
1109+ for ( let i = sliceStart ; i < sliceEnd ; i ++ ) {
1110+ const token = nodeTokens [ i ] ;
1111+ if ( filter ( token ) ) {
1112+ tokensBetween . push ( token ) ;
1113+ }
1114+ }
1115+ } else {
1116+ tokensBetween = [ ] ;
1117+ for ( let i = sliceStart ; i < sliceEnd && tokensBetween . length < count ; i ++ ) {
1118+ const token = nodeTokens [ i ] ;
1119+ if ( filter ( token ) ) {
1120+ tokensBetween . push ( token ) ;
1121+ }
1122+ }
1123+ }
1124+ }
1125+
1126+ return tokensBetween ;
10411127}
1042- /* oxlint-enable no-unused-vars */
10431128
10441129/**
10451130 * Get the first token between two non-overlapping nodes.
0 commit comments