feat: add hints to session, update API

This commit is contained in:
wancat committed 2023-08-08 20:38:27 +08:00
1 parent ae61bfc768
commit 6f368f761e
8 files changed
+52 -46

No files matched your search

+9
View File
@@ -26,6 +26,15 @@ services:
volumes: volumes:
- ./data:/data/db - ./data:/data/db
swagger:
image: swaggerapi/swagger-editor:latest
ports:
- 8080:8080
volumes:
- ./server/swagger.yaml:/tmp/swagger.yaml
environment:
- SWAGGER_FILE=/tmp/swagger.yaml
networks: networks:
internal: internal:
players: players:
+2 -2
View File
@@ -1,6 +1,6 @@
title: Hello, Linux World! title: Hello, Linux World!
order: 1 order: 1
introduction: | instruction: |
你身在一個漆黑的房間裡,沒有任何的光線或聲音。你想不起來為什麼自己會來到這裡。但你的腦中隱約感到某個聲音跟你說: 你身在一個漆黑的房間裡,沒有任何的光線或聲音。你想不起來為什麼自己會來到這裡。但你的腦中隱約感到某個聲音跟你說:
「輸入 echo Hello World!」 「輸入 echo Hello World!」
@@ -17,7 +17,7 @@ stages:
- 首先,你必須要學會如何使用指令。 - 首先,你必須要學會如何使用指令。
- 一個指令是由一個指令名稱和一些參數所組成的,而指令名稱和參數之間是以空白字元分隔。 - 一個指令是由一個指令名稱和一些參數所組成的,而指令名稱和參數之間是以空白字元分隔。
- 例如,你可以輸入 `ls` 來查看目前的目錄下有哪些檔案。 - 例如,你可以輸入 `ls` 來查看目前的目錄下有哪些檔案。
hint: hints:
- 使用 `ls` 指令來查看目前的目錄下有哪些檔案。 - 使用 `ls` 指令來查看目前的目錄下有哪些檔案。
next: ls next: ls
- id: ls - id: ls
@@ -6,7 +6,7 @@ import commandHandler from '../../game/commandHandler.js'
export async function newCommand(req, res) { export async function newCommand(req, res) {
console.log('new command:', req.body) console.log('new command:', req.body)
const { token, command, pwd, exit_code, output } = req.body const { token, command, pwd, output, error } = req.body
if (!command) { if (!command) {
res.status(400).json({ message: 'command is required' }) res.status(400).json({ message: 'command is required' })
@@ -33,8 +33,8 @@ export async function newCommand(req, res) {
session, session,
command, command,
pwd, pwd,
exit_code,
output, output,
error,
}) })
await c.save() await c.save()
@@ -3,9 +3,8 @@ import Quest from '../../models/quest.js'
export async function getQuests(req, res) { export async function getQuests(req, res) {
const quests = await Quest.find({}).sort({ order: 1 }) const quests = await Quest.find({}).sort({ order: 1 })
res.json( res.json(
quests.map(({ name, title, order, _id }) => ({ quests.map(({ title, order, _id }) => ({
_id, _id,
name,
title, title,
order, order,
})) }))
@@ -19,5 +18,6 @@ export async function getQuestDetail(req, res) {
res.status(404).json({ message: 'Quest not found.' }) res.status(404).json({ message: 'Quest not found.' })
return return
} }
res.json(quest) const { _id, title, order, instruction } = quest
res.json({ _id, title, order, instruction })
} }
+1 -1
View File
@@ -28,6 +28,7 @@ const commandHandler = async (session, commandInput) => {
if (!commandMatch || !outputMatch || !errorMatch) return {} if (!commandMatch || !outputMatch || !errorMatch) return {}
session.completion.push(session.progress) session.completion.push(session.progress)
session.hints.push(...stage.hints)
const nextStage = quest.stages.find((s) => s.id === stage.next) const nextStage = quest.stages.find((s) => s.id === stage.next)
session.progress = nextStage.id session.progress = nextStage.id
@@ -35,7 +36,6 @@ const commandHandler = async (session, commandInput) => {
return { return {
responses: stage.responses, responses: stage.responses,
hint: stage.hint,
} }
} }
+2 -2
View File
@@ -23,7 +23,7 @@ const stageSchema = new Schema({
type: [String], type: [String],
required: true, required: true,
}, },
hint: { hints: {
type: [String], type: [String],
required: true, required: true,
}, },
@@ -39,7 +39,7 @@ const Quest = model(
_id: String, _id: String,
title: String, title: String,
order: Number, order: Number,
introduction: String, instruction: String,
stages: [stageSchema], stages: [stageSchema],
}) })
) )
+1
View File
@@ -16,6 +16,7 @@ const Session = model(
finishedAt: Date, finishedAt: Date,
progress: String, progress: String,
completion: [String], completion: [String],
hints: [String],
}, },
{ timestamps: true } { timestamps: true }
) )
+32 -36
View File
@@ -1,6 +1,8 @@
openapi: 3.0.0 openapi: 3.0.0
servers: servers:
- url: /api/v1 - url: /api/v1
- url: https://odyssey.wancat.cc/api/v1
- url: http://localhost:3000/api/v1
info: info:
description: Linux Odyssey API description: Linux Odyssey API
version: '1.0.0' version: '1.0.0'
@@ -304,6 +306,10 @@ paths:
responses: responses:
'201': '201':
description: Command recorded successfully description: Command recorded successfully
content:
application/json:
schema:
$ref: '#/components/schemas/CommandResponse'
'400': '400':
description: Invalid request body description: Invalid request body
'401': '401':
@@ -333,10 +339,9 @@ components:
title: title:
type: string type: string
example: Hello World example: Hello World
content: instruction:
type: string type: string
format: html example: 'In this quest, you need to learn how to use `ls` to list the file.'
example: '<h1>Hello World</h1>'
order: order:
type: number type: number
@@ -372,20 +377,21 @@ components:
finished_at: finished_at:
type: string type: string
format: date-time format: date-time
terminals:
type: array
items:
type: string
graphs:
$ref: '#/components/schemas/TreeNode'
progress:
type: array
items:
$ref: '#/components/schemas/Progress'
hints: hints:
type: array type: array
items: items:
$ref: '#/components/schemas/Hint' type: string
example: '`ls -al` to list detail information of all files.'
progress:
type: string
description: current stage id
example: helloworld
completion:
type: array
description: list of completed stage ids
items:
type: string
example: helloworld
SessionSummary: SessionSummary:
type: object type: object
@@ -418,28 +424,6 @@ components:
items: items:
$ref: '#/components/schemas/TreeNode' $ref: '#/components/schemas/TreeNode'
Progress:
type: object
properties:
name:
type: string
finished_at:
type: string
format: date-time
skipped_at:
type: string
format: date-time
Hint:
type: object
properties:
name:
type: string
content:
type: string
source:
type: string
Command: Command:
type: object type: object
required: required:
@@ -461,6 +445,18 @@ components:
output: output:
type: string type: string
description: The output of the command description: The output of the command
error:
type: string
description: The error message of the command
CommandResponse:
type: object
properties:
responses:
type: array
items:
type: string
example: 'You have completed the quest!'
securitySchemes: securitySchemes:
BearerAuth: BearerAuth: