comparison rust/hg-cpython/src/dirstate/status.rs @ 43916:6a88ced33c40

rust-dirstate-status: update bridge for new rust version of `dirstate.status` Differential Revision: https://phab.mercurial-scm.org/D7530
author Raphaël Gomès <rgomes@octobus.net>
date Fri, 29 Nov 2019 17:30:10 +0100
parents 8c77826116f7
children 06df075b8925
comparison
equal deleted inserted replaced
43915:8c77826116f7 43916:6a88ced33c40
10 //! `rustext.dirstate.status`. 10 //! `rustext.dirstate.status`.
11 11
12 use crate::dirstate::DirstateMap; 12 use crate::dirstate::DirstateMap;
13 use cpython::exc::ValueError; 13 use cpython::exc::ValueError;
14 use cpython::{ 14 use cpython::{
15 PyBytes, PyErr, PyList, PyObject, PyResult, Python, PythonObject, 15 ObjectProtocol, PyBytes, PyErr, PyList, PyObject, PyResult, PyTuple,
16 ToPyObject, 16 Python, PythonObject, ToPyObject,
17 }; 17 };
18 use hg::utils::files::get_path_from_bytes; 18 use hg::utils::hg_path::HgPathBuf;
19 19 use hg::{
20 use hg::matchers::AlwaysMatcher; 20 matchers::{AlwaysMatcher, FileMatcher},
21 use hg::status; 21 status,
22 use hg::utils::hg_path::HgPath; 22 utils::{files::get_path_from_bytes, hg_path::HgPath},
23 StatusResult,
24 };
25 use std::borrow::Borrow;
23 26
24 /// This will be useless once trait impls for collection are added to `PyBytes` 27 /// This will be useless once trait impls for collection are added to `PyBytes`
25 /// upstream. 28 /// upstream.
26 fn collect_pybytes_list<P: AsRef<HgPath>>( 29 fn collect_pybytes_list<P: AsRef<HgPath>>(
27 py: Python, 30 py: Python,
41 } 44 }
42 45
43 pub fn status_wrapper( 46 pub fn status_wrapper(
44 py: Python, 47 py: Python,
45 dmap: DirstateMap, 48 dmap: DirstateMap,
49 matcher: PyObject,
46 root_dir: PyObject, 50 root_dir: PyObject,
47 list_clean: bool, 51 list_clean: bool,
48 last_normal_time: i64, 52 last_normal_time: i64,
49 check_exec: bool, 53 check_exec: bool,
50 ) -> PyResult<(PyList, PyList, PyList, PyList, PyList, PyList, PyList)> { 54 ) -> PyResult<(PyList, PyList, PyList, PyList, PyList, PyList, PyList)> {
52 let root_dir = get_path_from_bytes(bytes.data(py)); 56 let root_dir = get_path_from_bytes(bytes.data(py));
53 57
54 let dmap: DirstateMap = dmap.to_py_object(py); 58 let dmap: DirstateMap = dmap.to_py_object(py);
55 let dmap = dmap.get_inner(py); 59 let dmap = dmap.get_inner(py);
56 60
57 // TODO removed in the next patch to get the code to compile. This patch 61 match matcher.get_type(py).name(py).borrow() {
58 // is part of a series and does not make real sense on its own. 62 "alwaysmatcher" => {
59 let matcher = AlwaysMatcher; 63 let matcher = AlwaysMatcher;
64 let (lookup, status_res) = status(
65 &dmap,
66 &matcher,
67 &root_dir,
68 list_clean,
69 last_normal_time,
70 check_exec,
71 )
72 .map_err(|e| PyErr::new::<ValueError, _>(py, e.to_string()))?;
73 build_response(lookup, status_res, py)
74 }
75 "exactmatcher" => {
76 let files = matcher.call_method(
77 py,
78 "files",
79 PyTuple::new(py, &[]),
80 None,
81 )?;
82 let files: PyList = files.cast_into(py)?;
83 let files: PyResult<Vec<HgPathBuf>> = files
84 .iter(py)
85 .map(|f| {
86 Ok(HgPathBuf::from_bytes(
87 f.extract::<PyBytes>(py)?.data(py),
88 ))
89 })
90 .collect();
60 91
61 let (lookup, status_res) = status( 92 let files = files?;
62 &dmap, 93 let matcher = FileMatcher::new(&files)
63 &matcher, 94 .map_err(|e| PyErr::new::<ValueError, _>(py, e.to_string()))?;
64 &root_dir, 95 let (lookup, status_res) = status(
65 list_clean, 96 &dmap,
66 last_normal_time, 97 &matcher,
67 check_exec, 98 &root_dir,
68 ) 99 list_clean,
69 .map_err(|e| PyErr::new::<ValueError, _>(py, e.to_string()))?; 100 last_normal_time,
101 check_exec,
102 )
103 .map_err(|e| PyErr::new::<ValueError, _>(py, e.to_string()))?;
104 build_response(lookup, status_res, py)
105 }
106 e => {
107 return Err(PyErr::new::<ValueError, _>(
108 py,
109 format!("Unsupported matcher {}", e),
110 ));
111 }
112 }
113 }
70 114
115 fn build_response(
116 lookup: Vec<&HgPath>,
117 status_res: StatusResult,
118 py: Python,
119 ) -> PyResult<(PyList, PyList, PyList, PyList, PyList, PyList, PyList)> {
71 let modified = collect_pybytes_list(py, status_res.modified.as_ref()); 120 let modified = collect_pybytes_list(py, status_res.modified.as_ref());
72 let added = collect_pybytes_list(py, status_res.added.as_ref()); 121 let added = collect_pybytes_list(py, status_res.added.as_ref());
73 let removed = collect_pybytes_list(py, status_res.removed.as_ref()); 122 let removed = collect_pybytes_list(py, status_res.removed.as_ref());
74 let deleted = collect_pybytes_list(py, status_res.deleted.as_ref()); 123 let deleted = collect_pybytes_list(py, status_res.deleted.as_ref());
75 let clean = collect_pybytes_list(py, status_res.clean.as_ref()); 124 let clean = collect_pybytes_list(py, status_res.clean.as_ref());