odin-union 0.1.0

Dependency-free shorthand for Rust enums whose variants wrap same-named types
Documentation
# odin-union

`odin-union` provides a dependency-free attribute macro for declaring Rust
enums whose variants contain same-named types.

Instead of repeating each type:

```rust
enum Thing {
    Person(Person),
    Animal(Animal),
}
```

write:

```rust
use odin_union::odin_union;

struct Person {
    name: String,
}

struct Animal {
    species: String,
}

#[odin_union]
enum Thing {
    Person,
    Animal,
}
```

The macro expands the declaration to the ordinary payload enum above. It also
generates `From<Person> for Thing` and `From<Animal> for Thing`, so values can
be wrapped with `.into()`:

```rust
# use odin_union::odin_union;
# struct Person { name: String }
# struct Animal { species: String }
# #[odin_union]
# enum Thing { Person, Animal }
let person = Person {
    name: "Ada".to_owned(),
};

let thing: Thing = person.into();

match thing {
    Thing::Person(person) => assert_eq!(person.name, "Ada"),
    Thing::Animal(_) => unreachable!(),
}
```

This is declaration shorthand, not a new runtime representation. The result is
a normal Rust enum: its tag and active payload are stored together, matching,
derives, visibility, and attributes continue to work normally, and no runtime
support library is involved.

## Rules

- Every listed variant must be a bare unit variant such as `Person`.
- A same-named type must be in scope at the enum declaration.
- The source enum cannot be generic. The macro cannot infer which generic
  arguments should be supplied to each same-named payload type.
- A variant-level `#[cfg(...)]` attribute is copied to the generated `From`
  implementation.
- Manually implementing the same `From<T>` conversion will conflict with the
  generated implementation.
- Rust does not perform implicit user-defined conversions. Use `.into()`,
  `Thing::from(value)`, or `Thing::Person(value)`.

The crate has no dependencies and supports Rust 1.85 or newer.