You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Yew中use_state使用报错求助:类型不匹配问题排查

解决Yew组件中use_state的类型不匹配及代码问题

核心错误原因

  • use_state声明语法错误:你在let (books: ...中多写了一个左括号,use_state返回的是单个UseStateHandle实例,而非元组,多余的括号让编译器误以为你在声明元组,从而抛出“期望结构体UseStateHandle,却找到元组”的错误。
  • 结构体定义不完整:struct BookList末尾缺少分号,且若要从API响应解析JSON,需派生serde::Deserialize trait并补充字段。
  • 异步请求写法错误:Request::get仅创建请求实例,需调用.send().await发送;解析数据要用.json().await而非response.data;异步函数需通过use_effect_with_deps触发执行,且要捕获外部变量并处理错误。
  • 语法细节错误:cloned_books = books.clone():末尾的冒号应改为分号。

修正后的完整代码

// 需在Cargo.toml添加serde依赖:serde = { version = "1.0", features = ["derive"] }
use gloo_net::http::Request;
use serde::Deserialize;
use yew::prelude::*;

// 补充分结构体定义,派生Deserialize用于JSON解析
#[derive(Debug, Deserialize, Clone)]
struct BookList {
    // 根据API返回的实际字段调整,示例为id和标题
    id: u32,
    title: String,
}

#[function_component(App)]
pub fn app() -> Html {
    // 移除多余括号,正确声明use_state
    let books = use_state(|| vec![]);

    // 使用use_effect_with_deps在组件挂载时触发异步请求
    {
        let books = books.clone();
        use_effect_with_deps(move |_| {
            let fetch_task = async move {
                // 发送请求并处理响应
                match Request::get("http://localhost:3000/books")
                    .send()
                    .await
                {
                    Ok(response) => {
                        match response.json::<Vec<BookList>>().await {
                            Ok(fetched_books) => books.set(fetched_books),
                            Err(e) => log::error!("解析JSON失败: {}", e),
                        }
                    }
                    Err(e) => log::error!("请求失败: {}", e),
                }
            };

            // 启动异步任务,返回空清理函数
            wasm_bindgen_futures::spawn_local(fetch_task);
            || ()
        }, ());
    }

    html! {
        <div>
            <h1>{"书籍列表"}</h1>
            <ul>
                {
                    books.iter().map(|book| {
                        html! {
                            <li key={book.id}>{"标题: "}{&book.title}</li>
                        }
                    }).collect::<Html>()
                }
            </ul>
        </div>
    }
}

额外注意事项

  • 需在Cargo.toml中补充依赖:
    [dependencies]
    yew = "0.20"
    gloo-net = "0.2"
    serde = { version = "1.0", features = ["derive"] }
    wasm-bindgen-futures = "0.4"
    log = "0.4"
    
  • 若API返回字段与BookList字段名不匹配,可使用#[serde(rename = "api_field_name")]属性做映射。

内容的提问来源于stack exchange,提问作者Daniel

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.07 22:00:23