开发一个不那么另类的 Swift 服务端框架:Pjango

发布于:2017-06-18 17:11,阅读数:2619,点赞数:16


> 这是一款 Swift 服务端开发框架,在[「GitHub」](https://github.com/enums/Pjango)开源。
>
> 项目使用 Apache 2.0 许可,任何违反许可的行为都将承担责任。

# 引言

用 Python 开发过服务端的同学可能会对`Pjango`这个名字眼熟。没错,名字来源于著名的 Python 服务端框架`Django`。为什么要叫 Pjango 呢,因为它是基于 Perfect 开发的,Perfect 全家桶在工程里有着举足轻重的作用。最终取了这个名字,向二者致敬。

本框架基于 Perfect,并做了 MVC 设计,读者可以使用 MVC 来构建你的网站。

写这篇博文的目的是想找一两个熟悉 Django 又熟悉 Swift for Linux 的小伙伴一起开发,一起讨论。

# Demo

Demo 的地址已和核心框架一起上传 GitHub,这里就简单介绍一下。

## 配置和路由

这两项分别在 Demo 的`Settings.swift`和`Urls.swift`中。

`Settings.swift`:

```swift
import Foundation
import Pjango_Core

public func pjangoUserSetSettings() {

// Pjango

#if os(macOS)
WORKSPACE_PATH = "/Users/Enum/Developer/macOS/Pjango/Workspace"
#else
WORKSPACE_PATH = "/media/psf/Home/Developer/macOS/Pjango/Workspace"
#endif

DEBUG_LOG = true



// Django

BASE_DIR = ""

TEMPLATES_DIR = "templates"

STATIC_URL = "static"

DATABASE = PCDataBaseConfig.init(param: [
"ENGINE": PCDataBaseEnginType.mysql,
"NAME": "Pjango_default",
"USER": "github",
"PASSWORD": "enumsgithub.",
"HOST": "127.0.0.1",
"PORT": UInt16(3306),
])!
}

```

`Urls.swift`:

```swift
import Foundation
import Pjango_Core

public func pjangoUserSetUrls() -> [PCUrlConfig] {

return [

pjangoUrl("", IndexView.self, "index"),
pjangoUrl("time_zone", TimeZoneView.self, "time_zone"),

]

}
```

用过 Django 的同学一定会觉得这个画面十分眼熟。实现细节都在`Pjango-Core`中,如果读者只想使用框架,就不必去了解背后实现的细节。

Django 的路由是用正则匹配的,很不幸的是 Pjango 的路由最终会向着 Perfect-HTTPServer 中的规则走,并不会使用正则。但功能都是可以实现的。

## 数据库无关页面

### 写 View 和 Web

某些动态的页面可能不需要经过数据库,页面上或许只有个时间,或者只有个动态字符串。使用 Pjango 开发,只需要在 Web 中遵守 Mustache 模板规则嵌入变量,在服务端代码中返回一个字典去一一对应就可以了。

```swift
class IndexView: PCView {

override var templateName: String {
return "index.html"
}

override var viewParam: PCViewParam? {
return [
"_pjango_url_timezone": pjangoUrlReverse("time_zone"),
"_pjango_param_time": Date.init().stringValue,
"_pjango_param_msg": "Msg from Pjango"
]
}

}
```

```html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Welcome to Pjango</title>
<link rel="stylesheet" href="http://cdn.static.runoob.com/libs/bootstrap/3.3.7/css/bootstrap.min.css">
<script src="http://cdn.static.runoob.com/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="http://cdn.static.runoob.com/libs/bootstrap/3.3.7/js/bootstrap.min.js"></script>
</head>
<body>
<h1 class="text-center">Welcome to Pjango!</h1>
<h4 class="text-center">{{_pjango_param_msg}}</h4>
<h4 class="text-center">{{_pjango_param_time}}</h4>

<div class="text-center">
<button type="button" class="btn btn-default" onclick="window.open('{{_pjango_url_timezone}}')">See More Time Zone</button>
</div>

</body>
</html>


```

查看效果:[http://enumsblog.com:8080](http://enumsblog.com:8080)


## 数据库相关页面

数据库相关的页面,常见的就是列出表的相关内容了。使用 Pjango,只需要编写 Model,Pjango 在运行时会自动检查表是否存在,如果表不存在会自动创建跟模型对应的表。

### 1、写 Model

```swift
class TimeZoneModel: PCModel {

override var tableName: String {
return "TimeZone"
}

var zone = PCDataBaseField.init(name: "ZONE", type: .string, length: 3)
var memo = PCDataBaseField.init(name: "MEMO", type: .string, length: 50)

override func registerFields() -> [PCDataBaseField] {
return [
zone, memo
]
}
}
```

### 2、写 View 和 Web

```swift
class TimeZoneView: PCListView {

override var templateName: String {
return "time_zone.html"
}

override var querySet: Array<PCModel>? {
return TimeZoneModel.queryObjects()
}


}
```

如果需要展示额外字段,重载这个方法即可:

```swift

override func viewParamUserField(withModel model: PCModel) -> PCViewParam? {
let model = model as! TimeZoneModel
let formatter = DateFormatter.init()
formatter.timeZone = TimeZone.init(identifier: model.zone.value as! String)
formatter.dateFormat = "YYYY-MM-dd HH:mm:ss"
return [
"_pjango_param_table_TimeZone_TIME": formatter.string(from: Date.init())
]
}

```

页面也需要遵守 Mustache 模板规则,嵌入包含表格的代码:

```html
<body>
<table class="table">
<thead>
<tr>
<th>ZONE</th>
<th>MEMO</th>
<th>TIME</th>
</tr>
</thead>
<tbody>
{{#_pjango_param_table}}
<tr>
<td>{{_pjango_param_table_TimeZone_ZONE}}</td>
<td>{{_pjango_param_table_TimeZone_MEMO}}</td>
<td>{{_pjango_param_table_TimeZone_TIME}}</td>
</tr>
{{/_pjango_param_table}}
</tbody>
</table>

</body>
```

查看效果:[http://enumsblog.com:8080/time_zone](http://enumsblog.com:8080/time_zone)

效果中由于 Swift 在 Linux 下时区设置存在 bug,因此时间显示是错误的。在 macOS 中没有这个问题,感兴趣的同学可以下载源码,在 macOS 上查看效果。

# 结语

说了这么多,只是想让 Swift 服务端之路走得更顺利点罢了,欢迎感兴趣的同学加入。

发邮件给我:[i@yuusann.com](mailto:i@yuusann.com)


评论:0条


返回列表

返回归档

返回主页