diff rust/hg-core/src/dirstate/dirs_multiset.rs @ 42957:7a01778bc7b7

rust-hgpath: replace all paths and filenames with HgPath/HgPathBuf Differential Revision: https://phab.mercurial-scm.org/D6774
author Raphaël Gomès <rgomes@octobus.net>
date Sun, 01 Sep 2019 20:53:14 +0200
parents a03a29462c0a
children 1fe2e574616e
line wrap: on
line diff
--- a/rust/hg-core/src/dirstate/dirs_multiset.rs	Sun Sep 01 20:53:14 2019 +0200
+++ b/rust/hg-core/src/dirstate/dirs_multiset.rs	Sun Sep 01 20:53:14 2019 +0200
@@ -8,6 +8,7 @@
 //! A multiset of directory names.
 //!
 //! Used to counts the references to directories in a manifest or dirstate.
+use crate::utils::hg_path::{HgPath, HgPathBuf};
 use crate::{
     dirstate::EntryState, utils::files, DirstateEntry, DirstateMapError,
 };
@@ -15,11 +16,11 @@
 use std::collections::HashMap;
 
 // could be encapsulated if we care API stability more seriously
-pub type DirsMultisetIter<'a> = hash_map::Keys<'a, Vec<u8>, u32>;
+pub type DirsMultisetIter<'a> = hash_map::Keys<'a, HgPathBuf, u32>;
 
 #[derive(PartialEq, Debug)]
 pub struct DirsMultiset {
-    inner: HashMap<Vec<u8>, u32>,
+    inner: HashMap<HgPathBuf, u32>,
 }
 
 impl DirsMultiset {
@@ -27,7 +28,7 @@
     ///
     /// If `skip_state` is provided, skips dirstate entries with equal state.
     pub fn from_dirstate(
-        vec: &HashMap<Vec<u8>, DirstateEntry>,
+        vec: &HashMap<HgPathBuf, DirstateEntry>,
         skip_state: Option<EntryState>,
     ) -> Self {
         let mut multiset = DirsMultiset {
@@ -49,7 +50,7 @@
     }
 
     /// Initializes the multiset from a manifest.
-    pub fn from_manifest(vec: &Vec<Vec<u8>>) -> Self {
+    pub fn from_manifest(vec: &Vec<HgPathBuf>) -> Self {
         let mut multiset = DirsMultiset {
             inner: HashMap::new(),
         };
@@ -64,7 +65,7 @@
     /// Increases the count of deepest directory contained in the path.
     ///
     /// If the directory is not yet in the map, adds its parents.
-    pub fn add_path(&mut self, path: &[u8]) {
+    pub fn add_path(&mut self, path: &HgPath) {
         for subpath in files::find_dirs(path) {
             if let Some(val) = self.inner.get_mut(subpath) {
                 *val += 1;
@@ -81,7 +82,7 @@
     /// If the directory is not in the map, something horrible has happened.
     pub fn delete_path(
         &mut self,
-        path: &[u8],
+        path: &HgPath,
     ) -> Result<(), DirstateMapError> {
         for subpath in files::find_dirs(path) {
             match self.inner.entry(subpath.to_owned()) {
@@ -104,7 +105,7 @@
         Ok(())
     }
 
-    pub fn contains(&self, key: &[u8]) -> bool {
+    pub fn contains(&self, key: &HgPath) -> bool {
         self.inner.contains_key(key)
     }
 
@@ -125,20 +126,20 @@
     #[test]
     fn test_delete_path_path_not_found() {
         let mut map = DirsMultiset::from_manifest(&vec![]);
-        let path = b"doesnotexist/";
+        let path = HgPathBuf::from_bytes(b"doesnotexist/");
         assert_eq!(
-            Err(DirstateMapError::PathNotFound(path.to_vec())),
-            map.delete_path(path)
+            Err(DirstateMapError::PathNotFound(path.to_owned())),
+            map.delete_path(&path)
         );
     }
 
     #[test]
     fn test_delete_path_empty_path() {
-        let mut map = DirsMultiset::from_manifest(&vec![vec![]]);
-        let path = b"";
+        let mut map = DirsMultiset::from_manifest(&vec![HgPathBuf::new()]);
+        let path = HgPath::new(b"");
         assert_eq!(Ok(()), map.delete_path(path));
         assert_eq!(
-            Err(DirstateMapError::PathNotFound(path.to_vec())),
+            Err(DirstateMapError::PathNotFound(path.to_owned())),
             map.delete_path(path)
         );
     }
@@ -148,34 +149,40 @@
         let mut map = DirsMultiset {
             inner: [("", 5), ("a", 3), ("a/b", 2), ("a/c", 1)]
                 .iter()
-                .map(|(k, v)| (k.as_bytes().to_vec(), *v))
+                .map(|(k, v)| (HgPathBuf::from_bytes(k.as_bytes()), *v))
                 .collect(),
         };
 
-        assert_eq!(Ok(()), map.delete_path(b"a/b/"));
-        assert_eq!(Ok(()), map.delete_path(b"a/b/"));
+        assert_eq!(Ok(()), map.delete_path(HgPath::new(b"a/b/")));
+        eprintln!("{:?}", map);
+        assert_eq!(Ok(()), map.delete_path(HgPath::new(b"a/b/")));
+        eprintln!("{:?}", map);
         assert_eq!(
-            Err(DirstateMapError::PathNotFound(b"a/b/".to_vec())),
-            map.delete_path(b"a/b/")
+            Err(DirstateMapError::PathNotFound(HgPathBuf::from_bytes(
+                b"a/b/"
+            ))),
+            map.delete_path(HgPath::new(b"a/b/"))
         );
 
-        assert_eq!(2, *map.inner.get(&b"a".to_vec()).unwrap());
-        assert_eq!(1, *map.inner.get(&b"a/c".to_vec()).unwrap());
+        assert_eq!(2, *map.inner.get(HgPath::new(b"a")).unwrap());
+        assert_eq!(1, *map.inner.get(HgPath::new(b"a/c")).unwrap());
         eprintln!("{:?}", map);
-        assert_eq!(Ok(()), map.delete_path(b"a/"));
+        assert_eq!(Ok(()), map.delete_path(HgPath::new(b"a/")));
         eprintln!("{:?}", map);
 
-        assert_eq!(Ok(()), map.delete_path(b"a/c/"));
+        assert_eq!(Ok(()), map.delete_path(HgPath::new(b"a/c/")));
         assert_eq!(
-            Err(DirstateMapError::PathNotFound(b"a/c/".to_vec())),
-            map.delete_path(b"a/c/")
+            Err(DirstateMapError::PathNotFound(HgPathBuf::from_bytes(
+                b"a/c/"
+            ))),
+            map.delete_path(HgPath::new(b"a/c/"))
         );
     }
 
     #[test]
     fn test_add_path_empty_path() {
         let mut map = DirsMultiset::from_manifest(&vec![]);
-        let path = b"";
+        let path = HgPath::new(b"");
         map.add_path(path);
 
         assert_eq!(1, map.len());
@@ -185,42 +192,42 @@
     fn test_add_path_successful() {
         let mut map = DirsMultiset::from_manifest(&vec![]);
 
-        map.add_path(b"a/");
-        assert_eq!(1, *map.inner.get(&b"a".to_vec()).unwrap());
-        assert_eq!(1, *map.inner.get(&Vec::new()).unwrap());
+        map.add_path(HgPath::new(b"a/"));
+        assert_eq!(1, *map.inner.get(HgPath::new(b"a")).unwrap());
+        assert_eq!(1, *map.inner.get(HgPath::new(b"")).unwrap());
         assert_eq!(2, map.len());
 
         // Non directory should be ignored
-        map.add_path(b"a");
-        assert_eq!(1, *map.inner.get(&b"a".to_vec()).unwrap());
+        map.add_path(HgPath::new(b"a"));
+        assert_eq!(1, *map.inner.get(HgPath::new(b"a")).unwrap());
         assert_eq!(2, map.len());
 
         // Non directory will still add its base
-        map.add_path(b"a/b");
-        assert_eq!(2, *map.inner.get(&b"a".to_vec()).unwrap());
+        map.add_path(HgPath::new(b"a/b"));
+        assert_eq!(2, *map.inner.get(HgPath::new(b"a")).unwrap());
         assert_eq!(2, map.len());
 
         // Duplicate path works
-        map.add_path(b"a/");
-        assert_eq!(3, *map.inner.get(&b"a".to_vec()).unwrap());
+        map.add_path(HgPath::new(b"a/"));
+        assert_eq!(3, *map.inner.get(HgPath::new(b"a")).unwrap());
 
         // Nested dir adds to its base
-        map.add_path(b"a/b/");
-        assert_eq!(4, *map.inner.get(&b"a".to_vec()).unwrap());
-        assert_eq!(1, *map.inner.get(&b"a/b".to_vec()).unwrap());
+        map.add_path(HgPath::new(b"a/b/"));
+        assert_eq!(4, *map.inner.get(HgPath::new(b"a")).unwrap());
+        assert_eq!(1, *map.inner.get(HgPath::new(b"a/b")).unwrap());
 
         // but not its base's base, because it already existed
-        map.add_path(b"a/b/c/");
-        assert_eq!(4, *map.inner.get(&b"a".to_vec()).unwrap());
-        assert_eq!(2, *map.inner.get(&b"a/b".to_vec()).unwrap());
+        map.add_path(HgPath::new(b"a/b/c/"));
+        assert_eq!(4, *map.inner.get(HgPath::new(b"a")).unwrap());
+        assert_eq!(2, *map.inner.get(HgPath::new(b"a/b")).unwrap());
 
-        map.add_path(b"a/c/");
-        assert_eq!(1, *map.inner.get(&b"a/c".to_vec()).unwrap());
+        map.add_path(HgPath::new(b"a/c/"));
+        assert_eq!(1, *map.inner.get(HgPath::new(b"a/c")).unwrap());
 
         let expected = DirsMultiset {
             inner: [("", 2), ("a", 5), ("a/b", 2), ("a/b/c", 1), ("a/c", 1)]
                 .iter()
-                .map(|(k, v)| (k.as_bytes().to_vec(), *v))
+                .map(|(k, v)| (HgPathBuf::from_bytes(k.as_bytes()), *v))
                 .collect(),
         };
         assert_eq!(map, expected);
@@ -245,11 +252,11 @@
     fn test_dirsmultiset_new_no_skip() {
         let input_vec = ["a/", "b/", "a/c", "a/d/"]
             .iter()
-            .map(|e| e.as_bytes().to_vec())
+            .map(|e| HgPathBuf::from_bytes(e.as_bytes()))
             .collect();
         let expected_inner = [("", 2), ("a", 3), ("b", 1), ("a/d", 1)]
             .iter()
-            .map(|(k, v)| (k.as_bytes().to_vec(), *v))
+            .map(|(k, v)| (HgPathBuf::from_bytes(k.as_bytes()), *v))
             .collect();
 
         let new = DirsMultiset::from_manifest(&input_vec);
@@ -262,7 +269,7 @@
             .iter()
             .map(|f| {
                 (
-                    f.as_bytes().to_vec(),
+                    HgPathBuf::from_bytes(f.as_bytes()),
                     DirstateEntry {
                         state: EntryState::Normal,
                         mode: 0,
@@ -274,7 +281,7 @@
             .collect();
         let expected_inner = [("", 2), ("a", 3), ("b", 1), ("a/d", 1)]
             .iter()
-            .map(|(k, v)| (k.as_bytes().to_vec(), *v))
+            .map(|(k, v)| (HgPathBuf::from_bytes(k.as_bytes()), *v))
             .collect();
 
         let new = DirsMultiset::from_dirstate(&input_map, None);
@@ -295,7 +302,7 @@
         .iter()
         .map(|(f, state)| {
             (
-                f.as_bytes().to_vec(),
+                HgPathBuf::from_bytes(f.as_bytes()),
                 DirstateEntry {
                     state: *state,
                     mode: 0,
@@ -309,7 +316,7 @@
         // "a" incremented with "a/c" and "a/d/"
         let expected_inner = [("", 1), ("a", 2), ("a/d", 1)]
             .iter()
-            .map(|(k, v)| (k.as_bytes().to_vec(), *v))
+            .map(|(k, v)| (HgPathBuf::from_bytes(k.as_bytes()), *v))
             .collect();
 
         let new =