mirror of
https://github.com/DioxusLabs/dioxus
synced 2024-11-23 04:33:06 +00:00
ac3e33af46
* clean up logging to avoid random extra trace * fix race condition with updates * properly wire up verbose * fix bundling (macos) and logging * Add structured output * clean up clap names * extract out wire format * switch structured key to json * fix random println, fallback to `dioxus/platform` * clean up logging for run/build * clean up logging around project * remove manual exits * fix tokio runtime for mobile * rework dog app * rip out ssg * Switch dioxus/axum to dioxus/server * add android template inline * pre restructure for bundle prep * add the whole res directory * Better theme for the app * remove mobile demo now that most apps work natively * self-referential android * only use deep linking for assets * fix imports for android * clippy, fixup ios and android * I'm not boxing compiler message you can't make me * fix clippy on unix
223 lines
7.5 KiB
Markdown
223 lines
7.5 KiB
Markdown
# Dioxus Fullstack
|
|
|
|
[![Crates.io][crates-badge]][crates-url]
|
|
[![MIT licensed][mit-badge]][mit-url]
|
|
[![Build Status][actions-badge]][actions-url]
|
|
[![Discord chat][discord-badge]][discord-url]
|
|
|
|
[crates-badge]: https://img.shields.io/crates/v/dioxus-fullstack.svg
|
|
[crates-url]: https://crates.io/crates/dioxus-fullstack
|
|
[mit-badge]: https://img.shields.io/badge/license-MIT-blue.svg
|
|
[mit-url]: https://github.com/dioxuslabs/dioxus/blob/main/LICENSE-MIT
|
|
[actions-badge]: https://github.com/dioxuslabs/dioxus/actions/workflows/main.yml/badge.svg
|
|
[actions-url]: https://github.com/dioxuslabs/dioxus/actions?query=workflow%3ACI+branch%3Amaster
|
|
[discord-badge]: https://img.shields.io/discord/899851952891002890.svg?logo=discord&style=flat-square
|
|
[discord-url]: https://discord.gg/XgGxMSkvUM
|
|
|
|
[Website](https://dioxuslabs.com) |
|
|
[Guides](https://dioxuslabs.com/learn/0.5/) |
|
|
[API Docs](https://docs.rs/dioxus-fullstack/latest/dioxus_fullstack/) |
|
|
[Chat](https://discord.gg/XgGxMSkvUM)
|
|
|
|
Fullstack utilities for the [`Dioxus`](https://dioxuslabs.com) framework.
|
|
|
|
# Features
|
|
|
|
- Integrates with the [Axum](./examples/axum-hello-world/src/main.rs) server framework with utilities for serving and rendering Dioxus applications.
|
|
- [Server functions](https://docs.rs/dioxus-fullstack/latest/dioxus_fullstack/prelude/attr.server.html) allow you to call code on the server from the client as if it were a normal function.
|
|
- Instant RSX Hot reloading with [`dioxus-hot-reload`](https://crates.io/crates/dioxus-hot-reload).
|
|
- Passing root props from the server to the client.
|
|
|
|
# Example
|
|
|
|
Full stack Dioxus in under 30 lines of code
|
|
|
|
```rust, no_run
|
|
#![allow(non_snake_case)]
|
|
use dioxus::prelude::*;
|
|
|
|
fn main() {
|
|
dioxus::launch(App);
|
|
}
|
|
|
|
#[component]
|
|
fn App() -> Element {
|
|
let mut meaning = use_signal(|| None);
|
|
|
|
rsx! {
|
|
h1 { "Meaning of life: {meaning:?}" }
|
|
button {
|
|
onclick: move |_| async move {
|
|
if let Ok(data) = get_meaning("life the universe and everything".into()).await {
|
|
meaning.set(data);
|
|
}
|
|
},
|
|
"Run a server function"
|
|
}
|
|
}
|
|
}
|
|
|
|
#[server]
|
|
async fn get_meaning(of: String) -> Result<Option<u32>, ServerFnError> {
|
|
Ok(of.contains("life").then(|| 42))
|
|
}
|
|
```
|
|
|
|
## Axum Integration
|
|
|
|
If you have an existing Axum router or you need more control over the server, you can use the [`DioxusRouterExt`](https://docs.rs/dioxus-fullstack/0.6.0-alpha.2/dioxus_fullstack/prelude/trait.DioxusRouterExt.html) trait to integrate with your existing Axum router.
|
|
|
|
First, make sure your `axum` dependency is optional and enabled by the server feature flag. Axum cannot be compiled to wasm, so if it is enabled by default, it will cause a compile error:
|
|
|
|
```toml
|
|
[dependencies]
|
|
dioxus = { version = "*", features = ["fullstack"] }
|
|
axum = { version = "0.7.0", optional = true }
|
|
|
|
[features]
|
|
server = ["dioxus/server", "dep:axum"]
|
|
web = ["dioxus/web"]
|
|
```
|
|
|
|
Then we can set up dioxus with the axum server:
|
|
|
|
```rust, no_run
|
|
#![allow(non_snake_case)]
|
|
use dioxus::prelude::*;
|
|
|
|
// The entry point for the server
|
|
#[cfg(feature = "server")]
|
|
fn main() {
|
|
// Get the address the server should run on. If the CLI is running, the CLI proxies fullstack into the main address
|
|
// and we use the generated address the CLI gives us
|
|
let address = dioxus_cli_config::fullstack_address_or_localhost();
|
|
|
|
// Set up the axum router
|
|
let router = axum::Router::new()
|
|
// You can add a dioxus application to the router with the `serve_dioxus_application` method
|
|
// This will add a fallback route to the router that will serve your component and server functions
|
|
.serve_dioxus_application(ServeConfigBuilder::default(), App);
|
|
|
|
// Finally, we can launch the server
|
|
let router = router.into_make_service();
|
|
let listener = tokio::net::TcpListener::bind(address).await.unwrap();
|
|
axum::serve(listener, router).await.unwrap();
|
|
}
|
|
|
|
// For any other platform, we just launch the app
|
|
#[cfg(not(feature = "server"))]
|
|
fn main() {
|
|
dioxus::launch(App);
|
|
}
|
|
|
|
#[component]
|
|
fn App() -> Element {
|
|
let mut meaning = use_signal(|| None);
|
|
|
|
rsx! {
|
|
h1 { "Meaning of life: {meaning:?}" }
|
|
button {
|
|
onclick: move |_| async move {
|
|
if let Ok(data) = get_meaning("life the universe and everything".into()).await {
|
|
meaning.set(data);
|
|
}
|
|
},
|
|
"Run a server function"
|
|
}
|
|
}
|
|
}
|
|
|
|
#[server]
|
|
async fn get_meaning(of: String) -> Result<Option<u32>, ServerFnError> {
|
|
Ok(of.contains("life").then(|| 42))
|
|
}
|
|
```
|
|
|
|
## Axum Integration
|
|
|
|
If you have an existing Axum router or you need more control over the server, you can use the [`DioxusRouterExt`](https://docs.rs/dioxus-fullstack/0.6.0-alpha.2/dioxus_fullstack/prelude/trait.DioxusRouterExt.html) trait to integrate with your existing Axum router.
|
|
|
|
First, make sure your `axum` dependency is optional and enabled by the server feature flag. Axum cannot be compiled to wasm, so if it is enabled by default, it will cause a compile error:
|
|
|
|
```toml
|
|
[dependencies]
|
|
dioxus = { version = "*", features = ["fullstack"] }
|
|
axum = { version = "0.7.0", optional = true }
|
|
|
|
[features]
|
|
server = ["dioxus/server", "dep:axum"]
|
|
web = ["dioxus/web"]
|
|
```
|
|
|
|
Then we can set up dioxus with the axum server:
|
|
|
|
```rust, no_run
|
|
#![allow(non_snake_case)]
|
|
use dioxus::prelude::*;
|
|
|
|
// The entry point for the server
|
|
#[cfg(feature = "server")]
|
|
fn main() {
|
|
// Get the address the server should run on. If the CLI is running, the CLI proxies fullstack into the main address
|
|
// and we use the generated address the CLI gives us
|
|
let address = dioxus_cli_config::fullstack_address_or_localhost();
|
|
|
|
// Set up the axum router
|
|
let router = axum::Router::new()
|
|
// You can add a dioxus application to the router with the `serve_dioxus_application` method
|
|
// This will add a fallback route to the router that will serve your component and server functions
|
|
.serve_dioxus_application(ServeConfigBuilder::default(), App);
|
|
|
|
// Finally, we can launch the server
|
|
let router = router.into_make_service();
|
|
let listener = tokio::net::TcpListener::bind(address).await.unwrap();
|
|
axum::serve(listener, router).await.unwrap();
|
|
}
|
|
|
|
// For any other platform, we just launch the app
|
|
#[cfg(not(feature = "server"))]
|
|
fn main() {
|
|
dioxus::launch(App);
|
|
}
|
|
|
|
#[component]
|
|
fn App() -> Element {
|
|
let mut meaning = use_signal(|| None);
|
|
|
|
rsx! {
|
|
h1 { "Meaning of life: {meaning:?}" }
|
|
button {
|
|
onclick: move |_| async move {
|
|
if let Ok(data) = get_meaning("life the universe and everything".into()).await {
|
|
meaning.set(data);
|
|
}
|
|
},
|
|
"Run a server function"
|
|
}
|
|
}
|
|
}
|
|
|
|
#[server]
|
|
async fn get_meaning(of: String) -> Result<Option<u32>, ServerFnError> {
|
|
Ok(of.contains("life").then(|| 42))
|
|
}
|
|
```
|
|
|
|
## Getting Started
|
|
|
|
To get started with full stack Dioxus, check out our [getting started guide](https://dioxuslabs.com/learn/0.5/getting_started), or the [full stack examples](https://github.com/DioxusLabs/dioxus/tree/master/examples).
|
|
|
|
## Contributing
|
|
|
|
- Report issues on our [issue tracker](https://github.com/dioxuslabs/dioxus/issues).
|
|
- Join the discord and ask questions!
|
|
|
|
## License
|
|
|
|
This project is licensed under the [MIT license].
|
|
|
|
[mit license]: https://github.com/dioxuslabs/dioxus/blob/main/LICENSE-MIT
|
|
|
|
Unless you explicitly state otherwise, any contribution intentionally submitted
|
|
for inclusion in Dioxus by you shall be licensed as MIT without any additional
|
|
terms or conditions.
|