Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
S
srvpro
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Locked Files
Issues
0
Issues
0
List
Boards
Labels
Service Desk
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Security & Compliance
Security & Compliance
Dependency List
License Compliance
Packages
Packages
List
Container Registry
Analytics
Analytics
CI / CD
Code Review
Insights
Issues
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
nanahira
srvpro
Commits
5ecb95fa
Commit
5ecb95fa
authored
Feb 11, 2026
by
nanahira
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
test neos reuse
parent
e8491dbe
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
277 additions
and
19 deletions
+277
-19
data/default_config.json
data/default_config.json
+1
-0
tcp-protocol-detector.js
tcp-protocol-detector.js
+71
-0
tcp-protocol-detector.ts
tcp-protocol-detector.ts
+85
-0
ygopro-server.coffee
ygopro-server.coffee
+58
-8
ygopro-server.js
ygopro-server.js
+62
-11
No files found.
data/default_config.json
View file @
5ecb95fa
...
@@ -208,6 +208,7 @@
...
@@ -208,6 +208,7 @@
"neos"
:
{
"neos"
:
{
"enabled"
:
false
,
"enabled"
:
false
,
"port"
:
7977
,
"port"
:
7977
,
"reuse_port"
:
false
,
"ip_header"
:
"x-forwarded-for"
"ip_header"
:
"x-forwarded-for"
},
},
"test_mode"
:
{
"test_mode"
:
{
...
...
tcp-protocol-detector.js
0 → 100644
View file @
5ecb95fa
"
use strict
"
;
Object
.
defineProperty
(
exports
,
"
__esModule
"
,
{
value
:
true
});
exports
.
isHttp
=
isHttp
;
exports
.
isHttps
=
isHttps
;
exports
.
detectAndHandle
=
detectAndHandle
;
/**
* 检测 TCP 连接的第一个包是否为 HTTP 请求
* @param firstChunk 第一个数据包
* @returns 是否为 HTTP 请求
*/
function
isHttp
(
firstChunk
)
{
if
(
!
firstChunk
||
firstChunk
.
length
===
0
)
{
return
false
;
}
const
str
=
firstChunk
.
toString
(
'
ascii
'
,
0
,
Math
.
min
(
firstChunk
.
length
,
16
));
// HTTP 请求方法
const
httpMethods
=
[
'
GET
'
,
'
POST
'
,
'
PUT
'
,
'
DELETE
'
,
'
HEAD
'
,
'
OPTIONS
'
,
'
PATCH
'
,
'
TRACE
'
,
'
CONNECT
'
];
return
httpMethods
.
some
(
method
=>
str
.
startsWith
(
method
));
}
/**
* 检测 TCP 连接的第一个包是否为 HTTPS 请求(TLS/SSL ClientHello)
* @param firstChunk 第一个数据包
* @returns 是否为 HTTPS 请求
*/
function
isHttps
(
firstChunk
)
{
if
(
!
firstChunk
||
firstChunk
.
length
<
3
)
{
return
false
;
}
// TLS/SSL ClientHello 的特征:
// 第一个字节:0x16 (Handshake)
// 第二个字节:0x03 (SSL 3.0/TLS 1.x)
// 第三个字节:0x00-0x03 (版本号:SSL 3.0, TLS 1.0, 1.1, 1.2, 1.3)
return
(
firstChunk
[
0
]
===
0x16
&&
firstChunk
[
1
]
===
0x03
&&
firstChunk
[
2
]
>=
0x00
&&
firstChunk
[
2
]
<=
0x04
);
}
/**
* 检测 TCP 连接的协议类型并调用相应的处理函数
* @param socket TCP socket
* @param httpHandler HTTP/HTTPS 处理函数
* @param defaultHandler 默认处理函数(非 HTTP/HTTPS)
* @param isHttpsMode 是否为 HTTPS 模式
*/
function
detectAndHandle
(
socket
,
httpHandler
,
defaultHandler
,
isHttpsMode
)
{
let
firstDataReceived
=
false
;
const
dataHandler
=
(
chunk
)
=>
{
if
(
firstDataReceived
)
{
return
;
}
firstDataReceived
=
true
;
// 移除数据监听器,避免重复处理
socket
.
removeListener
(
'
data
'
,
dataHandler
);
const
isHttpRequest
=
isHttpsMode
?
isHttps
(
chunk
)
:
isHttp
(
chunk
);
if
(
isHttpRequest
)
{
// 是 HTTP/HTTPS 请求,交给 HTTP 服务器处理
// 需要把第一个数据包重新放回去
socket
.
unshift
(
chunk
);
httpHandler
(
socket
,
chunk
);
}
else
{
// 不是 HTTP/HTTPS 请求,交给默认处理器(YGOPro 协议)
// 同样需要把第一个数据包重新放回去
socket
.
unshift
(
chunk
);
defaultHandler
(
socket
);
}
};
socket
.
once
(
'
data
'
,
dataHandler
);
}
tcp-protocol-detector.ts
0 → 100644
View file @
5ecb95fa
import
{
Socket
}
from
'
net
'
;
/**
* 检测 TCP 连接的第一个包是否为 HTTP 请求
* @param firstChunk 第一个数据包
* @returns 是否为 HTTP 请求
*/
export
function
isHttp
(
firstChunk
:
Buffer
):
boolean
{
if
(
!
firstChunk
||
firstChunk
.
length
===
0
)
{
return
false
;
}
const
str
=
firstChunk
.
toString
(
'
ascii
'
,
0
,
Math
.
min
(
firstChunk
.
length
,
16
));
// HTTP 请求方法
const
httpMethods
=
[
'
GET
'
,
'
POST
'
,
'
PUT
'
,
'
DELETE
'
,
'
HEAD
'
,
'
OPTIONS
'
,
'
PATCH
'
,
'
TRACE
'
,
'
CONNECT
'
];
return
httpMethods
.
some
(
method
=>
str
.
startsWith
(
method
));
}
/**
* 检测 TCP 连接的第一个包是否为 HTTPS 请求(TLS/SSL ClientHello)
* @param firstChunk 第一个数据包
* @returns 是否为 HTTPS 请求
*/
export
function
isHttps
(
firstChunk
:
Buffer
):
boolean
{
if
(
!
firstChunk
||
firstChunk
.
length
<
3
)
{
return
false
;
}
// TLS/SSL ClientHello 的特征:
// 第一个字节:0x16 (Handshake)
// 第二个字节:0x03 (SSL 3.0/TLS 1.x)
// 第三个字节:0x00-0x03 (版本号:SSL 3.0, TLS 1.0, 1.1, 1.2, 1.3)
return
(
firstChunk
[
0
]
===
0x16
&&
firstChunk
[
1
]
===
0x03
&&
firstChunk
[
2
]
>=
0x00
&&
firstChunk
[
2
]
<=
0x04
);
}
/**
* 检测 TCP 连接的协议类型并调用相应的处理函数
* @param socket TCP socket
* @param httpHandler HTTP/HTTPS 处理函数
* @param defaultHandler 默认处理函数(非 HTTP/HTTPS)
* @param isHttpsMode 是否为 HTTPS 模式
*/
export
function
detectAndHandle
(
socket
:
Socket
,
httpHandler
:
(
socket
:
Socket
,
firstChunk
:
Buffer
)
=>
void
,
defaultHandler
:
(
socket
:
Socket
)
=>
void
,
isHttpsMode
:
boolean
):
void
{
let
firstDataReceived
=
false
;
const
dataHandler
=
(
chunk
:
Buffer
)
=>
{
if
(
firstDataReceived
)
{
return
;
}
firstDataReceived
=
true
;
// 移除数据监听器,避免重复处理
socket
.
removeListener
(
'
data
'
,
dataHandler
);
const
isHttpRequest
=
isHttpsMode
?
isHttps
(
chunk
)
:
isHttp
(
chunk
);
if
(
isHttpRequest
)
{
// 是 HTTP/HTTPS 请求,交给 HTTP 服务器处理
// 需要把第一个数据包重新放回去
socket
.
unshift
(
chunk
);
httpHandler
(
socket
,
chunk
);
}
else
{
// 不是 HTTP/HTTPS 请求,交给默认处理器(YGOPro 协议)
// 同样需要把第一个数据包重新放回去
socket
.
unshift
(
chunk
);
defaultHandler
(
socket
);
}
};
socket
.
once
(
'
data
'
,
dataHandler
);
}
ygopro-server.coffee
View file @
5ecb95fa
...
@@ -13,6 +13,7 @@ _async = require('async')
...
@@ -13,6 +13,7 @@ _async = require('async')
# ts utility
# ts utility
utility
=
require
'./utility.js'
utility
=
require
'./utility.js'
tcpDetector
=
require
'./tcp-protocol-detector.js'
# 三方库
# 三方库
_
=
global
.
_
=
require
'underscore'
_
=
global
.
_
=
require
'underscore'
...
@@ -626,9 +627,55 @@ init = () ->
...
@@ -626,9 +627,55 @@ init = () ->
,
1000
,
1000
log
.
info
(
"Starting server."
)
log
.
info
(
"Starting server."
)
net
.
createServer
(
netRequestHandler
).
listen
settings
.
port
,
->
log
.
info
"server started"
,
settings
.
port
# 用于存储 neos 相关的服务器对象
return
neosHttpServer
=
null
neosWsServer
=
null
# 检查是否需要在主端口上复用检测 HTTP/HTTPS
neosReuseMainPort
=
settings
.
modules
.
neos
.
enabled
and
(
settings
.
modules
.
neos
.
port
==
settings
.
port
or
settings
.
modules
.
neos
.
reuse_port
)
if
neosReuseMainPort
# 需要复用主端口,创建 neos HTTP 服务器但不监听端口
log
.
info
"neos will reuse main port
#{
settings
.
port
}
"
ws
=
require
'ws'
if
settings
.
modules
.
http
.
ssl
.
enabled
https
=
require
'https'
httpsOptions
=
cert
:
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
cert
)
key
:
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
key
)
neosHttpServer
=
https
.
createServer
(
httpsOptions
)
else
neosHttpServer
=
http
.
createServer
()
neosWsServer
=
new
ws
.
WebSocketServer
({
server
:
neosHttpServer
})
neosWsServer
.
on
'connection'
,
neosRequestListener
# 创建主服务器,带协议检测
mainTcpServer
=
net
.
createServer
(
socket
)
->
isHttpsMode
=
settings
.
modules
.
http
.
ssl
.
enabled
tcpDetector
.
detectAndHandle
socket
,
# HTTP/HTTPS 处理器
(
sock
,
firstChunk
)
->
# 将 socket 交给 neos HTTP 服务器处理
neosHttpServer
.
emit
'connection'
,
sock
,
# 默认处理器(YGOPro 协议)
(
sock
)
->
netRequestHandler
(
sock
)
,
isHttpsMode
mainTcpServer
.
listen
settings
.
port
,
->
log
.
info
"server started with neos port reuse"
,
settings
.
port
else
# 不需要复用,直接创建普通的 TCP 服务器
net
.
createServer
(
netRequestHandler
).
listen
settings
.
port
,
->
log
.
info
"server started"
,
settings
.
port
return
if
settings
.
modules
.
stop
if
settings
.
modules
.
stop
log
.
info
"NOTE: server not open due to config, "
,
settings
.
modules
.
stop
log
.
info
"NOTE: server not open due to config, "
,
settings
.
modules
.
stop
...
@@ -637,10 +684,11 @@ init = () ->
...
@@ -637,10 +684,11 @@ init = () ->
main_http_server
=
http_server
main_http_server
=
http_server
if
settings
.
modules
.
http
.
ssl
.
enabled
if
settings
.
modules
.
http
.
ssl
.
enabled
https
=
require
'https'
unless
neosReuseMainPort
# 如果没有在上面创建 https 相关对象
httpsOptions
=
https
=
require
'https'
cert
:
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
cert
)
httpsOptions
=
key
:
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
key
)
cert
:
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
cert
)
key
:
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
key
)
https_server
=
https
.
createServer
(
httpsOptions
,
httpRequestListener
)
https_server
=
https
.
createServer
(
httpsOptions
,
httpRequestListener
)
https_server
.
listen
settings
.
modules
.
http
.
ssl
.
port
https_server
.
listen
settings
.
modules
.
http
.
ssl
.
port
main_http_server
=
https_server
main_http_server
=
https_server
...
@@ -649,7 +697,8 @@ init = () ->
...
@@ -649,7 +697,8 @@ init = () ->
roomlist
.
init
main_http_server
,
ROOM_all
roomlist
.
init
main_http_server
,
ROOM_all
http_server
.
listen
settings
.
modules
.
http
.
port
http_server
.
listen
settings
.
modules
.
http
.
port
if
settings
.
modules
.
neos
.
enabled
if
settings
.
modules
.
neos
.
enabled
and
not
neosReuseMainPort
# neos 启用但不复用主端口,单独监听
ws
=
require
'ws'
ws
=
require
'ws'
neosHttpServer
=
null
neosHttpServer
=
null
if
settings
.
modules
.
http
.
ssl
.
enabled
if
settings
.
modules
.
http
.
ssl
.
enabled
...
@@ -659,6 +708,7 @@ init = () ->
...
@@ -659,6 +708,7 @@ init = () ->
neosWsServer
=
new
ws
.
WebSocketServer
({
server
:
neosHttpServer
})
neosWsServer
=
new
ws
.
WebSocketServer
({
server
:
neosHttpServer
})
neosWsServer
.
on
'connection'
,
neosRequestListener
neosWsServer
.
on
'connection'
,
neosRequestListener
neosHttpServer
.
listen
settings
.
modules
.
neos
.
port
neosHttpServer
.
listen
settings
.
modules
.
neos
.
port
log
.
info
"neos listening on separate port
#{
settings
.
modules
.
neos
.
port
}
"
mkdirList
=
[
mkdirList
=
[
"./plugins"
,
"./plugins"
,
...
...
ygopro-server.js
View file @
5ecb95fa
// Generated by CoffeeScript 2.7.0
// Generated by CoffeeScript 2.7.0
(
function
()
{
(
function
()
{
// 标准库
// 标准库
var
Aragami
,
CLIENT_get_absolute_pos
,
CLIENT_get_authorize_key
,
CLIENT_get_kick_reconnect_target
,
CLIENT_get_partner
,
CLIENT_heartbeat_register
,
CLIENT_heartbeat_unregister
,
CLIENT_import_data
,
CLIENT_is_able_to_kick_reconnect
,
CLIENT_is_able_to_reconnect
,
CLIENT_is_banned_by_mc
,
CLIENT_is_player
,
CLIENT_kick
,
CLIENT_kick_reconnect
,
CLIENT_pre_reconnect
,
CLIENT_reconnect
,
CLIENT_reconnect_register
,
CLIENT_reconnect_unregister
,
CLIENT_send_pre_reconnect_info
,
CLIENT_send_reconnect_info
,
CLIENT_send_replays
,
CLIENT_send_replays_and_kick
,
CLIENT_set_ip
,
PQueue
,
Q
,
ROOM_all
,
ROOM_bad_ip
,
ROOM_ban_player
,
ROOM_clear_disconnect
,
ROOM_connected_ip
,
ROOM_find_by_name
,
ROOM_find_by_pid
,
ROOM_find_by_port
,
ROOM_find_by_title
,
ROOM_find_or_create_ai
,
ROOM_find_or_create_by_name
,
ROOM_find_or_create_random
,
ROOM_kick
,
ROOM_player_flee
,
ROOM_player_get_score
,
ROOM_player_lose
,
ROOM_player_win
,
ROOM_players_oppentlist
,
ROOM_unwelcome
,
ROOM_validate
,
ReplayParser
,
ResolveData
,
Room
,
SERVER_clear_disconnect
,
SERVER_kick
,
SOCKET_flush_data
,
YGOProDeck
,
YGOProYrp
,
_
,
_async
,
addCallback
,
aragami
,
aragami_classes
,
athleticChecker
,
auth
,
axios
,
badwordR
,
badwords
,
ban_user
,
bunyan
,
call_match_api
,
challonge
,
checkFileExists
,
createDirectoryIfNotExists
,
crypto
,
dataManager
,
deck_name_match
,
dialogues
,
disconnect_list
,
exec
,
execFile
,
extra_mode_list
,
fs
,
geoip
,
getDuelLogQueryFromQs
,
getRealIp
,
get_memory_usage
,
http
,
httpRequestListener
,
importOldConfig
,
import_datas
,
init
,
ip6addr
,
isTrustedProxy
,
lflists
,
loadJSON
,
loadJSONAsync
,
loadLFList
,
loadRemoteData
,
load_dialogues
,
load_tips
,
log
,
long_resolve_cards
,
memory_usage
,
merge
,
moment
,
moment_long_ago_string
,
moment_now
,
moment_now_string
,
msg_polyfill
,
neosRequestListener
,
net
,
netRequestHandler
,
os
,
osu
,
path
,
qs
,
real_windbot_server_ip
,
release_disconnect
,
report_to_big_brother
,
request
,
roomlist
,
rooms_count
,
setting_change
,
setting_get
,
setting_save
,
settings
,
spawn
,
spawnSync
,
spawn_windbot
,
tips
,
toIpv4
,
toIpv6
,
util
,
utility
,
wait_room_start
,
wait_room_start_arena
,
windbot_looplimit
,
windbot_process
,
windbots
,
ygopro
,
zlib
;
var
Aragami
,
CLIENT_get_absolute_pos
,
CLIENT_get_authorize_key
,
CLIENT_get_kick_reconnect_target
,
CLIENT_get_partner
,
CLIENT_heartbeat_register
,
CLIENT_heartbeat_unregister
,
CLIENT_import_data
,
CLIENT_is_able_to_kick_reconnect
,
CLIENT_is_able_to_reconnect
,
CLIENT_is_banned_by_mc
,
CLIENT_is_player
,
CLIENT_kick
,
CLIENT_kick_reconnect
,
CLIENT_pre_reconnect
,
CLIENT_reconnect
,
CLIENT_reconnect_register
,
CLIENT_reconnect_unregister
,
CLIENT_send_pre_reconnect_info
,
CLIENT_send_reconnect_info
,
CLIENT_send_replays
,
CLIENT_send_replays_and_kick
,
CLIENT_set_ip
,
PQueue
,
Q
,
ROOM_all
,
ROOM_bad_ip
,
ROOM_ban_player
,
ROOM_clear_disconnect
,
ROOM_connected_ip
,
ROOM_find_by_name
,
ROOM_find_by_pid
,
ROOM_find_by_port
,
ROOM_find_by_title
,
ROOM_find_or_create_ai
,
ROOM_find_or_create_by_name
,
ROOM_find_or_create_random
,
ROOM_kick
,
ROOM_player_flee
,
ROOM_player_get_score
,
ROOM_player_lose
,
ROOM_player_win
,
ROOM_players_oppentlist
,
ROOM_unwelcome
,
ROOM_validate
,
ReplayParser
,
ResolveData
,
Room
,
SERVER_clear_disconnect
,
SERVER_kick
,
SOCKET_flush_data
,
YGOProDeck
,
YGOProYrp
,
_
,
_async
,
addCallback
,
aragami
,
aragami_classes
,
athleticChecker
,
auth
,
axios
,
badwordR
,
badwords
,
ban_user
,
bunyan
,
call_match_api
,
challonge
,
checkFileExists
,
createDirectoryIfNotExists
,
crypto
,
dataManager
,
deck_name_match
,
dialogues
,
disconnect_list
,
exec
,
execFile
,
extra_mode_list
,
fs
,
geoip
,
getDuelLogQueryFromQs
,
getRealIp
,
get_memory_usage
,
http
,
httpRequestListener
,
importOldConfig
,
import_datas
,
init
,
ip6addr
,
isTrustedProxy
,
lflists
,
loadJSON
,
loadJSONAsync
,
loadLFList
,
loadRemoteData
,
load_dialogues
,
load_tips
,
log
,
long_resolve_cards
,
memory_usage
,
merge
,
moment
,
moment_long_ago_string
,
moment_now
,
moment_now_string
,
msg_polyfill
,
neosRequestListener
,
net
,
netRequestHandler
,
os
,
osu
,
path
,
qs
,
real_windbot_server_ip
,
release_disconnect
,
report_to_big_brother
,
request
,
roomlist
,
rooms_count
,
setting_change
,
setting_get
,
setting_save
,
settings
,
spawn
,
spawnSync
,
spawn_windbot
,
t
cpDetector
,
t
ips
,
toIpv4
,
toIpv6
,
util
,
utility
,
wait_room_start
,
wait_room_start_arena
,
windbot_looplimit
,
windbot_process
,
windbots
,
ygopro
,
zlib
;
net
=
require
(
'
net
'
);
net
=
require
(
'
net
'
);
...
@@ -28,6 +28,8 @@
...
@@ -28,6 +28,8 @@
// ts utility
// ts utility
utility
=
require
(
'
./utility.js
'
);
utility
=
require
(
'
./utility.js
'
);
tcpDetector
=
require
(
'
./tcp-protocol-detector.js
'
);
// 三方库
// 三方库
_
=
global
.
_
=
require
(
'
underscore
'
);
_
=
global
.
_
=
require
(
'
underscore
'
);
...
@@ -348,7 +350,7 @@
...
@@ -348,7 +350,7 @@
};
};
init
=
async
function
()
{
init
=
async
function
()
{
var
AthleticChecker
,
Challonge
,
DataManager
,
chat_color
,
config
,
cppversion
,
defaultConfig
,
default_data
,
dirPath
,
dns
,
e
,
get_rooms_count
,
http_server
,
https
,
httpsOptions
,
https_server
,
imported
,
j
,
key
,
keysFromEnv
,
l
,
len
,
len1
,
len2
,
m
,
main
_http_server
,
mkdirList
,
neosHttpServer
,
neosWsServer
,
plugin_filename
,
plugin_list
,
plugin_path
,
settingKey
,
val
,
valFromDefault
,
ws
;
var
AthleticChecker
,
Challonge
,
DataManager
,
chat_color
,
config
,
cppversion
,
defaultConfig
,
default_data
,
dirPath
,
dns
,
e
,
get_rooms_count
,
http_server
,
https
,
httpsOptions
,
https_server
,
imported
,
j
,
key
,
keysFromEnv
,
l
,
len
,
len1
,
len2
,
m
,
main
TcpServer
,
main_http_server
,
mkdirList
,
neosHttpServer
,
neosReuseMainPort
,
neosWsServer
,
plugin_filename
,
plugin_list
,
plugin_path
,
settingKey
,
val
,
valFromDefault
,
ws
;
log
.
info
(
'
Reading config.
'
);
log
.
info
(
'
Reading config.
'
);
await
createDirectoryIfNotExists
(
"
./config
"
);
await
createDirectoryIfNotExists
(
"
./config
"
);
await
importOldConfig
();
await
importOldConfig
();
...
@@ -815,20 +817,67 @@
...
@@ -815,20 +817,67 @@
return
results
;
return
results
;
},
1000
);
},
1000
);
log
.
info
(
"
Starting server.
"
);
log
.
info
(
"
Starting server.
"
);
net
.
createServer
(
netRequestHandler
).
listen
(
settings
.
port
,
function
()
{
log
.
info
(
"
server started
"
,
settings
.
port
);
// 用于存储 neos 相关的服务器对象
});
neosHttpServer
=
null
;
neosWsServer
=
null
;
// 检查是否需要在主端口上复用检测 HTTP/HTTPS
neosReuseMainPort
=
settings
.
modules
.
neos
.
enabled
&&
(
settings
.
modules
.
neos
.
port
===
settings
.
port
||
settings
.
modules
.
neos
.
reuse_port
);
if
(
neosReuseMainPort
)
{
// 需要复用主端口,创建 neos HTTP 服务器但不监听端口
log
.
info
(
`neos will reuse main port
${
settings
.
port
}
`
);
ws
=
require
(
'
ws
'
);
if
(
settings
.
modules
.
http
.
ssl
.
enabled
)
{
https
=
require
(
'
https
'
);
httpsOptions
=
{
cert
:
(
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
cert
)),
key
:
(
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
key
))
};
neosHttpServer
=
https
.
createServer
(
httpsOptions
);
}
else
{
neosHttpServer
=
http
.
createServer
();
}
neosWsServer
=
new
ws
.
WebSocketServer
({
server
:
neosHttpServer
});
neosWsServer
.
on
(
'
connection
'
,
neosRequestListener
);
// 创建主服务器,带协议检测
mainTcpServer
=
net
.
createServer
(
function
(
socket
)
{
var
isHttpsMode
;
isHttpsMode
=
settings
.
modules
.
http
.
ssl
.
enabled
;
// HTTP/HTTPS 处理器
return
tcpDetector
.
detectAndHandle
(
socket
,
function
(
sock
,
firstChunk
)
{
// 将 socket 交给 neos HTTP 服务器处理
return
neosHttpServer
.
emit
(
'
connection
'
,
sock
);
// 默认处理器(YGOPro 协议)
},
function
(
sock
)
{
return
netRequestHandler
(
sock
);
},
isHttpsMode
);
});
mainTcpServer
.
listen
(
settings
.
port
,
function
()
{
return
log
.
info
(
"
server started with neos port reuse
"
,
settings
.
port
);
});
}
else
{
// 不需要复用,直接创建普通的 TCP 服务器
net
.
createServer
(
netRequestHandler
).
listen
(
settings
.
port
,
function
()
{
log
.
info
(
"
server started
"
,
settings
.
port
);
});
}
if
(
settings
.
modules
.
stop
)
{
if
(
settings
.
modules
.
stop
)
{
log
.
info
(
"
NOTE: server not open due to config,
"
,
settings
.
modules
.
stop
);
log
.
info
(
"
NOTE: server not open due to config,
"
,
settings
.
modules
.
stop
);
}
}
http_server
=
http
.
createServer
(
httpRequestListener
);
http_server
=
http
.
createServer
(
httpRequestListener
);
main_http_server
=
http_server
;
main_http_server
=
http_server
;
if
(
settings
.
modules
.
http
.
ssl
.
enabled
)
{
if
(
settings
.
modules
.
http
.
ssl
.
enabled
)
{
https
=
require
(
'
https
'
);
if
(
!
neosReuseMainPort
)
{
// 如果没有在上面创建 https 相关对象
httpsOptions
=
{
https
=
require
(
'
https
'
);
cert
:
(
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
cert
)),
httpsOptions
=
{
key
:
(
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
key
))
cert
:
(
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
cert
)),
};
key
:
(
await
fs
.
promises
.
readFile
(
settings
.
modules
.
http
.
ssl
.
key
))
};
}
https_server
=
https
.
createServer
(
httpsOptions
,
httpRequestListener
);
https_server
=
https
.
createServer
(
httpsOptions
,
httpRequestListener
);
https_server
.
listen
(
settings
.
modules
.
http
.
ssl
.
port
);
https_server
.
listen
(
settings
.
modules
.
http
.
ssl
.
port
);
main_http_server
=
https_server
;
main_http_server
=
https_server
;
...
@@ -837,7 +886,8 @@
...
@@ -837,7 +886,8 @@
roomlist
.
init
(
main_http_server
,
ROOM_all
);
roomlist
.
init
(
main_http_server
,
ROOM_all
);
}
}
http_server
.
listen
(
settings
.
modules
.
http
.
port
);
http_server
.
listen
(
settings
.
modules
.
http
.
port
);
if
(
settings
.
modules
.
neos
.
enabled
)
{
if
(
settings
.
modules
.
neos
.
enabled
&&
!
neosReuseMainPort
)
{
// neos 启用但不复用主端口,单独监听
ws
=
require
(
'
ws
'
);
ws
=
require
(
'
ws
'
);
neosHttpServer
=
null
;
neosHttpServer
=
null
;
if
(
settings
.
modules
.
http
.
ssl
.
enabled
)
{
if
(
settings
.
modules
.
http
.
ssl
.
enabled
)
{
...
@@ -850,6 +900,7 @@
...
@@ -850,6 +900,7 @@
});
});
neosWsServer
.
on
(
'
connection
'
,
neosRequestListener
);
neosWsServer
.
on
(
'
connection
'
,
neosRequestListener
);
neosHttpServer
.
listen
(
settings
.
modules
.
neos
.
port
);
neosHttpServer
.
listen
(
settings
.
modules
.
neos
.
port
);
log
.
info
(
`neos listening on separate port
${
settings
.
modules
.
neos
.
port
}
`
);
}
}
mkdirList
=
[
"
./plugins
"
,
settings
.
modules
.
tournament_mode
.
deck_path
,
settings
.
modules
.
tournament_mode
.
replay_path
,
settings
.
modules
.
tournament_mode
.
log_save_path
,
settings
.
modules
.
deck_log
.
local
];
mkdirList
=
[
"
./plugins
"
,
settings
.
modules
.
tournament_mode
.
deck_path
,
settings
.
modules
.
tournament_mode
.
replay_path
,
settings
.
modules
.
tournament_mode
.
log_save_path
,
settings
.
modules
.
deck_log
.
local
];
for
(
l
=
0
,
len1
=
mkdirList
.
length
;
l
<
len1
;
l
++
)
{
for
(
l
=
0
,
len1
=
mkdirList
.
length
;
l
<
len1
;
l
++
)
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment