forked from 54088kkk/RW-HPS-Docs
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
30 changed files
with
1,607 additions
and
2 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,36 @@ | ||
# RW-HPS Docs | ||
别急,等下就好 | ||
# RW-HPS 目录 | ||
|
||
**欢迎来到 RW-HPS 文档** | ||
|
||
##对于初次使用的用户,请阅读 [**用户手册**](run/UserManual.md) | ||
|
||
## JVM 平台 RW-HPS 开发 | ||
|
||
本节介绍使用 Java 等 JVM 平台编程语言开发 RW-HPS 插件。 | ||
|
||
**为了避免遇到各种问题,请逐步仔细阅读。** | ||
|
||
1. [**JVM 环境和开发准备工作**](plugin/Preparations.md) | ||
|
||
2. 阅读 API 文档(见下文) | ||
|
||
### RW-HPS-core API 文档导航 | ||
|
||
请在 [**CoreAPI目录**](api/CoreAPI.md) 阅读 **RW-HPS-Core** 使用文档。 | ||
|
||
### Plugin 帮助 | ||
|
||
请在 [**插件开发目录**](plugin/README.md) 阅读 **RW-HPS-Plugin** 的各种操作 | ||
|
||
## RW-HPS 其他文档 | ||
|
||
### RW-HPS 版本规范 | ||
|
||
请在 [**版本规范**](update/Evolution.md) 阅读 **RW-HPS** 的版本规范 | ||
|
||
## 其他 RW-HPS 协议实现 | ||
|
||
**`RW-HPS` 提供 Kotlin/Java 等 JVM 平台语言 开发支持 如果不熟悉这些语言,请使用以下实现** | ||
|
||
- [`Minxyzgo/Go-RW-HPS` ](https://github.com/Minxyzgo/Go-RW-HPS) **咕咕咕** | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
* [English](/en/README.md) | ||
* [简体中文](/) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
# RW-HPS - File | ||
|
||
在 RW-HPS 中 文件操作同一使用 `FileUtil` 进行操作 | ||
`FileUtil` 默认根是在与jar同级目录 因此 不需要特别进行管理 | ||
|
||
对于插件在 `pluginDataFileUtil` 中获取到的, 则根在 `plugin/插件名/` | ||
|
||
## FileUtil | ||
|
||
`FileUtil` 代表一个外部文件或文件夹 | ||
|
||
构造 `FileUtil` 可以通过以下方法构造 | ||
|
||
```java | ||
// 因为不会创建文件 同时 位置和Jar同目录 | ||
FileUtil.getFile("文件名"); | ||
// 因为不会创建文件 只会创建目录 | ||
FileUtil.getFolder("文件夹名"); | ||
// 只会创建目录 | ||
FileUtil.getFolder("文件夹名").toFile("文件名"); | ||
/** | ||
FileUtil的三个实例什么都不会做 也不会创建目录和文件 | ||
如果需要先目录再文件 那么用FileUtil.toFolder(文件夹名).toFile(文件名) | ||
如果需要先进入多个目录 那么用FileUtil.toFolder(文件夹名).toFolder(文件夹名) | ||
只有使用FileUtil().read/Write时才会进行文件创建 | ||
注意: | ||
FileUtil.toFolder初始目录是Server.jar的目录或者Main提交的参数目录 | ||
toFolder只是起一个进入作用 | ||
*/ | ||
// 获取临时文件 | ||
FileUtil.getTempFile("文件名") | ||
// 获取临时文件夹 | ||
FileUtil.getTempDirectory("文件夹名") | ||
// 会创建文件夹并尝试创建文件 | ||
new FileUtil().mkdir(); | ||
// 会尝试创建文件 | ||
nwe FileUtil().createNewFile(); | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,179 @@ | ||
# RW-HPS - Http API | ||
|
||
> 注: | ||
> - 本章节是介绍 `RW-HPS` 中的一个内置插件 | ||
> - 本章节**不是**关于 `UPLIST-API` 的章节 | ||
## 使用 | ||
|
||
要想使用HttpApi,你需要先使用`GET`方式请求`/HttpApi/api/AuthCookie`并携带参数`passwd` | ||
|
||
默认密码是*随机生成*的,可在配置文件找到`webToken`查询 | ||
|
||
请求完成后会得到一个名为`HttpApi-Authentication`的cookie,有效期为**24小时** | ||
|
||
之后每一次请求都**必须**携带此cookie,否则服务器会返回403 | ||
|
||
### GET | ||
|
||
路径: `/HttpApi/api/get/xxx` | ||
|
||
#### info | ||
|
||
##### SystemInfo | ||
|
||
路径: `/HttpApi/api/get/info/SystemInfo`(其他同理) | ||
|
||
返回 | ||
|
||
```json | ||
{ | ||
"status": "OK", | ||
"data": "{\"system\":\"Linux\",\"arch\":\"amd64\",\"jvmName\":\"OpenJDK 64-Bit Server VM\",\"jvmVersion\":\"11.0.20\"}" | ||
} | ||
``` | ||
|
||
##### GameInfo | ||
|
||
返回 | ||
|
||
```json | ||
{ | ||
"status": "OK", | ||
"data": "{\"income\":1.0,\"noNukes\":false,\"credits\":0,\"sharedControl\":false,\"players\":[]}" | ||
} | ||
``` | ||
|
||
##### ModsInfo | ||
|
||
返回 | ||
|
||
```json | ||
{ | ||
"status": "OK", | ||
"data": "[\"RW-HPS CoreUnits\"]" | ||
} | ||
``` | ||
|
||
#### event | ||
|
||
##### GameOver | ||
|
||
返回 | ||
|
||
```json | ||
{ | ||
"status": "OK", | ||
"data": "[]" | ||
} | ||
``` | ||
|
||
### POST | ||
|
||
路径: `/HttpApi/api/post/xxx` | ||
|
||
#### run | ||
|
||
##### ServerCommand | ||
|
||
用处: *执行服务器命令,发送返回* | ||
|
||
// TODO | ||
|
||
##### ClientCommand | ||
|
||
用处: *执行客户端命令,发送返回* | ||
|
||
// TODO | ||
|
||
### WebSocket | ||
|
||
路径: `/WebSocket/HttpApi/api/Console` | ||
|
||
每隔几秒客户端需要`ping`(下文可找到此方法),若在10秒内无操作,服务器将会以超时为由断开客户端连接 | ||
|
||
以下为可用操作 | ||
|
||
#### Register | ||
|
||
用处: *在服务器中注册此cookie,参数使用上文所得到的cookie,注册完成后客户端无需继续携带此cookie* | ||
|
||
发送 | ||
|
||
```json | ||
{ | ||
"cookie" : "5420dedf8f1829bc43d03843d26216523fe19e06ee253abcacd3a4ee5b9af12b", | ||
"type" : "register" | ||
} | ||
``` | ||
|
||
返回 | ||
|
||
```json | ||
{ | ||
"code": 200, | ||
"data": "Register OK" | ||
} | ||
``` | ||
|
||
#### Ping | ||
|
||
用处: *保活* | ||
|
||
发送 | ||
|
||
```json | ||
{ | ||
"type": "ping" | ||
} | ||
``` | ||
|
||
返回 | ||
|
||
```json | ||
{ | ||
"code": 200, | ||
"data": "pong" | ||
} | ||
``` | ||
|
||
#### GetConsole | ||
|
||
用处: *将服务器控制台输入发送至ws直到客户端断开连接* | ||
|
||
发送 | ||
|
||
```json | ||
{ | ||
"type": "getConsole" | ||
} | ||
``` | ||
|
||
返回 | ||
|
||
```json | ||
{ | ||
"code": 200, | ||
"data": "[9072-79-85 20:08:33] 这是一条不存在的日志" | ||
} | ||
``` | ||
|
||
#### RunCommand | ||
|
||
用处: *运行服务器命令* | ||
|
||
注: 要获取返回结果请先`getConsole` | ||
|
||
发送 | ||
|
||
```json | ||
{ | ||
"type": "runCommand", | ||
"runCommand": "version" | ||
} | ||
``` | ||
|
||
返回 | ||
|
||
**无** | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,60 @@ | ||
# RW-HPS - Net | ||
|
||
**目录** | ||
|
||
- [1. Net](#1-Net) | ||
- [创建Net](#创建Net) | ||
- [启动端口监听](#启动端口监听) | ||
- [修改协议](#修改协议) | ||
|
||
## 1. Net | ||
|
||
在服务器的启动中 服务器使用的是 [CoreCommand : startnetservice] 来启动的端口监听 | ||
|
||
### 创建Net | ||
|
||
在服务器中 每个Port 或者是Port段 均是被StartNet描述 | ||
服务器的核心即在这里 | ||
|
||
```kotlin | ||
class StartNet { | ||
// 默认协议 | ||
constructor() | ||
|
||
// 自定义协议 | ||
constructor(abstractNetClass: Class<*>) | ||
} | ||
``` | ||
|
||
通常的调用方法为: | ||
|
||
``` | ||
// Kotlin | ||
val startNet = StartNet() | ||
// Java | ||
StartNet startNet = StartNet(); | ||
``` | ||
|
||
#### 启动端口监听 | ||
|
||
``` | ||
val startNet = ~ | ||
startNet.openPort(主端口) | ||
如果是监听多个端口 那么可以 | ||
startNet.openPort(主端口,监听范围起始,监听范围结束) | ||
``` | ||
|
||
#### 修改协议 | ||
|
||
只需要继承AbstractNet即可修改 initChannel 实现, 来自定义协议 | ||
在 `RW-HPS` 中 已经默认实现了一个GamePort共用解析器, 您可以自行调用 | ||
|
||
```kotlin | ||
class NewShunt(startNet: StartNet) : AbstractNet(startNet) { | ||
override fun initChannel(socketChannel: SocketChannel) { | ||
// 发挥创造力 | ||
socketChannel.pipeline().addLast() | ||
} | ||
} | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,69 @@ | ||
# RW-HPS - SaveData API | ||
|
||
## Plugin保存数据 | ||
|
||
### 设计目标 | ||
|
||
- 源码级静态强类型:避免 `getString()`, `getList()`... | ||
- 全自动加载保存:插件仅需在启动时通过一行代码链接自动保存 | ||
- 与前端同步修改:在 Android 等图形化前端实现中可以在内存动态同步修改 | ||
- 存储扩展性:可使用多种方式存储,无论是文件还是数据库,插件层都使用同一种实现方式 | ||
|
||
综上,**最小化插件作者在处理数据和配置做的付出**。 | ||
|
||
*暂无数据库保存支持,但这已经被提上日程。* | ||
|
||
## [`Value`] | ||
|
||
```java | ||
interface Value<T> { | ||
private T data; | ||
|
||
protected Value(T data) { | ||
this.data = data; | ||
} | ||
} | ||
``` | ||
|
||
表示一个值代理。在 [`PluginData`] 中,值都经过 [`Value`] 包装。 | ||
|
||
## [`PluginData`] | ||
|
||
一个插件内部的, 对用户隐藏的数据对象。类似于属性名作为键,对应 [`Value`] 作为值的 `Map`。 | ||
|
||
[`PluginData`] 接口拥有一个基础实现类,[`AbstractPluginData`],默认不支持自动保存,仅存储键值关系及其序列化器。 | ||
|
||
插件可继承 [`AbstractPluginData`],拥有高自由的实现细节访问权限,并扩展数据结构。 | ||
但通常,插件使用 [`AutoSavePluginData`]。 | ||
|
||
[`AutoSavePluginData`] 监听保存在它之中的值的修改,并在合适的时机在提供的 [`AutoSavePluginDataHolder`] 协程作用域下启动协程保存数据。 | ||
|
||
### 使用 `PluginData` | ||
|
||
示例在此时比理论更高效 | ||
|
||
1. 插件自己创建 | ||
|
||
```java | ||
public class Main extends Plugin { | ||
PluginData pluginData = new PluginData(); | ||
|
||
/** | ||
* 这里主要做初始化 | ||
*/ | ||
@Override | ||
public void init() { | ||
// this.pluginDataFileUtil 是 继承Plugin后自动生成 | ||
// 设置Bin文件位置 | ||
pluginData.setFileUtil(this.pluginDataFileUtil.toFile("ExampleData.bin")); | ||
pluginData.read(); | ||
|
||
// 读取 | ||
long lastStartTime = this.pluginData.getData("lastStartTime", Time.concurrentMillis()); | ||
String lastStartTimeString = this.pluginData.getData("lastStartTimeString", Time.getUtcMilliFormat(1)); | ||
// 写入 | ||
this.pluginData.setData("lastStartTime", Time.concurrentMillis()); | ||
this.pluginData.setData("lastStartTimeString", Time.getUtcMilliFormat(1)); | ||
} | ||
} | ||
``` |
Oops, something went wrong.