应用接口抽象

Zino框架的应用接口抽象由Application trait定义,它包含一个关联类型和两个必须实现的方法:

  1. pub trait Application {
  2. type Routes;
  3. fn register(self, routes: Self::Routes) -> Self;
  4. fn run_with<T: AsyncScheduler + Send + 'static>(self, scheduler: T);
  5. }

其中register用来注册路由,run_with用来加载异步任务并运行应用。 需要注意的是,异步任务的执行涉及到异步运行时的选择, 而zino-core本身并没有限定只能使用特定的运行时^runtime, 所以需要实现者自行在run_with方法的实现中指定。对于同步任务,不涉及到异步运行时的选择, 我们就在Applicationspawn方法中提供了默认实现。

这就是Zino框架的起点!我们只要给其他Web框架实现这个trait,就能把这个框架的功能集成到Zino中,并使应用的启动方式保存一致:

  1. mod router;
  2. mod schedule;
  3. use zino::prelude::*;
  4. fn main() {
  5. zino::Cluster::boot()
  6. .register(router::routes())
  7. .register_debug(router::debug_routes())
  8. .spawn(schedule::job_scheduler())
  9. .run_with(schedule::async_job_scheduler())
  10. }

目前我们已经为actix-webaxumdioxus-desktop实现了Application trait, 它们对应的关联类型Routes分别为:

  • actix-web:引入ActixCluster类型,基于ServiceConfig来定义路由。

    1. pub type RouterConfigure = fn(cfg: &mut actix_web::web::ServiceConfig);
    2. impl Application for ActixCluster {
    3. type Routes = Vec<RouterConfigure>;
    4. }
  • axum:引入AxumCluster类型,基于Router来定义路由。

    1. impl Application for AxumCluster {
    2. type Routes = Vec<axum::Router>;
    3. }
  • dioxus-desktop:引入DioxusDesktop<R>类型,基于Routable泛型约束来定义路由。

    1. impl Application for DioxusDesktop<R>
    2. where
    3. R: dioxus_router::routable::Routable,
    4. <R as FromStr>::Err: Display,
    5. {
    6. type Routes = R;
    7. }

可以看到,在以上框架的Application实现中,我们并没有定义自己的路由类型, 这就使得actix-webaxum中的路由、中间件可以直接在我们的Zino框架中使用。 确保充分理解了这一点,对我们的应用开发至关重要。