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

如何正确处理Result错误并打印?Rust数据库连接编译报错求助

解决tokio_postgres连接时的match类型不兼容问题

编译器报错的核心原因是match表达式的所有分支必须返回相同类型:你的Ok分支返回了(Client, Connection<Socket, NoTlsStream>)元组,但Err分支仅打印错误后默认返回空单元类型(),两者类型不匹配,导致编译失败。

你可以通过以下几种常见方式修复:

方式1:错误时退出程序

在Err分支中调用std::process::exit(1)终止程序,该函数属于发散类型(不会返回值),可以和任何类型兼容:

use tokio_postgres::{NoTls, Error};
use tokio;

#[tokio::main]
async fn main() {
    let connection_result = tokio_postgres::connect(
        "host=localhost user=postgres password=123456 dbname=postgres",
        NoTls,
    ).await;

    let (client, connection) = match connection_result {
        Ok(conn) => conn,
        Err(e) => {
            eprintln!("连接错误: {}", e);
            std::process::exit(1);
        }
    };

    // 后台运行连接任务
    tokio::spawn(async move {
        if let Err(e) = connection.await {
            eprintln!("连接运行错误: {}", e);
        }
    });

    let query_result = client.query("select * from mock_data", &[]).await;

    let rows = match query_result {
        Ok(rows) => rows,
        Err(e) => {
            eprintln!("查询错误: {}", e);
            std::process::exit(1);
        }
    };

    for row in rows {
        println!("{:#?}", row.get::<usize, String>(0));
    }
}

方式2:将后续逻辑包裹在Ok分支内

如果不想直接退出程序,可以把依赖client和connection的代码放到Ok分支的代码块中,避免类型不匹配:

use tokio_postgres::{NoTls, Error};
use tokio;

#[tokio::main]
async fn main() {
    let connection_result = tokio_postgres::connect(
        "host=localhost user=postgres password=123456 dbname=postgres",
        NoTls,
    ).await;

    if let Ok((client, connection)) = connection_result {
        // 后台运行连接任务
        tokio::spawn(async move {
            if let Err(e) = connection.await {
                eprintln!("连接运行错误: {}", e);
            }
        });

        let query_result = client.query("select * from mock_data", &[]).await;

        let rows = match query_result {
            Ok(rows) => rows,
            Err(e) => {
                eprintln!("查询错误: {}", e);
                return;
            }
        };

        for row in rows {
            println!("{:#?}", row.get::<usize, String>(0));
        }
    } else if let Err(e) = connection_result {
        eprintln!("连接错误: {}", e);
    }
}

方式3:用?操作符简化错误处理

如果你的main函数返回Result<(), Error>,可以用?操作符自动向上传递错误,让代码更简洁:

use tokio_postgres::{NoTls, Error};
use tokio;

#[tokio::main]
async fn main() -> Result<(), Error> {
    let (client, connection) = tokio_postgres::connect(
        "host=localhost user=postgres password=123456 dbname=postgres",
        NoTls,
    ).await?;

    tokio::spawn(async move {
        if let Err(e) = connection.await {
            eprintln!("连接运行错误: {}", e);
        }
    });

    let rows = client.query("select * from mock_data", &[]).await?;

    for row in rows {
        println!("{:#?}", row.get::<usize, String>(0));
    }

    Ok(())
}

这种方式下,任何错误会自动返回并由Rust运行时打印,无需手动编写match分支处理错误。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.10 11:52:25