Commit 81fea176 authored by mercury233's avatar mercury233

merge

parent c5b16dea
{
"port": 2333,
"version": 4921,
"port": 7911,
"ygopro_path": "ygopro",
"modules": {
"welcome": "YGOPRO Server",
......@@ -9,13 +8,21 @@
"tips": "http://mercury233.me/ygosrv233/tips.json",
"dialogues": "http://mercury233.me/ygosrv233/dialogues.json",
"redis_port": 6379,
"enable_websocket_roomlist": false,
"enable_random_duel": false,
"mycard_auth": false,
"post_start_watching": true,
"TCG_banlist_id": 8,
"enable_TCG_as_default": false,
"http": {
"port": 7922,
"password": "123456"
"password": "123456",
"ssl": {
"enabled": false,
"port": 7923,
"cert": "ssl/ygopro-server.crt",
"key": "ssl/ygopro-server.key"
}
}
}
}
......@@ -2,10 +2,7 @@
"name": "ygopro-server",
"version": "2.3.3",
"description": "a server for ygopro",
"repository": {
"type": "git",
"url": "https://github.com/mercury233/ygopro-server.git"
},
"repository": "github:mercury233/ygopro-server",
"keywords": [
"mycard",
"ygopro",
......@@ -13,18 +10,17 @@
],
"author": "zh99998 <zh99998@gmail.com>, mercury233 <me@mercury233.me>",
"dependencies": {
"underscore": "*",
"underscore.string": "*",
"request": "*",
"moment": "*",
"bunyan": "*"
"underscore": "latest",
"underscore.string": "latest",
"request": "latest",
"moment": "latest",
"sqlite3": "latest",
"bunyan": "latest",
"ws": "latest",
"pg": "latest"
},
"license": "GPL-3.0",
"main": "ygopro-server.js",
"license": "AGPL-3.0",
"scripts": {
"start": "pm2 start ygopro-server.js"
},
"engines": {
"node": "*"
"start": "node ygopro-server.js"
}
}
......@@ -4,6 +4,7 @@ _.mixin(_.str.exports());
spawn = require('child_process').spawn
spawnSync = require('child_process').spawnSync
ygopro = require './ygopro.js'
roomlist = require './roomlist' if settings.modules.enable_websocket_roomlist
bunyan = require 'bunyan'
moment = require 'moment'
#redis = require 'redis'
......@@ -134,7 +135,7 @@ class Room
room_pass = room_name_and_pass[1]
client_name == room_name and client_pass != room_pass
constructor: (name) ->
constructor: (name, @hostinfo) ->
@name = name
@alive = true
@players = []
......@@ -148,7 +149,7 @@ class Room
@welcome = ''
Room.all.push this
@hostinfo =
@hostinfo ||=
lflist: 0
rule: if settings.modules.enable_TCG_as_default then 2 else 0
mode: 0
......@@ -308,6 +309,7 @@ class Room
@process.stdout.setEncoding('utf8')
@process.stdout.once 'data', (data)=>
@established = true
roomlist.create(this) if !@private and settings.modules.enable_websocket_roomlist
@port = parseInt data
_.each @players, (player)=>
player.server.connect @port, '127.0.0.1',=>
......@@ -350,6 +352,7 @@ class Room
index = _.indexOf(Room.all, this)
#Room.all[index] = null unless index == -1
Room.all.splice(index, 1) unless index == -1
roomlist.delete @name if !@private and !@started and @established and settings.modules.enable_websocket_roomlist
return
get_playing_player: ->
......@@ -380,6 +383,7 @@ class Room
Room.players_oppentlist[client.remoteAddress] = null
if @established
roomlist.update(this) if !@private and !@started and settings.modules.enable_websocket_roomlist
client.server.connect @port, '127.0.0.1', ->
client.server.write buffer for buffer in client.pre_establish_buffers
client.established = true
......@@ -401,6 +405,7 @@ class Room
Room.ban_player(client.name, client.ip, "强退")
if @players.length
ygopro.stoc_send_chat_to_room this, "#{client.name} #{'离开了游戏'}#{if error then ": #{error}" else ''}"
roomlist.update(this) if !@private and !@started and settings.modules.enable_websocket_roomlist
#client.room = null
else
@process.kill()
......
// Generated by CoffeeScript 1.10.0
(function() {
var Room, _, bunyan, get_memory_usage, log, moment, settings, spawn, spawnSync, ygopro;
var Room, _, bunyan, get_memory_usage, log, moment, roomlist, settings, spawn, spawnSync, ygopro;
_ = require('underscore');
......@@ -14,6 +14,10 @@
ygopro = require('./ygopro.js');
if (settings.modules.enable_websocket_roomlist) {
roomlist = require('./roomlist');
}
bunyan = require('bunyan');
moment = require('moment');
......@@ -184,8 +188,9 @@
});
};
function Room(name) {
function Room(name, hostinfo) {
var draw_count, error1, lflist, param, rule, start_hand, start_lp, time_limit;
this.hostinfo = hostinfo;
this.name = name;
this.alive = true;
this.players = [];
......@@ -198,7 +203,7 @@
this.random_type = '';
this.welcome = '';
Room.all.push(this);
this.hostinfo = {
this.hostinfo || (this.hostinfo = {
lflist: 0,
rule: settings.modules.enable_TCG_as_default ? 2 : 0,
mode: 0,
......@@ -209,7 +214,7 @@
start_hand: 5,
draw_count: 1,
time_limit: 180
};
});
if (name.slice(0, 2) === 'M#') {
this.hostinfo.mode = 1;
} else if (name.slice(0, 2) === 'T#') {
......@@ -391,6 +396,9 @@
this.process.stdout.once('data', (function(_this) {
return function(data) {
_this.established = true;
if (!_this["private"] && settings.modules.enable_websocket_roomlist) {
roomlist.create(_this);
}
_this.port = parseInt(data);
_.each(_this.players, function(player) {
player.server.connect(_this.port, '127.0.0.1', function() {
......@@ -447,6 +455,9 @@
if (index !== -1) {
Room.all.splice(index, 1);
}
if (!this["private"] && !this.started && this.established && settings.modules.enable_websocket_roomlist) {
roomlist["delete"](this.name);
}
};
Room.prototype.get_playing_player = function() {
......@@ -489,6 +500,9 @@
}
}
if (this.established) {
if (!this["private"] && !this.started && settings.modules.enable_websocket_roomlist) {
roomlist.update(this);
}
client.server.connect(this.port, '127.0.0.1', function() {
var buffer, i, len, ref;
ref = client.pre_establish_buffers;
......@@ -520,6 +534,9 @@
}
if (this.players.length) {
ygopro.stoc_send_chat_to_room(this, client.name + " " + '离开了游戏' + (error ? ": " + error : ''));
if (!this["private"] && !this.started && settings.modules.enable_websocket_roomlist) {
roomlist.update(this);
}
} else {
this.process.kill();
this["delete"]();
......
WebSocketServer = require('ws').Server;
server = null
room_data = (room)->
id: room.name,
title: room.title,
user: {username: room.username}
users: ({username: client.name, position: client.pos} for client in room.players),
options: room.hostinfo
init = (http_server, Room)->
server = new WebSocketServer
server: http_server
server.on 'connection', (connection) ->
connection.send JSON.stringify
event: 'init'
data: room_data(room) for room in Room.all when room.established and !room.private and !room.started
create = (room)->
broadcast('create', room_data(room))
update = (room)->
broadcast('update', room_data(room))
_delete = (room_id)->
broadcast('delete', room_id)
broadcast = (event, data)->
return if !server
message = JSON.stringify
event: event
data: data
for connection in server.clients
try
connection.send message
module.exports =
init: init
create: create
update: update
delete: _delete
\ No newline at end of file
// Generated by CoffeeScript 1.10.0
(function() {
var WebSocketServer, _delete, broadcast, create, init, room_data, server, update;
WebSocketServer = require('ws').Server;
server = null;
room_data = function(room) {
var client;
return {
id: room.name,
title: room.title,
user: {
username: room.username
},
users: (function() {
var i, len, ref, results;
ref = room.players;
results = [];
for (i = 0, len = ref.length; i < len; i++) {
client = ref[i];
results.push({
username: client.name,
position: client.pos
});
}
return results;
})(),
options: room.hostinfo
};
};
init = function(http_server, Room) {
server = new WebSocketServer({
server: http_server
});
return server.on('connection', function(connection) {
var room;
return connection.send(JSON.stringify({
event: 'init',
data: (function() {
var i, len, ref, results;
ref = Room.all;
results = [];
for (i = 0, len = ref.length; i < len; i++) {
room = ref[i];
if (room.established && !room["private"] && !room.started) {
results.push(room_data(room));
}
}
return results;
})()
}));
});
};
create = function(room) {
return broadcast('create', room_data(room));
};
update = function(room) {
return broadcast('update', room_data(room));
};
_delete = function(room_id) {
return broadcast('delete', room_id);
};
broadcast = function(event, data) {
var connection, i, len, message, ref, results;
if (!server) {
return;
}
message = JSON.stringify({
event: event,
data: data
});
ref = server.clients;
results = [];
for (i = 0, len = ref.length; i < len; i++) {
connection = ref[i];
try {
results.push(connection.send(message));
} catch (undefined) {}
}
return results;
};
module.exports = {
init: init,
create: create,
update: update,
"delete": _delete
};
}).call(this);
......@@ -5,6 +5,7 @@ url = require 'url'
path = require 'path'
fs = require 'fs'
os = require 'os'
crypto = require 'crypto'
execFile = require('child_process').execFile
#三方库
......@@ -28,11 +29,14 @@ settings = require './config.json'
settings.BANNED_user = []
settings.BANNED_IP = []
settings.modules.hang_timeout=90
settings.version = parseInt(fs.readFileSync('ygopro/gframe/game.cpp', 'utf8').match(/PRO_VERSION = ([x\d]+)/)[1], '16')
#组件
ygopro = require './ygopro.js'
Room = require './room.js'
roomlist = require './roomlist.js' if settings.modules.enable_websocket_roomlist
users_cache = {}
#debug模式 端口号+1
debug = false
......@@ -315,7 +319,144 @@ ygopro.ctos_follow 'JOIN_GAME', false, (buffer, info, client, server)->
code: 2
}
client.end()
else if info.pass.length and settings.modules.mycard_auth
ygopro.stoc_send_chat(client,'正在读取用户信息...', 11)
if info.pass.length <= 8
ygopro.stoc_send_chat(client,'主机密码不正确 (Invalid Length)', 11)
ygopro.stoc_send client, 'ERROR_MSG',{
msg: 1
code: 2
}
client.end()
return
buffer = new Buffer(info.pass[0...8], 'base64')
if buffer.length != 6
ygopro.stoc_send_chat(client,'主机密码不正确 (Invalid Payload Length)', 11)
ygopro.stoc_send client, 'ERROR_MSG',{
msg: 1
code: 2
}
client.end()
return
check = (buf)->
checksum = 0
for i in [0...buf.length]
checksum += buf.readUInt8(i)
(checksum & 0xFF) == 0
finish = (buffer)->
action = buffer.readUInt8(1) >> 4
if buffer != decrypted_buffer and action in [1,2,4]
ygopro.stoc_send_chat(client,'主机密码不正确 (Unauthorized)', 11)
ygopro.stoc_send client, 'ERROR_MSG',{
msg: 1
code: 2
}
client.end()
return
# 1 create public room
# 2 create private room
# 3 join room
# 4 join match
switch action
when 1,2
name = crypto.createHash('md5').update(info.pass + client.name).digest('base64')[0...10].replace('+','-').replace('/', '_');
if Room.find_by_name(name)
ygopro.stoc_send_chat(client,'主机密码不正确 (Already Existed)', 11)
ygopro.stoc_send client, 'ERROR_MSG',{
msg: 1
code: 2
}
client.end()
return
opt1 = buffer.readUInt8(2)
opt2 = buffer.readUInt16LE(3)
opt3 = buffer.readUInt8(5)
options = {
lflist: 0
time_limit: 180
rule: (opt1 >> 5) & 3
mode: (opt1 >> 3) & 3
enable_priority: !!((opt1 >> 2) & 1)
no_check_deck: !!((opt1 >> 1) & 1)
no_shuffle_deck: !!(opt1 & 1)
start_lp: opt2
start_hand: opt3 >> 4
draw_count: opt3 & 0xF
}
room = new Room(name, options)
room.title = info.pass.slice(8).replace(String.fromCharCode(0xFEFF), ' ')
room.private = action == 2
when 3
name = info.pass.slice(8)
room = Room.find_by_name(name)
if(!room)
ygopro.stoc_send_chat(client,'主机密码不正确 (Not Found)', 11)
ygopro.stoc_send client, 'ERROR_MSG',{
msg: 1
code: 2
}
client.end()
return
when 4
room = Room.find_or_create_by_name('M#' + info.pass.slice(8))
room.private = true
else
ygopro.stoc_send_chat(client,'主机密码不正确 (Invalid Action)', 11)
ygopro.stoc_send client, 'ERROR_MSG',{
msg: 1
code: 2
}
client.end()
return
client.room = room
client.room.connect(client)
if id = users_cache[client.name]
secret = id % 65535 + 1;
decrypted_buffer = new Buffer(6)
for i in [0,2,4]
decrypted_buffer.writeUInt16LE(buffer.readUInt16LE(i) ^ secret, i)
if check(decrypted_buffer)
return finish(decrypted_buffer)
#TODO: query database directly, like preload.
request
baseUrl: settings.modules.mycard_auth,
url: '/users/' + encodeURIComponent(client.name) + '.json',
qs:
api_key: 'dc7298a754828b3d26b709f035a0eeceb43e73cbd8c4fa8dec18951f8a95d2bc',
api_username: client.name,
skip_track_visit: true
json: true
, (error, response, body)->
if body and body.user
secret = body.user.id % 65535 + 1;
decrypted_buffer = new Buffer(6)
for i in [0,2,4]
decrypted_buffer.writeUInt16LE(buffer.readUInt16LE(i) ^ secret, i)
if check(decrypted_buffer)
buffer = decrypted_buffer
# buffer != decrypted_buffer ==> auth failed
if !check(buffer)
ygopro.stoc_send_chat(client,'主机密码不正确 (Checksum Failed)', 11)
ygopro.stoc_send client, 'ERROR_MSG',{
msg: 1
code: 2
}
client.end()
return
users_cache[client.name] = body.user.id
finish(buffer)
else if info.pass.length && !Room.validate(info.pass)
#ygopro.stoc_send client, 'ERROR_MSG',{
# msg: 1
......@@ -575,10 +716,22 @@ if settings.modules.tips
#log.info "tips loaded", tips.length
return
if settings.modules.mycard_auth and process.env.MYCARD_AUTH_DATABASE
pg = require('pg');
pg.connect process.env.MYCARD_AUTH_DATABASE, (error, client, done)->
if(error)
return console.error('error fetching client from pool', err);
client.query 'SELECT username, id from users', (error, result)->
done();
for row in result.rows
users_cache[row.username] = row.id
console.log("users loaded", _.keys(users_cache).length)
ygopro.stoc_follow 'DUEL_START', false, (buffer, info, client, server)->
return unless client.room
unless client.room.started #first start
client.room.started = true
roomlist.delete client.room.name if settings.modules.enable_websocket_roomlist and not client.room.private
#client.room.duels = []
client.room.dueling_players = []
for player in client.room.players when player.pos != 7
......@@ -678,66 +831,78 @@ setInterval ()->
#http
if settings.modules.http
http_server = http.createServer (request, response)->
parseQueryString = true
u = url.parse(request.url, parseQueryString)
pass_validated = u.query.pass == settings.modules.http.password
if u.pathname == '/api/getrooms'
if !pass_validated
response.writeHead(200);
response.end(u.query.callback+'( {"rooms":[{"roomid":"0","roomname":"密码错误","needpass":"true"}]} );')
else
response.writeHead(200);
roomsjson = JSON.stringify rooms: (for room in Room.all when room.established
pid: room.process.pid.toString(),
roomid: room.port.toString(),
roomname: if pass_validated then room.name else room.name.split('$',2)[0],
needpass: (room.name.indexOf('$') != -1).toString(),
users: (for player in room.players when player.pos?
id: (-1).toString(),
name: player.name,
pos: player.pos
),
istart: if room.started then 'start' else 'wait'
)
response.end(u.query.callback+"( " + roomsjson + " );")
else if u.pathname == '/api/message'
if !pass_validated
response.writeHead(200);
response.end(u.query.callback+"( '密码错误', 0 );");
return
if u.query.shout
for room in Room.all
ygopro.stoc_send_chat_to_room(room, u.query.shout, 16)
response.writeHead(200)
response.end(u.query.callback+"( 'shout ok', '" + u.query.shout + "' );")
else if u.query.stop
if u.query.stop == 'false'
u.query.stop=false
settings.modules.stop = u.query.stop
response.writeHead(200)
response.end(u.query.callback+"( 'stop ok', '" + u.query.stop + "' );")
else if u.query.welcome
settings.modules.welcome = u.query.welcome
response.writeHead(200)
response.end(u.query.callback+"( 'welcome ok', '" + u.query.welcome + "' );")
else if u.query.ban
settings.BANNED_user.push(u.query.ban)
response.writeHead(200)
response.end(u.query.callback+"( 'ban ok', '" + u.query.ban + "' );")
else
response.writeHead(404);
response.end();
requestListener = (request, response)->
parseQueryString = true
u = url.parse(request.url, parseQueryString)
pass_validated = u.query.pass == settings.modules.http.password
if u.pathname == '/api/getrooms'
if u.query.pass and !pass_validated
response.writeHead(200);
response.end(u.query.callback+'( {"rooms":[{"roomid":"0","roomname":"密码错误","needpass":"true"}]} );')
else
response.writeHead(200);
roomsjson = JSON.stringify rooms: (for room in Room.all when room.established
pid: room.process.pid.toString(),
roomid: room.port.toString(),
roomname: if pass_validated then room.name else room.name.split('$',2)[0],
needpass: (room.name.indexOf('$') != -1).toString(),
users: (for player in room.players when player.pos?
id: (-1).toString(),
name: player.name,
pos: player.pos
),
istart: if room.started then 'start' else 'wait'
)
response.end(u.query.callback+"( " + roomsjson + " );")
else if u.pathname == '/api/message'
if !pass_validated
response.writeHead(200);
response.end(u.query.callback+"( '密码错误', 0 );");
return
if u.query.shout
for room in Room.all
ygopro.stoc_send_chat_to_room(room, u.query.shout, 16)
response.writeHead(200)
response.end(u.query.callback+"( 'shout ok', '" + u.query.shout + "' );")
else if u.query.stop
if u.query.stop == 'false'
u.query.stop=false
settings.modules.stop = u.query.stop
response.writeHead(200)
response.end(u.query.callback+"( 'stop ok', '" + u.query.stop + "' );")
else if u.query.welcome
settings.modules.welcome = u.query.welcome
response.writeHead(200)
response.end(u.query.callback+"( 'welcome ok', '" + u.query.welcome + "' );")
else if u.query.ban
settings.BANNED_user.push(u.query.ban)
response.writeHead(200)
response.end(u.query.callback+"( 'ban ok', '" + u.query.ban + "' );")
else
response.writeHead(404);
response.end();
return
else
response.writeHead(404);
response.end();
return
http_server = http.createServer(requestListener)
http_server.listen settings.modules.http.port
if settings.modules.http.ssl.enabled
https = require 'https'
options =
cert: fs.readFileSync(settings.modules.http.ssl.cert)
key: fs.readFileSync(settings.modules.http.ssl.key)
https_server = https.createServer(options, requestListener)
roomlist.init https_server, Room
https_server.listen settings.modules.http.ssl.port
\ No newline at end of file
// Generated by CoffeeScript 1.10.0
(function() {
var Graveyard, Room, _, bunyan, debug, dialogues, execFile, fs, http, http_server, log, moment, net, os, path, request, settings, tips, tribute, url, wait_room_start, ygopro;
var Graveyard, Room, _, bunyan, crypto, debug, dialogues, execFile, fs, http, http_server, https, https_server, log, moment, net, options, os, path, pg, request, requestListener, roomlist, settings, tips, tribute, url, users_cache, wait_room_start, ygopro;
net = require('net');
......@@ -14,6 +14,8 @@
os = require('os');
crypto = require('crypto');
execFile = require('child_process').execFile;
_ = require('underscore');
......@@ -36,10 +38,18 @@
settings.modules.hang_timeout = 90;
settings.version = parseInt(fs.readFileSync('ygopro/gframe/game.cpp', 'utf8').match(/PRO_VERSION = ([x\d]+)/)[1], '16');
ygopro = require('./ygopro.js');
Room = require('./room.js');
if (settings.modules.enable_websocket_roomlist) {
roomlist = require('./roomlist.js');
}
users_cache = {};
debug = false;
log = null;
......@@ -283,7 +293,7 @@
});
ygopro.ctos_follow('JOIN_GAME', false, function(buffer, info, client, server) {
var k, len, ref, room;
var check, decrypted_buffer, finish, i, id, k, l, len, len1, ref, ref1, room, secret;
if (settings.modules.stop) {
ygopro.stoc_send_chat(client, settings.modules.stop, 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
......@@ -340,6 +350,155 @@
code: 2
});
client.end();
} else if (info.pass.length && settings.modules.mycard_auth) {
ygopro.stoc_send_chat(client, '正在读取用户信息...', 11);
if (info.pass.length <= 8) {
ygopro.stoc_send_chat(client, '主机密码不正确 (Invalid Length)', 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
msg: 1,
code: 2
});
client.end();
return;
}
buffer = new Buffer(info.pass.slice(0, 8), 'base64');
if (buffer.length !== 6) {
ygopro.stoc_send_chat(client, '主机密码不正确 (Invalid Payload Length)', 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
msg: 1,
code: 2
});
client.end();
return;
}
check = function(buf) {
var checksum, i, k, ref;
checksum = 0;
for (i = k = 0, ref = buf.length; 0 <= ref ? k < ref : k > ref; i = 0 <= ref ? ++k : --k) {
checksum += buf.readUInt8(i);
}
return (checksum & 0xFF) === 0;
};
finish = function(buffer) {
var action, name, opt1, opt2, opt3, options, room;
action = buffer.readUInt8(1) >> 4;
if (buffer !== decrypted_buffer && (action === 1 || action === 2 || action === 4)) {
ygopro.stoc_send_chat(client, '主机密码不正确 (Unauthorized)', 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
msg: 1,
code: 2
});
client.end();
return;
}
switch (action) {
case 1:
case 2:
name = crypto.createHash('md5').update(info.pass + client.name).digest('base64').slice(0, 10).replace('+', '-').replace('/', '_');
if (Room.find_by_name(name)) {
ygopro.stoc_send_chat(client, '主机密码不正确 (Already Existed)', 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
msg: 1,
code: 2
});
client.end();
return;
}
opt1 = buffer.readUInt8(2);
opt2 = buffer.readUInt16LE(3);
opt3 = buffer.readUInt8(5);
options = {
lflist: 0,
time_limit: 180,
rule: (opt1 >> 5) & 3,
mode: (opt1 >> 3) & 3,
enable_priority: !!((opt1 >> 2) & 1),
no_check_deck: !!((opt1 >> 1) & 1),
no_shuffle_deck: !!(opt1 & 1),
start_lp: opt2,
start_hand: opt3 >> 4,
draw_count: opt3 & 0xF
};
room = new Room(name, options);
room.title = info.pass.slice(8).replace(String.fromCharCode(0xFEFF), ' ');
room["private"] = action === 2;
break;
case 3:
name = info.pass.slice(8);
room = Room.find_by_name(name);
if (!room) {
ygopro.stoc_send_chat(client, '主机密码不正确 (Not Found)', 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
msg: 1,
code: 2
});
client.end();
return;
}
break;
case 4:
room = Room.find_or_create_by_name('M#' + info.pass.slice(8));
room["private"] = true;
break;
default:
ygopro.stoc_send_chat(client, '主机密码不正确 (Invalid Action)', 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
msg: 1,
code: 2
});
client.end();
return;
}
client.room = room;
return client.room.connect(client);
};
if (id = users_cache[client.name]) {
secret = id % 65535 + 1;
decrypted_buffer = new Buffer(6);
ref = [0, 2, 4];
for (k = 0, len = ref.length; k < len; k++) {
i = ref[k];
decrypted_buffer.writeUInt16LE(buffer.readUInt16LE(i) ^ secret, i);
}
if (check(decrypted_buffer)) {
return finish(decrypted_buffer);
}
}
request({
baseUrl: settings.modules.mycard_auth,
url: '/users/' + encodeURIComponent(client.name) + '.json',
qs: {
api_key: 'dc7298a754828b3d26b709f035a0eeceb43e73cbd8c4fa8dec18951f8a95d2bc',
api_username: client.name,
skip_track_visit: true
},
json: true
}, function(error, response, body) {
var l, len1, ref1;
if (body && body.user) {
secret = body.user.id % 65535 + 1;
decrypted_buffer = new Buffer(6);
ref1 = [0, 2, 4];
for (l = 0, len1 = ref1.length; l < len1; l++) {
i = ref1[l];
decrypted_buffer.writeUInt16LE(buffer.readUInt16LE(i) ^ secret, i);
}
if (check(decrypted_buffer)) {
buffer = decrypted_buffer;
}
}
if (!check(buffer)) {
ygopro.stoc_send_chat(client, '主机密码不正确 (Checksum Failed)', 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
msg: 1,
code: 2
});
client.end();
return;
}
users_cache[client.name] = body.user.id;
return finish(buffer);
});
} else if (info.pass.length && !Room.validate(info.pass)) {
ygopro.stoc_send_chat(client, "房间密码不正确", 11);
ygopro.stoc_send(client, 'ERROR_MSG', {
......@@ -393,9 +552,9 @@
ygopro.stoc_send_chat_to_room(client.room, client.name + " 加入了观战");
client.room.watchers.push(client);
ygopro.stoc_send_chat(client, "观战中", 14);
ref = client.room.watcher_buffers;
for (k = 0, len = ref.length; k < len; k++) {
buffer = ref[k];
ref1 = client.room.watcher_buffers;
for (l = 0, len1 = ref1.length; l < len1; l++) {
buffer = ref1[l];
client.write(buffer);
}
} else {
......@@ -653,6 +812,25 @@
});
}
if (settings.modules.mycard_auth && process.env.MYCARD_AUTH_DATABASE) {
pg = require('pg');
pg.connect(process.env.MYCARD_AUTH_DATABASE, function(error, client, done) {
if (error) {
return console.error('error fetching client from pool', err);
}
return client.query('SELECT username, id from users', function(error, result) {
var k, len, ref, row;
done();
ref = result.rows;
for (k = 0, len = ref.length; k < len; k++) {
row = ref[k];
users_cache[row.username] = row.id;
}
return console.log("users loaded", _.keys(users_cache).length);
});
});
}
ygopro.stoc_follow('DUEL_START', false, function(buffer, info, client, server) {
var k, len, player, ref;
if (!client.room) {
......@@ -660,6 +838,9 @@
}
if (!client.room.started) {
client.room.started = true;
if (settings.modules.enable_websocket_roomlist && !client.room["private"]) {
roomlist["delete"](client.room.name);
}
client.room.dueling_players = [];
ref = client.room.players;
for (k = 0, len = ref.length; k < len; k++) {
......@@ -812,13 +993,13 @@
}, 1000);
if (settings.modules.http) {
http_server = http.createServer(function(request, response) {
requestListener = function(request, response) {
var k, len, parseQueryString, pass_validated, player, ref, room, roomsjson, u;
parseQueryString = true;
u = url.parse(request.url, parseQueryString);
pass_validated = u.query.pass === settings.modules.http.password;
if (u.pathname === '/api/getrooms') {
if (!pass_validated) {
if (u.query.pass && !pass_validated) {
response.writeHead(200);
response.end(u.query.callback + '( {"rooms":[{"roomid":"0","roomname":"密码错误","needpass":"true"}]} );');
} else {
......@@ -898,8 +1079,19 @@
response.writeHead(404);
response.end();
}
});
};
http_server = http.createServer(requestListener);
http_server.listen(settings.modules.http.port);
if (settings.modules.http.ssl.enabled) {
https = require('https');
options = {
cert: fs.readFileSync(settings.modules.http.ssl.cert),
key: fs.readFileSync(settings.modules.http.ssl.key)
};
https_server = https.createServer(options, requestListener);
roomlist.init(https_server, Room);
https_server.listen(settings.modules.http.ssl.port);
}
}
}).call(this);
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment