rust-dirs: address failing tests for `dirs` impl with a temporary fix
https://phab.mercurial-scm.org/D7252 (
5d40317d42b7083b49467502549e25f144888cb3)
introduced a regression in Rust tests.
This is a temporary fix that replicates the behavior of the C and Python impl,
pending the resolution of the discussion (in the phabricator link) about how
we actually want to solve this problem.
Differential Revision: https://phab.mercurial-scm.org/D7503
--- a/rust/hg-core/src/dirstate/dirs_multiset.rs Sun Dec 01 18:46:10 2019 -0500
+++ b/rust/hg-core/src/dirstate/dirs_multiset.rs Fri Nov 22 10:39:05 2019 +0100
@@ -65,14 +65,20 @@
/// 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: &HgPath) {
+ pub fn add_path(&mut self, path: &HgPath) -> Result<(), DirstateMapError> {
for subpath in files::find_dirs(path) {
+ if subpath.as_bytes().last() == Some(&b'/') {
+ // TODO Remove this once PathAuditor is certified
+ // as the only entrypoint for path data
+ return Err(DirstateMapError::ConsecutiveSlashes);
+ }
if let Some(val) = self.inner.get_mut(subpath) {
*val += 1;
break;
}
self.inner.insert(subpath.to_owned(), 1);
}
+ Ok(())
}
/// Decreases the count of deepest directory contained in the path.
--- a/rust/hg-core/src/dirstate/dirstate_map.rs Sun Dec 01 18:46:10 2019 -0500
+++ b/rust/hg-core/src/dirstate/dirstate_map.rs Fri Nov 22 10:39:05 2019 +0100
@@ -83,16 +83,16 @@
filename: &HgPath,
old_state: EntryState,
entry: DirstateEntry,
- ) {
+ ) -> Result<(), DirstateMapError> {
if old_state == EntryState::Unknown || old_state == EntryState::Removed
{
if let Some(ref mut dirs) = self.dirs {
- dirs.add_path(filename)
+ dirs.add_path(filename)?;
}
}
if old_state == EntryState::Unknown {
if let Some(ref mut all_dirs) = self.all_dirs {
- all_dirs.add_path(filename)
+ all_dirs.add_path(filename)?;
}
}
self.state_map.insert(filename.to_owned(), entry.to_owned());
@@ -104,6 +104,7 @@
if entry.size == SIZE_FROM_OTHER_PARENT {
self.other_parent_set.insert(filename.to_owned());
}
+ Ok(())
}
/// Mark a file as removed in the dirstate.
--- a/rust/hg-core/src/lib.rs Sun Dec 01 18:46:10 2019 -0500
+++ b/rust/hg-core/src/lib.rs Fri Nov 22 10:39:05 2019 +0100
@@ -101,6 +101,20 @@
pub enum DirstateMapError {
PathNotFound(HgPathBuf),
EmptyPath,
+ ConsecutiveSlashes,
+}
+
+impl ToString for DirstateMapError {
+ fn to_string(&self) -> String {
+ use crate::DirstateMapError::*;
+ match self {
+ PathNotFound(_) => "expected a value, found none".to_string(),
+ EmptyPath => "Overflow in dirstate.".to_string(),
+ ConsecutiveSlashes => {
+ "found invalid consecutive slashes in path".to_string()
+ }
+ }
+ }
}
pub enum DirstateError {
--- a/rust/hg-cpython/src/dirstate/dirs_multiset.rs Sun Dec 01 18:46:10 2019 -0500
+++ b/rust/hg-cpython/src/dirstate/dirs_multiset.rs Fri Nov 22 10:39:05 2019 +0100
@@ -68,8 +68,19 @@
def addpath(&self, path: PyObject) -> PyResult<PyObject> {
self.inner_shared(py).borrow_mut()?.add_path(
HgPath::new(path.extract::<PyBytes>(py)?.data(py)),
- );
- Ok(py.None())
+ ).and(Ok(py.None())).or_else(|e| {
+ match e {
+ DirstateMapError::EmptyPath => {
+ Ok(py.None())
+ },
+ e => {
+ Err(PyErr::new::<exc::ValueError, _>(
+ py,
+ e.to_string(),
+ ))
+ }
+ }
+ })
}
def delpath(&self, path: PyObject) -> PyResult<PyObject> {
@@ -79,15 +90,15 @@
.and(Ok(py.None()))
.or_else(|e| {
match e {
- DirstateMapError::PathNotFound(_p) => {
+ DirstateMapError::EmptyPath => {
+ Ok(py.None())
+ },
+ e => {
Err(PyErr::new::<exc::ValueError, _>(
py,
- "expected a value, found none".to_string(),
+ e.to_string(),
))
}
- DirstateMapError::EmptyPath => {
- Ok(py.None())
- }
}
})
}
--- a/rust/hg-cpython/src/dirstate/dirstate_map.rs Sun Dec 01 18:46:10 2019 -0500
+++ b/rust/hg-cpython/src/dirstate/dirstate_map.rs Fri Nov 22 10:39:05 2019 +0100
@@ -25,8 +25,8 @@
use hg::{
utils::hg_path::{HgPath, HgPathBuf},
DirsMultiset, DirstateEntry, DirstateMap as RustDirstateMap,
- DirstateParents, DirstateParseError, EntryState, StateMapIter,
- PARENT_SIZE,
+ DirstateMapError, DirstateParents, DirstateParseError, EntryState,
+ StateMapIter, PARENT_SIZE,
};
// TODO
@@ -97,8 +97,9 @@
size: size.extract(py)?,
mtime: mtime.extract(py)?,
},
- );
- Ok(py.None())
+ ).and(Ok(py.None())).or_else(|e: DirstateMapError| {
+ Err(PyErr::new::<exc::ValueError, _>(py, e.to_string()))
+ })
}
def removefile(