##// END OF EJS Templates
automation: correct the path separator in LIBPATH on Windows...
automation: correct the path separator in LIBPATH on Windows I haven't tried building the x86 installer, but happened to notice this when working on the thg installer. Experimenting in PowerShell seems to show that LIBPATH was expanded at the end, but with ':' between, it effectively corrupted `${root}\WinSDK\Lib` and the first path in LIBPATH. Differential Revision: https://phab.mercurial-scm.org/D6642

File last commit:

r42630:9609430d default
r42804:862f6bdd default
Show More
filepatterns.rs
110 lines | 3.7 KiB | application/rls-services+xml | RustLexer
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 // filepatterns.rs
//
// Copyright 2019, Georges Racinet <gracinet@anybox.fr>,
// Raphaël Gomès <rgomes@octobus.net>
//
// This software may be used and distributed according to the terms of the
// GNU General Public License version 2 or any later version.
//! Bindings for the `hg::filepatterns` module provided by the
//! `hg-core` crate. From Python, this will be seen as `rustext.filepatterns`
//! and can be used as replacement for the the pure `filepatterns` Python module.
//!
use cpython::{
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 PyBytes, PyDict, PyModule, PyObject, PyResult, PyTuple, Python, ToPyObject,
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 };
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 use exceptions::{PatternError, PatternFileError};
use hg::{build_single_regex, read_pattern_file, LineNumber, PatternTuple};
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515
/// Rust does not like functions with different return signatures.
/// The 3-tuple version is always returned by the hg-core function,
/// the (potential) conversion is handled at this level since it is not likely
/// to have any measurable impact on performance.
///
/// The Python implementation passes a function reference for `warn` instead
/// of a boolean that is used to emit warnings while parsing. The Rust
/// implementation chooses to accumulate the warnings and propagate them to
/// Python upon completion. See the `readpatternfile` function in `match.py`
/// for more details.
fn read_pattern_file_wrapper(
py: Python,
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 file_path: PyObject,
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 warn: bool,
source_info: bool,
) -> PyResult<PyTuple> {
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 match read_pattern_file(file_path.extract::<PyBytes>(py)?.data(py), warn) {
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 Ok((patterns, warnings)) => {
if source_info {
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 let itemgetter = |x: &PatternTuple| {
(PyBytes::new(py, &x.0), x.1, PyBytes::new(py, &x.2))
};
let results: Vec<(PyBytes, LineNumber, PyBytes)> =
patterns.iter().map(itemgetter).collect();
return Ok((results, warnings).to_py_object(py));
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 }
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 let itemgetter = |x: &PatternTuple| PyBytes::new(py, &x.0);
let results: Vec<PyBytes> =
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 patterns.iter().map(itemgetter).collect();
Ok((results, warnings).to_py_object(py))
}
Err(e) => Err(PatternFileError::pynew(py, e)),
}
}
fn build_single_regex_wrapper(
py: Python,
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 kind: PyObject,
pat: PyObject,
globsuffix: PyObject,
) -> PyResult<PyBytes> {
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 match build_single_regex(
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 kind.extract::<PyBytes>(py)?.data(py),
pat.extract::<PyBytes>(py)?.data(py),
globsuffix.extract::<PyBytes>(py)?.data(py),
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 ) {
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 Ok(regex) => Ok(PyBytes::new(py, &regex)),
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 Err(e) => Err(PatternError::pynew(py, e)),
}
}
pub fn init_module(py: Python, package: &str) -> PyResult<PyModule> {
let dotted_name = &format!("{}.filepatterns", package);
let m = PyModule::new(py, dotted_name)?;
m.add(py, "__package__", package)?;
m.add(
py,
"__doc__",
"Patterns files parsing - Rust implementation",
)?;
m.add(
py,
"build_single_regex",
py_fn!(
py,
build_single_regex_wrapper(
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 kind: PyObject,
pat: PyObject,
globsuffix: PyObject
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 )
),
)?;
m.add(
py,
"read_pattern_file",
py_fn!(
py,
read_pattern_file_wrapper(
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 file_path: PyObject,
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 warn: bool,
source_info: bool
)
),
)?;
Raphaël Gomès
rust-filepatterns: use bytes instead of String...
r42630 m.add(py, "PatternError", py.get_type::<PatternError>())?;
Raphaël Gomès
rust-filepatterns: add `rust-cpython` bindings for `filepatterns`...
r42515 let sys = PyModule::import(py, "sys")?;
let sys_modules: PyDict = sys.get(py, "modules")?.extract(py)?;
sys_modules.set_item(py, dotted_name, &m)?;
Ok(m)
}