Change changelog, readme, examples, Cargo.toml for 0.12 release
This commit is contained in:
parent
1b92d3319c
commit
61236e685f
31
CHANGELOG.md
31
CHANGELOG.md
|
@ -1,3 +1,34 @@
|
|||
## [0.12.0]
|
||||
- Changed how userdata values are garbage collected, both to fix potential
|
||||
panics and to simplify it. Now, when userdata is garbage collected, it will
|
||||
be given a special "destructed userdata" metatable, and all interactions with
|
||||
it will error with `CallbackDestructed`. From the rust side, an expired
|
||||
userdata `AnyUserData` will not appear to be any rust type.
|
||||
- Changed the `RegistryKey` API to be more useful and general. Now, it is not
|
||||
100% necessary to manually drop `RegistryKey` instances in order to clean up
|
||||
the registry, instead you can periodically call `Lua::expire_registry_values`
|
||||
to remove registry values with `RegistryKey`s that have all been dropped.
|
||||
Also, it is no longer a panic to use a `RegistryKey` from a mismatched Lua
|
||||
instance, it is simply an error.
|
||||
- Lua is now `Send`, and all userdata / callback functions have a Send
|
||||
requirement. This is a potentially annoying breaking change, but there is a
|
||||
new way to pass !Send types to Lua in a limited way.
|
||||
- HUGE change, there is now a `Lua::scope` method, which allows passing
|
||||
non-'static functions to Lua in a controlled way. It also allows passing
|
||||
!Send functions and !Send userdata to Lua, with the same limitations. In
|
||||
order to make this safe, the scope method behaves similarly to the `crossbeam`
|
||||
crate's `crossbeam::scope` method, which ensures that types created within the
|
||||
scope are destructed at the end of the scope. When using callbacks / userdata
|
||||
created within the scope, the callbakcs / userdata are guaranteed to be
|
||||
destructed at the end of the scope, and inside Lua references to them are in
|
||||
an invalidated "destructed" state. This destructed state was already possible
|
||||
to observe through `__gc` methods, so it doesn't introduce anything new, but
|
||||
it has been fixed so that it cannot cause panics, and has a specific error
|
||||
type.
|
||||
- Correctly error on passing too many arguments to an `rlua::Function`, and
|
||||
correctly error when returning too many results from a callback. Previously,
|
||||
this was a panic.
|
||||
|
||||
## [0.11.0]
|
||||
- `rlua::Error` now implements `failure::Fail` and not `std::error::Error`, and
|
||||
external errors now require `failure::Fail`. This is the only API
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
[package]
|
||||
name = "rlua"
|
||||
version = "0.11.0"
|
||||
version = "0.12.0"
|
||||
authors = ["kyren <catherine@chucklefish.org>"]
|
||||
description = "High level bindings to Lua 5.3"
|
||||
repository = "https://github.com/chucklefish/rlua"
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
# rlua -- High level bindings between Rust and Lua
|
||||
|
||||
[![Build Status](https://travis-ci.org/chucklefish/rlua.svg?branch=master)](https://travis-ci.org/chucklefish/rlua)
|
||||
[![Latest Version](https://img.shields.io/crates/v/rlua.svg)](https://crates.io/crates/rlua)
|
||||
[![API Documentation](https://docs.rs/rlua/badge.svg)](https://docs.rs/rlua)
|
||||
|
||||
[API Documentation](https://docs.rs/rlua)
|
||||
|
||||
[Examples](examples/examples.rs)
|
||||
[Guided Tour](examples/guided_tour.rs)
|
||||
|
||||
This library is a high level interface between Rust and Lua. Its major goal is
|
||||
to expose as easy to use, practical, and flexible of an API between Rust and Lua
|
||||
|
|
|
@ -1,20 +1,20 @@
|
|||
extern crate rlua;
|
||||
|
||||
use std::f32;
|
||||
use std::iter::FromIterator;
|
||||
|
||||
use rlua::{Function, Lua, MetaMethod, Result, UserData, UserDataMethods, Variadic};
|
||||
|
||||
fn examples() -> Result<()> {
|
||||
// Create a Lua context with Lua::new(). Eventually, this will allow
|
||||
// further control on the lua std library, and will specifically allow
|
||||
// limiting Lua to a subset of "safe" functionality.
|
||||
fn guided_tour() -> Result<()> {
|
||||
// Create a Lua context with `Lua::new()`. Eventually, this will allow further control on the
|
||||
// lua std library, and will specifically allow limiting Lua to a subset of "safe"
|
||||
// functionality.
|
||||
|
||||
let lua = Lua::new();
|
||||
|
||||
// You can get and set global variables. Notice that the globals table here
|
||||
// is a permanent reference to _G, and it is mutated behind the scenes as
|
||||
// lua code is loaded. This API is based heavily around internal mutation
|
||||
// (just like lua itself).
|
||||
// You can get and set global variables. Notice that the globals table here is a permanent
|
||||
// reference to _G, and it is mutated behind the scenes as lua code is loaded. This API is
|
||||
// based heavily around internal mutation (just like lua itself).
|
||||
|
||||
let globals = lua.globals();
|
||||
|
||||
|
@ -24,8 +24,8 @@ fn examples() -> Result<()> {
|
|||
assert_eq!(globals.get::<_, String>("string_var")?, "hello");
|
||||
assert_eq!(globals.get::<_, i64>("int_var")?, 42);
|
||||
|
||||
// You can load and evaluate lua code. The second parameter here gives the
|
||||
// chunk a better name when lua error messages are printed.
|
||||
// You can load and evaluate lua code. The second parameter here gives the chunk a better name
|
||||
// when lua error messages are printed.
|
||||
|
||||
lua.exec::<()>(
|
||||
r#"
|
||||
|
@ -54,7 +54,7 @@ fn examples() -> Result<()> {
|
|||
let v: i64 = map_table.get("two")?;
|
||||
assert_eq!(v, 2);
|
||||
|
||||
// You can pass values like Table back into Lua
|
||||
// You can pass values like `Table` back into Lua
|
||||
|
||||
globals.set("array_table", array_table)?;
|
||||
globals.set("map_table", map_table)?;
|
||||
|
@ -77,18 +77,25 @@ fn examples() -> Result<()> {
|
|||
let print: Function = globals.get("print")?;
|
||||
print.call::<_, ()>("hello from rust")?;
|
||||
|
||||
// This API handles variadics using tuples. This is one way to call a function with multiple
|
||||
// parameters:
|
||||
// This API generally handles variadics using tuples. This is one way to call a function with
|
||||
// multiple parameters:
|
||||
|
||||
print.call::<_, ()>(("hello", "again", "from", "rust"))?;
|
||||
|
||||
// You can bind rust functions to lua as well. Callbacks receive the lua state itself as their
|
||||
// But, you can also pass variadic arguments with the `Variadic` type.
|
||||
|
||||
print.call::<_, ()>(Variadic::from_iter(
|
||||
["hello", "yet", "again", "from", "rust"].iter().cloned(),
|
||||
))?;
|
||||
|
||||
// You can bind rust functions to lua as well. Callbacks receive the Lua state itself as their
|
||||
// first parameter, and the arguments given to the function as the second parameter. The type
|
||||
// of the arguments can be anything that is convertible from the set of parameters, in this
|
||||
// case, the function expects two string sequences.
|
||||
// of the arguments can be anything that is convertible from the parameters given by Lua, in
|
||||
// this case, the function expects two string sequences.
|
||||
|
||||
let check_equal = lua.create_function(|_, (list1, list2): (Vec<String>, Vec<String>)| {
|
||||
// This function just checks whether two string lists are equal, and in an inefficient way.
|
||||
// Lua callbacks return rlua::Result, an Ok value is a normal return, and an Err return
|
||||
// Lua callbacks return `rlua::Result`, an Ok value is a normal return, and an Err return
|
||||
// turns into a Lua 'error'. Again, any type that is convertible to lua may be returned.
|
||||
Ok(list1 == list2)
|
||||
})?;
|
||||
|
@ -137,9 +144,39 @@ fn examples() -> Result<()> {
|
|||
|
||||
assert!(lua.eval::<f32>("(vec2(1, 2) + vec2(2, 2)):magnitude()", None)? - 5.0 < f32::EPSILON);
|
||||
|
||||
// Normally, Rust types passed to `Lua` must be `Send`, because `Lua` itself is `Send`, and must
|
||||
// be `'static`, because there is no way to tell when Lua might garbage collect them. There is,
|
||||
// however, a limited way to lift both of these restrictions. You can call `Lua::scope` to
|
||||
// create userdata types that do not have to be `Send`, and callback types that do not have to
|
||||
// be `Send` OR `'static`.
|
||||
|
||||
let mut rust_val = 0;
|
||||
|
||||
lua.scope(|scope| {
|
||||
// We create a 'sketchy' lua callback that modifies the variable `rust_val`. Outside of a
|
||||
// `Lua::scope` call, this would not be allowed.
|
||||
|
||||
lua.globals().set(
|
||||
"sketchy",
|
||||
scope.create_function_mut(|_, ()| {
|
||||
rust_val = 42;
|
||||
Ok(())
|
||||
})?,
|
||||
)?;
|
||||
|
||||
lua.eval::<()>("sketchy()", None)
|
||||
})?;
|
||||
|
||||
// We were able to run our 'sketchy' function inside the scope just fine. However, if we try to
|
||||
// run our 'sketchy' function outside of the scope, the function we created will have been
|
||||
// destroyed and we will generate an error.
|
||||
|
||||
assert_eq!(rust_val, 42);
|
||||
assert!(lua.eval::<()>("sketchy()", None).is_err());
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn main() {
|
||||
examples().unwrap();
|
||||
guided_tour().unwrap();
|
||||
}
|
Loading…
Reference in New Issue