@@ -25,16 +25,19 @@ use sha2::{
2525} ;
2626use value:: {
2727 heap_size:: HeapSize ,
28+ id_v6:: VirtualTableNumberMap ,
2829 utils:: display_sequence,
2930 val,
3031 ConvexObject ,
3132 ConvexValue ,
33+ DeveloperDocumentId ,
3234 TableId ,
3335 TableIdAndTableNumber ,
3436} ;
3537
3638use crate :: {
3739 bootstrap_model:: index:: database_index:: IndexedFields ,
40+ document:: ID_FIELD_PATH ,
3841 index:: IndexKeyBytes ,
3942 interval:: {
4043 BinaryKey ,
@@ -176,26 +179,36 @@ pub struct IndexRange {
176179}
177180
178181impl IndexRange {
179- pub fn compile ( self , indexed_fields : IndexedFields ) -> anyhow:: Result < Interval > {
182+ pub fn compile (
183+ self ,
184+ indexed_fields : IndexedFields ,
185+ virtual_table_number_map : Option < VirtualTableNumberMap > ,
186+ ) -> anyhow:: Result < Interval > {
180187 let index_name = self . index_name . clone ( ) ;
181188 let SplitIndexRange {
182189 equalities,
183190 inequality,
184- } = self . split ( ) ?;
191+ } = self . split ( ) ?. map_values ( |field, v| {
192+ if field == & * ID_FIELD_PATH {
193+ map_id_value_to_tablet ( v, virtual_table_number_map)
194+ } else {
195+ Ok ( v)
196+ }
197+ } ) ?;
185198
186199 // Check that some permutation of the equality field paths + the (optional)
187200 // inequality field path is a prefix of the indexed paths.
188201 //
189202 // NB: `indexed_fields` does not include the implicit `_id` field at the end of
190203 // every index, so this omission prevents the user from using it in an
191204 // index expression.
192- let index_rank: BTreeMap < _ , _ > = indexed_fields[ .. ]
193- . iter ( )
205+ let index_rank: BTreeMap < _ , _ > = indexed_fields
206+ . iter_with_id ( )
194207 . enumerate ( )
195208 . map ( |( i, field_name) | ( field_name, i) )
196209 . collect ( ) ;
197210 anyhow:: ensure!(
198- index_rank. len( ) == indexed_fields. len ( ) ,
211+ index_rank. len( ) == indexed_fields. iter_with_id ( ) . count ( ) ,
199212 "{index_name} has duplicate fields?"
200213 ) ;
201214
@@ -237,7 +250,7 @@ impl IndexRange {
237250
238251 let query_fields = QueryFields ( used_paths. clone ( ) ) ;
239252
240- let mut fields_iter = indexed_fields. iter ( ) ;
253+ let mut fields_iter = indexed_fields. iter_with_id ( ) ;
241254 for field_path in used_paths {
242255 let matching_field = fields_iter. next ( ) . ok_or_else ( || {
243256 invalid_index_range ( & index_name, & indexed_fields, & query_fields, & field_path)
@@ -387,6 +400,49 @@ struct SplitIndexRange {
387400 inequality : Option < IndexInequality > ,
388401}
389402
403+ impl SplitIndexRange {
404+ pub fn map_values (
405+ self ,
406+ f : impl Fn ( & FieldPath , ConvexValue ) -> anyhow:: Result < ConvexValue > ,
407+ ) -> anyhow:: Result < SplitIndexRange > {
408+ let equalities = self
409+ . equalities
410+ . into_iter ( )
411+ . map ( |( field, value) | {
412+ let new_value = match value. 0 {
413+ Some ( value) => MaybeValue ( Some ( f ( & field, value) ?) ) ,
414+ None => MaybeValue ( None ) ,
415+ } ;
416+ anyhow:: Ok ( ( field, new_value) )
417+ } )
418+ . try_collect ( ) ?;
419+ let inequality = self
420+ . inequality
421+ . map ( |inequality| {
422+ let start = match inequality. start {
423+ Bound :: Unbounded => Bound :: Unbounded ,
424+ Bound :: Included ( value) => Bound :: Included ( f ( & inequality. field_path , value) ?) ,
425+ Bound :: Excluded ( value) => Bound :: Excluded ( f ( & inequality. field_path , value) ?) ,
426+ } ;
427+ let end = match inequality. end {
428+ Bound :: Unbounded => Bound :: Unbounded ,
429+ Bound :: Included ( value) => Bound :: Included ( f ( & inequality. field_path , value) ?) ,
430+ Bound :: Excluded ( value) => Bound :: Excluded ( f ( & inequality. field_path , value) ?) ,
431+ } ;
432+ anyhow:: Ok ( IndexInequality {
433+ field_path : inequality. field_path ,
434+ start,
435+ end,
436+ } )
437+ } )
438+ . transpose ( ) ?;
439+ Ok ( SplitIndexRange {
440+ equalities,
441+ inequality,
442+ } )
443+ }
444+ }
445+
390446struct IndexInequality {
391447 field_path : FieldPath ,
392448 start : Bound < ConvexValue > ,
@@ -403,6 +459,21 @@ impl Display for QueryFields {
403459 }
404460}
405461
462+ fn map_id_value_to_tablet (
463+ value : ConvexValue ,
464+ virtual_table_number_map : Option < VirtualTableNumberMap > ,
465+ ) -> anyhow:: Result < ConvexValue > {
466+ let val = match ( & value, virtual_table_number_map) {
467+ ( ConvexValue :: String ( id) , Some ( virtual_table_number_map) ) => {
468+ let mapped =
469+ DeveloperDocumentId :: map_string_between_table_numbers ( id, virtual_table_number_map) ;
470+ val ! ( mapped)
471+ } ,
472+ _ => value,
473+ } ;
474+ Ok ( val)
475+ }
476+
406477fn already_defined_bound_error (
407478 bound_type : & str ,
408479 field_path : & FieldPath ,
0 commit comments