Skip to content
forked from PyO3/pyo3

Rust bindings for the Python interpreter

License

Notifications You must be signed in to change notification settings

nev3rfail/pyo3-py2

 
 

Repository files navigation

PyO3-py2

Sometimes systems have a proprietary legacy that is not possible to port to newer versions of languages. But people still need to work, systems using python 2 still have to be written.

This project is a fork of an old version of pyo3 that supported python2, with some patches to please newer Rust compilers.

⚠ WARNING

  1. DO NOT use python 2 in 2025
  2. Really, DO NOT use python 2 in 2025
  3. Use this project only as a last resort
  4. ???
  5. Rewrite everything to support modern languages.

Usage

I doubt I ever publish it to crates, so you just need to use git directly:

[dependencies]
pyo3 = { git = "git@github.com:nev3rfail/pyo3-py2.git", branch = "py2", features = ["python2"] }

Features

Currently only the code under the python2 feature flag has been modified to compile, so patches are welcome. For now i'm just patching whatever I personally need and not touching the other parts of the codebase, but it is theoretically possible to backport this into relevant versions of pyo3, or maybe even glue py2 support as a library.

Original README: PyO3

Build Status Build Status crates.io Join the dev chat

Rust bindings for Python. This includes running and interacting with python code from a rust binaries as well as writing native python modules.

A comparison with rust-cpython can be found in the guide.

Usage

Pyo3 supports python 2.7 as well as python 3.5 and up. The minimum required rust version is 1.30.0-nightly 2018-08-18.

You can either write a native python module in rust or use python from a rust binary.

Using rust from python

Pyo3 can be used to generate a native python module.

Cargo.toml:

[package]
name = "string-sum"
version = "0.1.0"

[lib]
name = "string_sum"
crate-type = ["cdylib"]

[dependencies.pyo3]
version = "0.4"
features = ["extension-module"]

src/lib.rs

#![feature(specialization)]

#[macro_use]
extern crate pyo3;

use pyo3::prelude::*;

#[pyfunction]
/// Formats the sum of two numbers as string
fn sum_as_string(a: usize, b: usize) -> PyResult<String> {
    Ok((a + b).to_string())
}

/// This module is a python module implemented in Rust.
#[pymodinit]
fn string_sum(py: Python, m: &PyModule) -> PyResult<()> {
    m.add_function(wrap_function!(sum_as_string))?;

    Ok(())
}

On windows and linux, you can build normally with cargo build --release. On macOS, you need to set additional linker arguments. One option is to compile with cargo rustc --release -- -C link-arg=-undefined -C link-arg=dynamic_lookup, the other is to create a .cargo/config with the following content:

[target.x86_64-apple-darwin]
rustflags = [
  "-C", "link-arg=-undefined",
  "-C", "link-arg=dynamic_lookup",
]

For developing, you can copy and rename the shared library from the target folder: On macOS, rename libstring_sum.dylib to string_sum.so, on windows libstring_sum.dll to string_sum.pyd and on linux libstring_sum.so to libstring_sum.so. Then open a python shell in the same folder and you'll be able to import string_sum.

To build, test and publish your crate as python module, you can use pyo3-pack or setuptools-rust. You can find an example for setuptools-rust in examples/word-count, while pyo3-pack should work on your crate without any configuration.

Using python from rust

Add pyo3 this to your Cargo.toml:

[dependencies]
pyo3 = "0.4"

Example program displaying the value of sys.version:

#![feature(specialization)]

extern crate pyo3;

use pyo3::prelude::*;
use pyo3::types::PyDict;

fn main() -> PyResult<()> {
    let gil = Python::acquire_gil();
    let py = gil.python();
    let sys = py.import("sys")?;
    let version: String = sys.get("version")?.extract()?;

    let locals = PyDict::new(py);
    locals.set_item("os", py.import("os")?)?;
    let user: String = py.eval("os.getenv('USER') or os.getenv('USERNAME')", None, Some(&locals))?.extract()?;

    println!("Hello {}, I'm Python {}", user, version);
    Ok(())
}

Examples and tooling

License

PyO3 is licensed under the Apache-2.0 license. Python is licensed under the Python License.

About

Rust bindings for the Python interpreter

Resources

License

Stars

Watchers

Forks

Packages

No packages published

Languages

  • Rust 99.5%
  • Other 0.5%