mirror of
https://github.com/PrismarineJS/node-minecraft-protocol.git
synced 2025-05-18 01:00:27 -04:00
don't require both email and username. closes #32
This change breaks backwards compatibility. `createClient` no longer takes an `email` argument. Instead, the `username` argument is used to authenticate and determine the case correct username. There is a special case if you leave out the `password` argument. In this case, `username` is used to connect directly to the server, and you may get kicked if the server is in online mode.
This commit is contained in:
parent
9c12b6d3d3
commit
df3f95e1ff
4 changed files with 49 additions and 49 deletions
13
README.md
13
README.md
|
@ -34,11 +34,10 @@ no more. If you want a higher-level API with which to write bots, see
|
||||||
```js
|
```js
|
||||||
var mc = require('minecraft-protocol');
|
var mc = require('minecraft-protocol');
|
||||||
var client = mc.createClient({
|
var client = mc.createClient({
|
||||||
host: "localhost", // optional
|
host: "localhost", // optional
|
||||||
port: 25565, // optional
|
port: 25565, // optional
|
||||||
username: "player",
|
username: "email@example.com",
|
||||||
email: "email@example.com", // email and password are required only for
|
password: "12345678",
|
||||||
password: "12345678", // online-mode=true servers
|
|
||||||
});
|
});
|
||||||
client.on(0x03, function(packet) {
|
client.on(0x03, function(packet) {
|
||||||
// Listen for chat messages and echo them back.
|
// Listen for chat messages and echo them back.
|
||||||
|
@ -49,6 +48,8 @@ client.on(0x03, function(packet) {
|
||||||
});
|
});
|
||||||
```
|
```
|
||||||
|
|
||||||
|
If the server is in offline mode, you may leave out the `password` option.
|
||||||
|
|
||||||
### Hello World server example
|
### Hello World server example
|
||||||
|
|
||||||
```js
|
```js
|
||||||
|
@ -128,7 +129,7 @@ correct data type.
|
||||||
|
|
||||||
* Ensure your system has the `java` executable in `PATH`.
|
* Ensure your system has the `java` executable in `PATH`.
|
||||||
* Download the appropriate version of `minecraft_server.jar`.
|
* Download the appropriate version of `minecraft_server.jar`.
|
||||||
* `MC_SERVER_JAR=path/to/minecraft_server.jar MC_USERNAME=username MC_EMAIL=email@example.com MC_PASSWORD=password npm test`
|
* `MC_SERVER_JAR=path/to/minecraft_server.jar MC_EMAIL=email@example.com MC_PASSWORD=password npm test`
|
||||||
|
|
||||||
### Test Coverage
|
### Test Coverage
|
||||||
|
|
||||||
|
|
|
@ -1,9 +1,7 @@
|
||||||
var mc = require('../');
|
var mc = require('../');
|
||||||
var client = mc.createClient({
|
var client = mc.createClient({
|
||||||
username: process.env.MC_USERNAME,
|
username: process.env.MC_USERNAME,
|
||||||
email: process.env.MC_EMAIL,
|
|
||||||
password: process.env.MC_PASSWORD,
|
password: process.env.MC_PASSWORD,
|
||||||
verbose: true,
|
|
||||||
});
|
});
|
||||||
client.on('connect', function() {
|
client.on('connect', function() {
|
||||||
console.info("connected");
|
console.info("connected");
|
||||||
|
|
63
index.js
63
index.js
|
@ -193,27 +193,43 @@ function createClient(options) {
|
||||||
var port = options.port || 25565;
|
var port = options.port || 25565;
|
||||||
var host = options.host || 'localhost';
|
var host = options.host || 'localhost';
|
||||||
assert.ok(options.username, "username is required");
|
assert.ok(options.username, "username is required");
|
||||||
var haveCredentials = typeof options.password !== "undefined";
|
var haveCredentials = options.password != null;
|
||||||
var keepAlive = options.keepAlive == null ? true : options.keepAlive;
|
var keepAlive = options.keepAlive == null ? true : options.keepAlive;
|
||||||
var email = options.email || options.username;
|
|
||||||
var password = options.password;
|
|
||||||
|
|
||||||
var client = new Client(false);
|
var client = new Client(false);
|
||||||
client.username = options.username;
|
client.on('connect', onConnect);
|
||||||
client.on('connect', function() {
|
if (keepAlive) client.on(0x00, onKeepAlive);
|
||||||
|
client.once(0xFC, onEncryptionKeyResponse);
|
||||||
|
client.once(0xFD, onEncryptionKeyRequest);
|
||||||
|
|
||||||
|
if (haveCredentials) {
|
||||||
|
// make a request to get the case-correct username before connecting.
|
||||||
|
getLoginSession(options.username, options.password, function(err, session) {
|
||||||
|
if (err) {
|
||||||
|
client.emit('error', err);
|
||||||
|
} else {
|
||||||
|
client.session = session;
|
||||||
|
client.username = session.username;
|
||||||
|
client.emit('session');
|
||||||
|
client.connect(port, host);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
} else {
|
||||||
|
// assume the server is in offline mode and just go for it.
|
||||||
|
client.username = options.username;
|
||||||
|
client.connect(port, host);
|
||||||
|
}
|
||||||
|
|
||||||
|
return client;
|
||||||
|
|
||||||
|
function onConnect() {
|
||||||
client.write(0x02, {
|
client.write(0x02, {
|
||||||
protocolVersion: protocol.version,
|
protocolVersion: protocol.version,
|
||||||
username: client.username,
|
username: client.username,
|
||||||
serverHost: host,
|
serverHost: host,
|
||||||
serverPort: port,
|
serverPort: port,
|
||||||
});
|
});
|
||||||
});
|
}
|
||||||
if (keepAlive) client.on(0x00, onKeepAlive);
|
|
||||||
client.once(0xFC, onEncryptionKeyResponse);
|
|
||||||
client.once(0xFD, onEncryptionKeyRequest);
|
|
||||||
client.connect(port, host);
|
|
||||||
|
|
||||||
return client;
|
|
||||||
|
|
||||||
function onKeepAlive(packet) {
|
function onKeepAlive(packet) {
|
||||||
client.write(0x00, {
|
client.write(0x00, {
|
||||||
|
@ -222,30 +238,21 @@ function createClient(options) {
|
||||||
}
|
}
|
||||||
|
|
||||||
function onEncryptionKeyRequest(packet) {
|
function onEncryptionKeyRequest(packet) {
|
||||||
var batch = new Batch();
|
crypto.randomBytes(16, gotSharedSecret);
|
||||||
var hash;
|
|
||||||
if (haveCredentials) {
|
function gotSharedSecret(err, sharedSecret) {
|
||||||
hash = crypto.createHash('sha1');
|
|
||||||
hash.update(packet.serverId);
|
|
||||||
batch.push(function(cb) { getLoginSession(email, password, cb); });
|
|
||||||
}
|
|
||||||
batch.push(function(cb) { crypto.randomBytes(16, cb); });
|
|
||||||
batch.end(function (err, results) {
|
|
||||||
if (err) {
|
if (err) {
|
||||||
client.emit('error', err);
|
client.emit('error', err);
|
||||||
client.end();
|
client.end();
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
var sharedSecret;
|
var hash = crypto.createHash('sha1');
|
||||||
|
hash.update(packet.serverId);
|
||||||
|
|
||||||
if (haveCredentials) {
|
if (haveCredentials) {
|
||||||
client.session = results[0];
|
|
||||||
client.username = client.session.username;
|
|
||||||
client.emit('session');
|
|
||||||
sharedSecret = results[1];
|
|
||||||
joinServerRequest(onJoinServerResponse);
|
joinServerRequest(onJoinServerResponse);
|
||||||
} else {
|
} else {
|
||||||
sharedSecret = results[0];
|
|
||||||
sendEncryptionKeyResponse();
|
sendEncryptionKeyResponse();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -298,7 +305,7 @@ function createClient(options) {
|
||||||
verifyToken: encryptedVerifyTokenBuffer,
|
verifyToken: encryptedVerifyTokenBuffer,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
});
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function onEncryptionKeyResponse(packet) {
|
function onEncryptionKeyResponse(packet) {
|
||||||
|
|
20
test/test.js
20
test/test.js
|
@ -264,7 +264,6 @@ describe("client", function() {
|
||||||
startServer({ 'online-mode': 'true' }, function() {
|
startServer({ 'online-mode': 'true' }, function() {
|
||||||
var client = mc.createClient({
|
var client = mc.createClient({
|
||||||
username: process.env.MC_USERNAME,
|
username: process.env.MC_USERNAME,
|
||||||
email: process.env.MC_EMAIL,
|
|
||||||
password: process.env.MC_PASSWORD,
|
password: process.env.MC_PASSWORD,
|
||||||
});
|
});
|
||||||
mcServer.on('line', function(line) {
|
mcServer.on('line', function(line) {
|
||||||
|
@ -299,12 +298,12 @@ describe("client", function() {
|
||||||
it("connects successfully - offline mode", function(done) {
|
it("connects successfully - offline mode", function(done) {
|
||||||
startServer({ 'online-mode': 'false' }, function() {
|
startServer({ 'online-mode': 'false' }, function() {
|
||||||
var client = mc.createClient({
|
var client = mc.createClient({
|
||||||
username: process.env.MC_USERNAME,
|
username: 'Player',
|
||||||
});
|
});
|
||||||
mcServer.on('line', function(line) {
|
mcServer.on('line', function(line) {
|
||||||
var match = line.match(/\[INFO\] <(.+?)> (.+)$/);
|
var match = line.match(/\[INFO\] <(.+?)> (.+)$/);
|
||||||
if (! match) return;
|
if (! match) return;
|
||||||
assert.strictEqual(match[1], process.env.MC_USERNAME);
|
assert.strictEqual(match[1], 'Player');
|
||||||
assert.strictEqual(match[2], "hello everyone; I have logged in.");
|
assert.strictEqual(match[2], "hello everyone; I have logged in.");
|
||||||
mcServer.stdin.write("say hello\n");
|
mcServer.stdin.write("say hello\n");
|
||||||
});
|
});
|
||||||
|
@ -322,7 +321,7 @@ describe("client", function() {
|
||||||
chatCount += 1;
|
chatCount += 1;
|
||||||
assert.ok(chatCount <= 2);
|
assert.ok(chatCount <= 2);
|
||||||
if (chatCount === 1) {
|
if (chatCount === 1) {
|
||||||
assert.strictEqual(packet.message, "<" + process.env.MC_USERNAME + ">" + " hello everyone; I have logged in.");
|
assert.strictEqual(packet.message, "<Player>" + " hello everyone; I have logged in.");
|
||||||
} else if (chatCount === 2) {
|
} else if (chatCount === 2) {
|
||||||
assert.strictEqual(packet.message, "[Server] hello");
|
assert.strictEqual(packet.message, "[Server] hello");
|
||||||
done();
|
done();
|
||||||
|
@ -333,7 +332,7 @@ describe("client", function() {
|
||||||
it("gets kicked when no credentials supplied in online mode", function(done) {
|
it("gets kicked when no credentials supplied in online mode", function(done) {
|
||||||
startServer({ 'online-mode': 'true' }, function() {
|
startServer({ 'online-mode': 'true' }, function() {
|
||||||
var client = mc.createClient({
|
var client = mc.createClient({
|
||||||
username: process.env.MC_USERNAME,
|
username: 'Player',
|
||||||
});
|
});
|
||||||
var gotKicked = false;
|
var gotKicked = false;
|
||||||
client.on(0xff, function(packet) {
|
client.on(0xff, function(packet) {
|
||||||
|
@ -349,7 +348,7 @@ describe("client", function() {
|
||||||
it("does not crash for " + SURVIVE_TIME + "ms", function(done) {
|
it("does not crash for " + SURVIVE_TIME + "ms", function(done) {
|
||||||
startServer({ 'online-mode': 'false' }, function() {
|
startServer({ 'online-mode': 'false' }, function() {
|
||||||
var client = mc.createClient({
|
var client = mc.createClient({
|
||||||
username: process.env.MC_USERNAME,
|
username: 'Player',
|
||||||
});
|
});
|
||||||
client.on(0x01, function(packet) {
|
client.on(0x01, function(packet) {
|
||||||
client.write(0x03, {
|
client.write(0x03, {
|
||||||
|
@ -357,7 +356,7 @@ describe("client", function() {
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
client.on(0x03, function(packet) {
|
client.on(0x03, function(packet) {
|
||||||
assert.strictEqual(packet.message, "<" + process.env.MC_USERNAME + ">" + " hello everyone; I have logged in.");
|
assert.strictEqual(packet.message, "<Player>" + " hello everyone; I have logged in.");
|
||||||
setTimeout(function() {
|
setTimeout(function() {
|
||||||
done();
|
done();
|
||||||
}, SURVIVE_TIME);
|
}, SURVIVE_TIME);
|
||||||
|
@ -533,7 +532,7 @@ describe("mc-server", function() {
|
||||||
});
|
});
|
||||||
it("kicks clients when invalid credentials", function(done) {
|
it("kicks clients when invalid credentials", function(done) {
|
||||||
var server = mc.createServer();
|
var server = mc.createServer();
|
||||||
var count = 5;
|
var count = 4;
|
||||||
server.on('connection', function(client) {
|
server.on('connection', function(client) {
|
||||||
client.on('end', function(reason) {
|
client.on('end', function(reason) {
|
||||||
resolve();
|
resolve();
|
||||||
|
@ -547,11 +546,6 @@ describe("mc-server", function() {
|
||||||
resolve();
|
resolve();
|
||||||
var client = mc.createClient({
|
var client = mc.createClient({
|
||||||
username: 'lalalal',
|
username: 'lalalal',
|
||||||
password: "this is wrong",
|
|
||||||
});
|
|
||||||
client.on('error', function(err) {
|
|
||||||
assert.strictEqual(err.code, 'ELOGIN400');
|
|
||||||
resolve();
|
|
||||||
});
|
});
|
||||||
client.on('end', function() {
|
client.on('end', function() {
|
||||||
resolve();
|
resolve();
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue