@@ -596,6 +596,22 @@ impl Index {
596596 Ok ( Binding :: from_raw ( & raw as * const _) )
597597 }
598598 }
599+
600+ /// Find the first position of any entries matching a prefix.
601+ ///
602+ /// To find the first position of a path inside a given folder, suffix the prefix with a '/'.
603+ pub fn find_prefix < T : IntoCString > ( & self , prefix : T ) -> Result < usize , Error > {
604+ let mut at_pos: size_t = 0 ;
605+ let entry_path = prefix. into_c_string ( ) ?;
606+ unsafe {
607+ try_call ! ( raw:: git_index_find_prefix(
608+ & mut at_pos,
609+ self . raw,
610+ entry_path
611+ ) ) ;
612+ Ok ( at_pos)
613+ }
614+ }
599615}
600616
601617impl Binding for Index {
@@ -746,7 +762,7 @@ mod tests {
746762 use std:: path:: Path ;
747763 use tempfile:: TempDir ;
748764
749- use crate :: { Index , IndexEntry , IndexTime , Oid , Repository , ResetType } ;
765+ use crate :: { ErrorCode , Index , IndexEntry , IndexTime , Oid , Repository , ResetType } ;
750766
751767 #[ test]
752768 fn smoke ( ) {
@@ -857,6 +873,27 @@ mod tests {
857873 assert_eq ! ( e. path. len( ) , 6 ) ;
858874 }
859875
876+ #[ test]
877+ fn add_then_find ( ) {
878+ let mut index = Index :: new ( ) . unwrap ( ) ;
879+ let mut e = entry ( ) ;
880+ e. path = b"foo/bar" . to_vec ( ) ;
881+ index. add ( & e) . unwrap ( ) ;
882+ let mut e = entry ( ) ;
883+ e. path = b"foo2/bar" . to_vec ( ) ;
884+ index. add ( & e) . unwrap ( ) ;
885+ assert_eq ! ( index. get( 0 ) . unwrap( ) . path, b"foo/bar" ) ;
886+ assert_eq ! (
887+ index. get_path( Path :: new( "foo/bar" ) , 0 ) . unwrap( ) . path,
888+ b"foo/bar"
889+ ) ;
890+ assert_eq ! ( index. find_prefix( Path :: new( "foo2/" ) ) , Ok ( 1 ) ) ;
891+ assert_eq ! (
892+ index. find_prefix( Path :: new( "empty/" ) ) . unwrap_err( ) . code( ) ,
893+ ErrorCode :: NotFound
894+ ) ;
895+ }
896+
860897 #[ test]
861898 fn add_frombuffer_then_read ( ) {
862899 let ( _td, repo) = crate :: test:: repo_init ( ) ;
0 commit comments