Swift 之 Vapor4 前瞻

1,250 阅读2分钟

Vapor 是 Swift 在服务器端最受欢迎的 web 框架。 现在 Vapor4 还未 release,截止 10/23 日,最新版本:

Vapor 4.0.0 Alpha 3.2

Vapor4 的变化主要源于底层技术的更新:

  • Swift 5.1 的新特性
  • SwiftNIO v2 and HTTP2 support
  • SwiftLog,苹果发布的日志框架
  • ...

Vapor4 中包含以下更新:

Vapor
* services on controllers
* synchronous content decoding
* upload / download streaming
* backpressure
* http/2
* extensible route builder (for openapi)
* apple logging
* improved session syntax
* dotenv support
* validation included
* authentication included
* XCTVapor testing module
* swift server http client
* simplified websocket endpoints
* graceful shutdown
* nio 2

ConsoleKit
* type safe signatures

RoutingKit
* performance improvements
* performance testing bot

Fluent
* dynamic models
* simplified driver requirements
* eager loading: join + subquery
* partial selects
* dirty updates

LeafKit
* improved body syntax
* separate lexer + parser

Toolbox
* dynamic project init

///
....

Fluent

Fluent 的更新会是一个重头戏。

Controllers 将会持有数据库对象,我们操作这个对象直接操作数据库,不需要从 Request 对象中获取。不再用 FutureSwiftNIOEventLoopFuture 作为别称。

// Vapor 3

import Vapor

/// Controls basic CRUD operations on `Todo`s.
final class TodoController {
    /// Returns a list of all `Todo`s.
    func index(_ req: Request) throws -> Future<[Todo]> {
        return Todo.query(on: req).all()
    }

    /// Saves a decoded `Todo` to the database.
    func create(_ req: Request) throws -> Future<Todo> {
        return try req.content.decode(Todo.self).flatMap { todo in
            return todo.save(on: req)
        }
    }

    /// Deletes a parameterized `Todo`.
    func delete(_ req: Request) throws -> Future<HTTPStatus> {
        return try req.parameters.next(Todo.self).flatMap { todo in
            return todo.delete(on: req)
        }.transform(to: .ok)
    }
}

// Vapor 4
import Fluent
import Vapor

final class TodoController {
    let db: Database

    init(db: Database) {
        self.db = db
    }

    func index(req: Request) throws -> EventLoopFuture<[Todo]> {
        return Todo.query(on: self.db).all()
    }

    func create(req: Request) throws -> EventLoopFuture<Todo> {
        let todo = try req.content.decode(Todo.self)
        return todo.save(on: self.db).map { todo }
    }

    func delete(req: Request) throws -> EventLoopFuture<HTTPStatus> {
        return Todo.find(req.parameters.get("todoID"), on: self.db)
            .unwrap(or: Abort(.notFound))
            .flatMap { $0.delete(on: self.db) }
            .transform(to: .ok)
    }
}

Fluent 具有动态模型,整个数据库层也更加复杂。您可以自定义自己的 keys, schemas 以及其他你自己喜好的配置。

// Vapor 3

import FluentSQLite
import Vapor

/// A single entry of a Todo list.
final class Todo: SQLiteModel {
    /// The unique identifier for this `Todo`.
    var id: Int?

    /// A title describing what this `Todo` entails.
    var title: String

    /// Creates a new `Todo`.
    init(id: Int? = nil, title: String) {
        self.id = id
        self.title = title
    }
}

/// Allows `Todo` to be used as a dynamic migration.
extension Todo: Migration { }

/// Allows `Todo` to be encoded to and decoded from HTTP messages.
extension Todo: Content { }

/// Allows `Todo` to be used as a dynamic parameter in route definitions.
extension Todo: Parameter { }

// ------------------------------------------------------------------------------------------

// Vapor 4

import Fluent
import Vapor

final class Todo: Model, Content {
    static let schema = "todos"
    
    @ID(key: "id")
    var id: Int?

    @Field(key: "title")
    var title: String

    init() { }

    init(id: Int? = nil, title: String) {
        self.id = id
        self.title = title
    }
}

有一个全新的迁移层,提供易于上手的 API。

import Fluent

struct CreateTodo: Migration {
    func prepare(on database: Database) -> EventLoopFuture<Void> {
        return database.schema("todos")
            .field("id", .int, .identifier(auto: true))
            .field("title", .string, .required)
            .create()
    }

    func revert(on database: Database) -> EventLoopFuture<Void> {
        return database.schema("todos").delete()
    }
}

Fluent is amazing in Vapor 4!

原文阅读:What's new in Vapor 4?

更多阅读,请关注官方微信公众号: