✨
This commit is contained in:
parent
0d0b24de75
commit
bcfbe0d6b3
11
CHANGELOG.md
11
CHANGELOG.md
@ -1,3 +1,14 @@
|
||||
## [1.2.1](https://github.com/chaos-zhu/easynode/releases) (2022-12-12)
|
||||
|
||||
### Features
|
||||
|
||||
* 新增支持终端长命令输入模式 ✔
|
||||
* 新增前端静态文件缓存 ✔
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* v1.2的若干bug...
|
||||
|
||||
## [1.2.0](https://github.com/chaos-zhu/easynode/releases) (2022-09-12)
|
||||
|
||||
### Features
|
||||
|
8
Q&A.md
8
Q&A.md
@ -1,8 +1,6 @@
|
||||
# 用于收集一些疑难杂症
|
||||
# Q&A
|
||||
|
||||
- **欢迎pr~**
|
||||
|
||||
## 甲骨文CentOS7/8启动服务失败
|
||||
## CentOS7/8启动服务失败
|
||||
|
||||
> 先关闭SELinux
|
||||
|
||||
@ -17,6 +15,6 @@ SELINUX=disabled
|
||||
|
||||
> 查看SELinux状态:sestatus
|
||||
|
||||
## 甲骨文ubuntu20.04客户端服务启动成功,无法连接?
|
||||
## 客户端服务启动成功,无法连接?
|
||||
|
||||
> 端口未开放:`iptables -I INPUT -s 0.0.0.0/0 -p tcp --dport 22022 -j ACCEPT` 或者 `rm -rf /etc/iptables && reboot`
|
||||
|
10
README.md
10
README.md
@ -42,12 +42,10 @@
|
||||
|
||||
- 依赖Node.js环境
|
||||
|
||||
- 占用端口:8082(http端口)、8083(https端口)、22022(客户端端口)
|
||||
- 占用端口:8082(http端口)、22022(客户端端口)
|
||||
|
||||
- 建议使用**境外服务器**(最好延迟低)安装服务端,客户端信息监控与webssh功能都将以`该服务器作为跳板机`
|
||||
|
||||
- https服务需自行配置证书,或者使用`nginx反代`解决(推荐)
|
||||
|
||||
#### Docker镜像
|
||||
|
||||
> 注意:网速统计功能可能受限,docker网络将使用host模式(与宿主机共享端口,占用: 8082、22022)
|
||||
@ -88,12 +86,6 @@ wget -qO- --no-check-certificate https://ghproxy.com/https://raw.githubuserconte
|
||||
|
||||
- 默认登录密码:admin(首次部署完成后请及时修改).
|
||||
|
||||
6. 部署https服务
|
||||
- 部署https服务需要自己上传域名证书至`\server\app\config\pem`,并且证书和私钥分别命名:`key.pem`和`cert.pem`
|
||||
- 配置域名:vim server/app/config/index.js 在domain字段中填写你解析到服务器的域名
|
||||
- pm2 restart easynode-server
|
||||
- 不出意外你就可以访问https服务:https://domain:8083
|
||||
|
||||
---
|
||||
|
||||
### 客户端安装
|
||||
|
0
client/bin/www
Normal file → Executable file
0
client/bin/www
Normal file → Executable file
@ -73,9 +73,16 @@ mv ${FILE_PATH}/${SERVER_NAME}.service ${SERVICE_PATH}
|
||||
# echo "***********************daemon-reload***********************"
|
||||
systemctl daemon-reload
|
||||
|
||||
echo "***********************启动服务***********************"
|
||||
echo "***********************准备启动服务***********************"
|
||||
systemctl start ${SERVER_NAME}
|
||||
|
||||
if [ $? != 0 ]
|
||||
then
|
||||
echo "***********************${SERVER_NAME}.service启动失败***********************"
|
||||
echo "***********************可能是服务器开启了SELinux, 参见Q&A***********************"
|
||||
exit 1
|
||||
fi
|
||||
echo "***********************服务启动成功***********************"
|
||||
|
||||
# echo "***********************设置开机启动***********************"
|
||||
systemctl enable ${SERVER_NAME}
|
||||
|
@ -1,25 +1,11 @@
|
||||
const path = require('path')
|
||||
const fs = require('fs')
|
||||
|
||||
const getCertificate =() => {
|
||||
try {
|
||||
return {
|
||||
cert: fs.readFileSync(path.join(__dirname, './pem/cert.pem')),
|
||||
key: fs.readFileSync(path.join(__dirname, './pem/key.pem'))
|
||||
}
|
||||
} catch (error) {
|
||||
return null
|
||||
}
|
||||
}
|
||||
module.exports = {
|
||||
domain: 'xxx.com', // https域名, 可不配置
|
||||
httpPort: 8082,
|
||||
httpsPort: 8083,
|
||||
clientPort: 22022, // 勿更改
|
||||
certificate: getCertificate(),
|
||||
uploadDir: path.join(process.cwd(),'app/static/upload'),
|
||||
staticDir: path.join(process.cwd(),'app/static'),
|
||||
sftpCacheDir: path.join(process.cwd(),'app/socket/.sftp-cache'),
|
||||
sftpCacheDir: path.join(process.cwd(),'app/socket/sftp-cache'),
|
||||
sshRecordPath: path.join(process.cwd(),'app/storage/ssh-record.json'),
|
||||
keyPath: path.join(process.cwd(),'app/storage/key.json'),
|
||||
hostListPath: path.join(process.cwd(),'app/storage/host-list.json'),
|
||||
|
@ -1,6 +1,6 @@
|
||||
const consola = require('consola')
|
||||
global.consola = consola
|
||||
const { httpServer, httpsServer, clientHttpServer } = require('./server')
|
||||
const { httpServer, clientHttpServer } = require('./server')
|
||||
const initLocal = require('./init')
|
||||
const scheduleJob = require('./schedule')
|
||||
|
||||
@ -10,6 +10,4 @@ initLocal()
|
||||
|
||||
httpServer()
|
||||
|
||||
httpsServer()
|
||||
|
||||
clientHttpServer()
|
||||
|
@ -1,10 +1,8 @@
|
||||
const cors = require('@koa/cors')
|
||||
// const { domain } = require('../config')
|
||||
|
||||
// 跨域处理
|
||||
const useCors = cors({
|
||||
origin: ({ req }) => {
|
||||
// return domain || req.headers.origin
|
||||
return req.headers.origin
|
||||
},
|
||||
credentials: true,
|
||||
|
@ -1,9 +1,8 @@
|
||||
const Koa = require('koa')
|
||||
const compose = require('koa-compose') // 组合中间件,简化写法
|
||||
const http = require('http')
|
||||
const https = require('https')
|
||||
const { clientPort } = require('./config')
|
||||
const { domain, httpPort, httpsPort, certificate } = require('./config')
|
||||
const { httpPort } = require('./config')
|
||||
const middlewares = require('./middlewares')
|
||||
const wsMonitorOsInfo = require('./socket/monitor')
|
||||
const wsTerminal = require('./socket/terminal')
|
||||
@ -17,22 +16,11 @@ const httpServer = () => {
|
||||
const server = http.createServer(app.callback())
|
||||
serverHandler(app, server)
|
||||
// ws一直报跨域的错误:参照官方文档使用createServer API创建服务
|
||||
server.listen(process.env.PORT || httpPort, () => {
|
||||
server.listen(httpPort, () => {
|
||||
consola.success(`Server(http) is running on: http://localhost:${ httpPort }`)
|
||||
})
|
||||
}
|
||||
|
||||
const httpsServer = () => {
|
||||
if(!certificate) return consola.error('未上传证书, 创建https服务失败')
|
||||
const app = new Koa()
|
||||
const server = https.createServer(certificate, app.callback())
|
||||
serverHandler(app, server)
|
||||
server.listen(httpsPort, (err) => {
|
||||
if (err) return consola.error('https server error: ', err)
|
||||
consola.success(`Server(https) is running: https://${ domain }:${ httpsPort }`)
|
||||
})
|
||||
}
|
||||
|
||||
const clientHttpServer = () => {
|
||||
const app = new Koa()
|
||||
const server = http.createServer(app.callback())
|
||||
@ -63,6 +51,5 @@ function serverHandler(app, server) {
|
||||
|
||||
module.exports = {
|
||||
httpServer,
|
||||
httpsServer,
|
||||
clientHttpServer
|
||||
}
|
@ -109,21 +109,21 @@ function listenInput(sftpClient, socket) {
|
||||
socket.emit('sftp_error', error.message)
|
||||
}
|
||||
})
|
||||
// socket.on('up_file', async ({ targetPath, fullPath, name, file }) => {
|
||||
// console.log({ targetPath, fullPath, name, file })
|
||||
// const exists = await sftpClient.exists(targetPath)
|
||||
// if(!exists) return socket.emit('not_exists_dir', '文件夹不存在或当前不可访问')
|
||||
// try {
|
||||
// const localPath = rawPath.join(sftpCacheDir, name)
|
||||
// fs.writeFileSync(localPath, file)
|
||||
// let res = await sftpClient.fastPut(localPath, fullPath)
|
||||
// consola.success('sftp上传成功: ', res)
|
||||
// socket.emit('up_file_success', res)
|
||||
// } catch (error) {
|
||||
// consola.error('up_file Error', error.message)
|
||||
// socket.emit('sftp_error', error.message)
|
||||
// }
|
||||
// })
|
||||
socket.on('up_file', async ({ targetPath, fullPath, name, file }) => {
|
||||
console.log({ targetPath, fullPath, name, file })
|
||||
const exists = await sftpClient.exists(targetPath)
|
||||
if(!exists) return socket.emit('not_exists_dir', '文件夹不存在或当前不可访问')
|
||||
try {
|
||||
const localPath = rawPath.join(sftpCacheDir, name)
|
||||
fs.writeFileSync(localPath, file)
|
||||
let res = await sftpClient.fastPut(localPath, fullPath)
|
||||
consola.success('sftp上传成功: ', res)
|
||||
socket.emit('up_file_success', res)
|
||||
} catch (error) {
|
||||
consola.error('up_file Error', error.message)
|
||||
socket.emit('sftp_error', error.message)
|
||||
}
|
||||
})
|
||||
|
||||
/** 分片上传 */
|
||||
// 1. 创建本地缓存文件夹
|
||||
@ -186,7 +186,7 @@ function listenInput(sftpClient, socket) {
|
||||
clearDir(resultDirPath, true) // 传服务器后移除文件夹及其文件
|
||||
} catch (error) {
|
||||
consola.error('sftp上传失败: ', error.message)
|
||||
socket.emit('sftp_error', error.message)
|
||||
socket.emit('up_file_fail', error.message)
|
||||
clearDir(resultDirPath, true) // 传服务器后移除文件夹及其文件
|
||||
}
|
||||
})
|
||||
|
File diff suppressed because one or more lines are too long
BIN
server/app/static/assets/index.5de3ed69.js.gz
Normal file
BIN
server/app/static/assets/index.5de3ed69.js.gz
Normal file
Binary file not shown.
Binary file not shown.
File diff suppressed because one or more lines are too long
BIN
server/app/static/assets/index.cf7d36d4.css.gz
Normal file
BIN
server/app/static/assets/index.cf7d36d4.css.gz
Normal file
Binary file not shown.
Binary file not shown.
@ -5,8 +5,8 @@
|
||||
<meta name="viewport" content="width=device-width, initial-scale=0,user-scalable=yes">
|
||||
<title>EasyNode</title>
|
||||
<script src="//at.alicdn.com/t/c/font_3309550_flid0kihu36.js"></script>
|
||||
<script type="module" crossorigin src="/assets/index.eb5f280e.js"></script>
|
||||
<link rel="stylesheet" href="/assets/index.a9194a35.css">
|
||||
<script type="module" crossorigin src="/assets/index.5de3ed69.js"></script>
|
||||
<link rel="stylesheet" href="/assets/index.cf7d36d4.css">
|
||||
</head>
|
||||
|
||||
<body>
|
||||
|
@ -1,2 +1 @@
|
||||
[
|
||||
]
|
||||
[]
|
@ -63,7 +63,7 @@ const getNetIPInfo = async (searchIp = '') => {
|
||||
let { origip: ip, location: country, city = '', regionName = '' } = res || {}
|
||||
searchResult.push({ ip, country, city: `${ regionName } ${ city }`, date })
|
||||
}
|
||||
console.log(searchResult)
|
||||
// console.log(searchResult)
|
||||
let validInfo = searchResult.find(item => Boolean(item.country))
|
||||
consola.info('查询IP信息:', validInfo)
|
||||
return validInfo || { ip: '获取IP信息API出错,请排查或更新API', country: '未知', city: '未知', date }
|
||||
|
0
server/bin/www
Normal file → Executable file
0
server/bin/www
Normal file → Executable file
Loading…
x
Reference in New Issue
Block a user