annotate rust/hg-cpython/src/discovery.rs @ 50979:4c5f6e95df84

rust: make `Revision` a newtype This change is the one we've been building towards during this series. The aim is to make `Revision` mean more than a simple integer, holding the information that it is valid for a given revlog index. While this still allows for programmer error, since creating a revision directly and querying a different index with a "checked" revision are still possible, the friction created by the newtype will hopefully make us think twice about which type to use. Enough of the Rust ecosystem relies on the newtype pattern to be efficiently optimized away (even compiler in codegen testsĀ¹), so I'm not worried about this being a fundamental problem. [1] https://github.com/rust-lang/rust/blob/7a70647f195f6b0a0f1ebd72b1542ba91a32f43a/tests/codegen/vec-in-place.rs#L47
author Raphaël Gomès <rgomes@octobus.net>
date Fri, 18 Aug 2023 14:34:29 +0200
parents f98f0e3ddaa1
children a6e293b21743
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
1 // discovery.rs
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
2 //
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
3 // Copyright 2018 Georges Racinet <gracinet@anybox.fr>
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
4 //
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
5 // This software may be used and distributed according to the terms of the
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
6 // GNU General Public License version 2 or any later version.
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
7
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
8 //! Bindings for the `hg::discovery` module provided by the
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
9 //! `hg-core` crate. From Python, this will be seen as `rustext.discovery`
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
10 //!
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
11 //! # Classes visible from Python:
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
12 //! - [`PartialDiscover`] is the Rust implementation of
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
13 //! `mercurial.setdiscovery.partialdiscovery`.
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
14
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
15 use crate::PyRevision;
42609
326fdce22fb2 rust: switch hg-core and hg-cpython to rust 2018 edition
Raphaël Gomès <rgomes@octobus.net>
parents: 42332
diff changeset
16 use crate::{
43269
33fe96a5c522 rust-cpython: removed now useless py_set() conversion
Georges Racinet <georges.racinet@octobus.net>
parents: 42741
diff changeset
17 cindex::Index, conversion::rev_pyiter_collect, exceptions::GraphError,
42609
326fdce22fb2 rust: switch hg-core and hg-cpython to rust 2018 edition
Raphaël Gomès <rgomes@octobus.net>
parents: 42332
diff changeset
18 };
42180
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
19 use cpython::{
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
20 ObjectProtocol, PyClone, PyDict, PyModule, PyObject, PyResult, PyTuple,
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
21 Python, PythonObject, ToPyObject,
42180
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
22 };
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
23 use hg::discovery::PartialDiscovery as CorePartialDiscovery;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
24 use hg::Revision;
43269
33fe96a5c522 rust-cpython: removed now useless py_set() conversion
Georges Racinet <georges.racinet@octobus.net>
parents: 42741
diff changeset
25 use std::collections::HashSet;
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
26
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
27 use std::cell::RefCell;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
28
43945
f98f0e3ddaa1 rust-index: add a function to convert PyObject index for hg-core
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 43269
diff changeset
29 use crate::revlog::pyindex_to_graph;
f98f0e3ddaa1 rust-index: add a function to convert PyObject index for hg-core
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 43269
diff changeset
30
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
31 py_class!(pub class PartialDiscovery |py| {
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
32 data inner: RefCell<Box<CorePartialDiscovery<Index>>>;
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
33 data index: RefCell<Index>;
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
34
42735
5154701a5413 rust-discovery: accept the new 'respectsize' init arg
Georges Racinet <georges.racinet@octobus.net>
parents: 42609
diff changeset
35 // `_respectsize` is currently only here to replicate the Python API and
5154701a5413 rust-discovery: accept the new 'respectsize' init arg
Georges Racinet <georges.racinet@octobus.net>
parents: 42609
diff changeset
36 // will be used in future patches inside methods that are yet to be
5154701a5413 rust-discovery: accept the new 'respectsize' init arg
Georges Racinet <georges.racinet@octobus.net>
parents: 42609
diff changeset
37 // implemented.
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
38 def __new__(
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
39 _cls,
42736
b6f3f704a561 rust-discovery: read the index from a repo passed at init
Georges Racinet <georges.racinet@octobus.net>
parents: 42735
diff changeset
40 repo: PyObject,
42735
5154701a5413 rust-discovery: accept the new 'respectsize' init arg
Georges Racinet <georges.racinet@octobus.net>
parents: 42609
diff changeset
41 targetheads: PyObject,
42741
4e7bd6180b53 rust-discovery: optionally don't randomize at all, for tests
Georges Racinet <georges.racinet@octobus.net>
parents: 42740
diff changeset
42 respectsize: bool,
4e7bd6180b53 rust-discovery: optionally don't randomize at all, for tests
Georges Racinet <georges.racinet@octobus.net>
parents: 42740
diff changeset
43 randomize: bool = true
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
44 ) -> PyResult<PartialDiscovery> {
42736
b6f3f704a561 rust-discovery: read the index from a repo passed at init
Georges Racinet <georges.racinet@octobus.net>
parents: 42735
diff changeset
45 let index = repo.getattr(py, "changelog")?.getattr(py, "index")?;
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
46 let index = pyindex_to_graph(py, index)?;
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
47 let target_heads = rev_pyiter_collect(py, &targetheads, &index)?;
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
48 Self::create_instance(
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
49 py,
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
50 RefCell::new(Box::new(CorePartialDiscovery::new(
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
51 index.clone_ref(py),
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
52 target_heads,
42741
4e7bd6180b53 rust-discovery: optionally don't randomize at all, for tests
Georges Racinet <georges.racinet@octobus.net>
parents: 42740
diff changeset
53 respectsize,
4e7bd6180b53 rust-discovery: optionally don't randomize at all, for tests
Georges Racinet <georges.racinet@octobus.net>
parents: 42740
diff changeset
54 randomize,
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
55 ))),
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
56 RefCell::new(index),
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
57 )
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
58 }
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
59
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
60 def addcommons(&self, commons: PyObject) -> PyResult<PyObject> {
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
61 let index = self.index(py).borrow();
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
62 let commons_vec: Vec<_> = rev_pyiter_collect(py, &commons, &*index)?;
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
63 let mut inner = self.inner(py).borrow_mut();
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
64 inner.add_common_revisions(commons_vec)
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
65 .map_err(|e| GraphError::pynew(py, e))?;
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
66 Ok(py.None())
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
67 }
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
68
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
69 def addmissings(&self, missings: PyObject) -> PyResult<PyObject> {
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
70 let index = self.index(py).borrow();
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
71 let missings_vec: Vec<_> = rev_pyiter_collect(py, &missings, &*index)?;
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
72 let mut inner = self.inner(py).borrow_mut();
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
73 inner.add_missing_revisions(missings_vec)
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
74 .map_err(|e| GraphError::pynew(py, e))?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
75 Ok(py.None())
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
76 }
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
77
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
78 def addinfo(&self, sample: PyObject) -> PyResult<PyObject> {
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
79 let mut missing: Vec<Revision> = Vec::new();
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
80 let mut common: Vec<Revision> = Vec::new();
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
81 for info in sample.iter(py)? { // info is a pair (Revision, bool)
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
82 let mut revknown = info?.iter(py)?;
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
83 let rev: PyRevision = revknown.next().unwrap()?.extract(py)?;
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
84 // This is fine since we're just using revisions as integers
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
85 // for the purposes of discovery
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
86 let rev = Revision(rev.0);
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
87 let known: bool = revknown.next().unwrap()?.extract(py)?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
88 if known {
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
89 common.push(rev);
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
90 } else {
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
91 missing.push(rev);
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
92 }
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
93 }
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
94 let mut inner = self.inner(py).borrow_mut();
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
95 inner.add_common_revisions(common)
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
96 .map_err(|e| GraphError::pynew(py, e))?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
97 inner.add_missing_revisions(missing)
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
98 .map_err(|e| GraphError::pynew(py, e))?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
99 Ok(py.None())
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
100 }
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
101
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
102 def hasinfo(&self) -> PyResult<bool> {
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
103 Ok(self.inner(py).borrow().has_info())
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
104 }
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
105
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
106 def iscomplete(&self) -> PyResult<bool> {
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
107 Ok(self.inner(py).borrow().is_complete())
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
108 }
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
109
42180
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
110 def stats(&self) -> PyResult<PyDict> {
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
111 let stats = self.inner(py).borrow().stats();
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
112 let as_dict: PyDict = PyDict::new(py);
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
113 as_dict.set_item(py, "undecided",
42332
163b8fd7bb72 rust-python3: compatibility fix for integer conversion
Georges Racinet <georges.racinet@octobus.net>
parents: 42180
diff changeset
114 stats.undecided.map(
163b8fd7bb72 rust-python3: compatibility fix for integer conversion
Georges Racinet <georges.racinet@octobus.net>
parents: 42180
diff changeset
115 |l| l.to_py_object(py).into_object())
163b8fd7bb72 rust-python3: compatibility fix for integer conversion
Georges Racinet <georges.racinet@octobus.net>
parents: 42180
diff changeset
116 .unwrap_or_else(|| py.None()))?;
42180
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
117 Ok(as_dict)
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
118 }
1b0be75cb61f rust-discovery: implementing and exposing stats()
Georges Racinet <georges.racinet@octobus.net>
parents: 42179
diff changeset
119
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
120 def commonheads(&self) -> PyResult<HashSet<PyRevision>> {
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
121 let res = self.inner(py).borrow().common_heads()
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
122 .map_err(|e| GraphError::pynew(py, e))?;
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
123 Ok(res.into_iter().map(Into::into).collect())
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
124 }
42740
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
125
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
126 def takefullsample(&self, _headrevs: PyObject,
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
127 size: usize) -> PyResult<PyObject> {
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
128 let mut inner = self.inner(py).borrow_mut();
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
129 let sample = inner.take_full_sample(size)
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
130 .map_err(|e| GraphError::pynew(py, e))?;
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
131 let as_vec: Vec<PyObject> = sample
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
132 .iter()
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
133 .map(|rev| PyRevision(rev.0).to_py_object(py).into_object())
42740
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
134 .collect();
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
135 Ok(PyTuple::new(py, as_vec.as_slice()).into_object())
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
136 }
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
137
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
138 def takequicksample(&self, headrevs: PyObject,
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
139 size: usize) -> PyResult<PyObject> {
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
140 let index = self.index(py).borrow();
42740
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
141 let mut inner = self.inner(py).borrow_mut();
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
142 let revsvec: Vec<_> = rev_pyiter_collect(py, &headrevs, &*index)?;
42740
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
143 let sample = inner.take_quick_sample(revsvec, size)
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
144 .map_err(|e| GraphError::pynew(py, e))?;
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
145 let as_vec: Vec<PyObject> = sample
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
146 .iter()
50979
4c5f6e95df84 rust: make `Revision` a newtype
Raphaël Gomès <rgomes@octobus.net>
parents: 43945
diff changeset
147 .map(|rev| PyRevision(rev.0).to_py_object(py).into_object())
42740
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
148 .collect();
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
149 Ok(PyTuple::new(py, as_vec.as_slice()).into_object())
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
150 }
1c4b5689bef5 rust-discovery: exposing sampling to python
Georges Racinet <georges.racinet@octobus.net>
parents: 42738
diff changeset
151
42179
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
152 });
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
153
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
154 /// Create the module, with __package__ given from parent
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
155 pub fn init_module(py: Python, package: &str) -> PyResult<PyModule> {
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
156 let dotted_name = &format!("{}.discovery", package);
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
157 let m = PyModule::new(py, dotted_name)?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
158 m.add(py, "__package__", package)?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
159 m.add(
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
160 py,
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
161 "__doc__",
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
162 "Discovery of common node sets - Rust implementation",
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
163 )?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
164 m.add_class::<PartialDiscovery>(py)?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
165
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
166 let sys = PyModule::import(py, "sys")?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
167 let sys_modules: PyDict = sys.get(py, "modules")?.extract(py)?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
168 sys_modules.set_item(py, dotted_name, &m)?;
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
169 // Example C code (see pyexpat.c and import.c) will "give away the
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
170 // reference", but we won't because it will be consumed once the
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
171 // Rust PyObject is dropped.
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
172 Ok(m)
13b64247f48f rust-discovery: cpython bindings for the core logic
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
173 }