From 9779d7021b533726f5eebcafaeead747ab3137d1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 30 Oct 2010 15:33:14 +0200 Subject: [PATCH 01/26] Better project description --- Readme.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/Readme.md b/Readme.md index 6e2b4bd02..45597e64e 100644 --- a/Readme.md +++ b/Readme.md @@ -2,8 +2,7 @@ ## Purpose -A node.js module implementing the -[MySQL protocol](http://forge.mysql.com/wiki/MySQL_Internals_ClientServer_Protocol). +A pure node.js JavaScript Client implementing the [MySQL protocol](http://forge.mysql.com/wiki/MySQL_Internals_ClientServer_Protocol). ## Contributors From ad1e2d11e6c6d9603597e2c5bd6c088d851696eb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 30 Oct 2010 15:49:17 +0200 Subject: [PATCH 02/26] Note about current status of this module --- Readme.md | 20 ++++++++++++-------- 1 file changed, 12 insertions(+), 8 deletions(-) diff --git a/Readme.md b/Readme.md index 45597e64e..ae945441f 100644 --- a/Readme.md +++ b/Readme.md @@ -4,6 +4,12 @@ A pure node.js JavaScript Client implementing the [MySQL protocol](http://forge.mysql.com/wiki/MySQL_Internals_ClientServer_Protocol). +## Current status + +This module was developed for [Transloadit](http://transloadit.com/), a service focused on uploading +and encoding images and videos. It is currently used in production there, but since the service is not +very heavy on database interaction your milage may vary. + ## Contributors * Bert Belder ([piscisaureus](http://github.com/felixge/node-mysql/commits/master?author=piscisaureus)) @@ -17,15 +23,13 @@ A pure node.js JavaScript Client implementing the [MySQL protocol](http://forge. * [Joyent](http://www.joyent.com/) * [pinkbike.com](http://pinkbike.com/) -I'm working on this driver because I need it for my own startup -([transloadit.com][transloadit]), but it's a big project (~100-200 hours) with -obvious benefits to other companies who are using MySql. +This is a rather large project requiring a significant amount of my limited resources. -So if your company could benefit from a well-engineered node.js mysql driver, -I would greatly appriciate any sponsorship you may be able to provide. All -sponsors will get lifetime display in this readme, priority support on problems, -and votes on roadmap decisions. If you are interested, contact me at -[felix@debuggable.com](mailto:felix@debuggable.com) for details. +If your company could benefit from a well-engineered non-blocking mysql driver, and +wants to support this project, I would greatly appriciate any sponsorship you may be +able to provide. All sponsors will get lifetime display in this readme, priority +support on problems, and votes on roadmap decisions. If you are interested, contact +me at [felix@debuggable.com](mailto:felix@debuggable.com) for details. Of course I'm also happy about code contributions. If you're interested in working on features, just get in touch so we can talk about API design and From d0cc512494abc1c8804359d7d0491dee15c18058 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 30 Oct 2010 15:52:19 +0200 Subject: [PATCH 03/26] Better introduction of the sponsors --- Readme.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Readme.md b/Readme.md index ae945441f..1505ed76b 100644 --- a/Readme.md +++ b/Readme.md @@ -20,8 +20,8 @@ very heavy on database interaction your milage may vary. ## Sponsors -* [Joyent](http://www.joyent.com/) -* [pinkbike.com](http://pinkbike.com/) +* [Joyent](http://www.joyent.com/) - Main sponsor, you should check out their [node.js hosting](https://no.de/). +* [pinkbike.com](http://pinkbike.com/) - The most awesome biking site there is This is a rather large project requiring a significant amount of my limited resources. From 58568c31d3867514e99dec6d46c5846b5e7100d1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 30 Oct 2010 15:53:27 +0200 Subject: [PATCH 04/26] Add myself to the contributors list --- Readme.md | 1 + 1 file changed, 1 insertion(+) diff --git a/Readme.md b/Readme.md index 1505ed76b..7edf32ebf 100644 --- a/Readme.md +++ b/Readme.md @@ -12,6 +12,7 @@ very heavy on database interaction your milage may vary. ## Contributors +* Felix Geisendörfer ([felixge](http://github.com/felixge/node-mysql/commits/master?author=felixge)), Author and maintainer * Bert Belder ([piscisaureus](http://github.com/felixge/node-mysql/commits/master?author=piscisaureus)) * Alan Gutierrez ([bigeasy](http://github.com/felixge/node-mysql/commits/master?author=bigeasy)) * Brian ([mscdex](http://github.com/felixge/node-mysql/commits/master?author=mscdex)) From a1a6585a92126c214ae93cb3679b701815da9b32 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 30 Oct 2010 15:54:02 +0200 Subject: [PATCH 05/26] Small readme change --- Readme.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Readme.md b/Readme.md index 7edf32ebf..fd262f0a8 100644 --- a/Readme.md +++ b/Readme.md @@ -12,7 +12,7 @@ very heavy on database interaction your milage may vary. ## Contributors -* Felix Geisendörfer ([felixge](http://github.com/felixge/node-mysql/commits/master?author=felixge)), Author and maintainer +* Felix Geisendörfer ([felixge](http://github.com/felixge/node-mysql/commits/master?author=felixge)) - Author and maintainer * Bert Belder ([piscisaureus](http://github.com/felixge/node-mysql/commits/master?author=piscisaureus)) * Alan Gutierrez ([bigeasy](http://github.com/felixge/node-mysql/commits/master?author=bigeasy)) * Brian ([mscdex](http://github.com/felixge/node-mysql/commits/master?author=mscdex)) From fb9c255b8cd34a46582e704e00f0fb558ea49d1a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 30 Oct 2010 16:56:23 +0200 Subject: [PATCH 06/26] Fix benchmark running --- test/common.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/test/common.js b/test/common.js index 47c8e88da..191182ee4 100644 --- a/test/common.js +++ b/test/common.js @@ -2,7 +2,8 @@ var path = require('path'); require.paths.unshift(path.dirname(__dirname)+'/lib'); var sys = require('mysql/sys'); -if (module.parent.filename.match(/test\/system/)) { +var parent = module.parent.filename; +if (parent.match(/test\/system/) || parent.match(/benchmark/)) { try { global.TEST_CONFIG = require('./config'); } catch (e) { From 0d08256fa816d60368ef3b7b182b3e5699b748e7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 30 Oct 2010 17:15:22 +0200 Subject: [PATCH 07/26] 22% performance improvement Turns out that using variables as the cases for the switch statement in the parser was a rather bad idea. The new version of the code will be a little harder to maintain, but I guess it's worth it. Also: I should investigate if switch() in general is slow --- lib/mysql/parser.js | 96 ++++++++++++++++++++++----------------------- 1 file changed, 48 insertions(+), 48 deletions(-) diff --git a/lib/mysql/parser.js b/lib/mysql/parser.js index b737209d9..32e5ed34e 100644 --- a/lib/mysql/parser.js +++ b/lib/mysql/parser.js @@ -85,7 +85,7 @@ Parser.prototype.write = function(buffer) { switch (state) { // PACKET HEADER - case Parser.PACKET_LENGTH: + case 0: // PACKET_LENGTH: if (!packet) { packet = this.packet = new EventEmitter(); packet.index = 0; @@ -101,7 +101,7 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.PACKET_NUMBER: + case 1: // PACKET_NUMBER: // 1 byte packet.number = c; @@ -120,7 +120,7 @@ Parser.prototype.write = function(buffer) { break; // GREETING_PACKET - case Parser.GREETING_PROTOCOL_VERSION: + case 2: // GREETING_PROTOCOL_VERSION: // Nice undocumented MySql gem, the initial greeting can be an error // packet. Happens for too many connections errors. if (c === 0xff) { @@ -134,7 +134,7 @@ Parser.prototype.write = function(buffer) { packet.protocolVersion = c; advance(); break; - case Parser.GREETING_SERVER_VERSION: + case 3: // GREETING_SERVER_VERSION: if (packet.index == 0) { packet.serverVersion = ''; } @@ -146,7 +146,7 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.GREETING_THREAD_ID: + case 4: // GREETING_THREAD_ID: if (packet.index == 0) { packet.threadId = 0; } @@ -158,7 +158,7 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.GREETING_SCRAMBLE_BUFF_1: + case 5: // GREETING_SCRAMBLE_BUFF_1: if (packet.index == 0) { packet.scrambleBuffer = new Buffer(8 + 12); } @@ -170,11 +170,11 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.GREETING_FILLER_1: + case 6: // GREETING_FILLER_1: // 1 byte - 0x00 advance(); break; - case Parser.GREETING_SERVER_CAPABILITIES: + case 7: // GREETING_SERVER_CAPABILITIES: if (packet.index == 0) { packet.serverCapabilities = 0; } @@ -185,11 +185,11 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.GREETING_SERVER_LANGUAGE: + case 8: // GREETING_SERVER_LANGUAGE: packet.serverLanguage = c; advance(); break; - case Parser.GREETING_SERVER_STATUS: + case 9: // GREETING_SERVER_STATUS: if (packet.index == 0) { packet.serverStatus = 0; } @@ -201,13 +201,13 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.GREETING_FILLER_2: + case 10: // GREETING_FILLER_2: // 13 bytes - 0x00 if (packet.index == 12) { advance(); } break; - case Parser.GREETING_SCRAMBLE_BUFF_2: + case 11: // GREETING_SCRAMBLE_BUFF_2: // 12 bytes - not 13 bytes like the protocol spec says ... if (packet.index < 12) { packet.scrambleBuffer[packet.index + 8] = c; @@ -215,7 +215,7 @@ Parser.prototype.write = function(buffer) { break; // OK_PACKET, ERROR_PACKET, or RESULT_SET_HEADER_PACKET - case Parser.FIELD_COUNT: + case 12: // FIELD_COUNT: if (packet.index == 0) { if (c === 0xff) { packet.type = Parser.ERROR_PACKET; @@ -244,7 +244,7 @@ Parser.prototype.write = function(buffer) { break; // ERROR_PACKET - case Parser.ERROR_NUMBER: + case 13: // ERROR_NUMBER: if (packet.index == 0) { packet.errorNumber = 0; } @@ -263,13 +263,13 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.ERROR_SQL_STATE_MARKER: + case 14: // ERROR_SQL_STATE_MARKER: // 1 character - always # packet.sqlStateMarker = String.fromCharCode(c); packet.sqlState = ''; advance(); break; - case Parser.ERROR_SQL_STATE: + case 15: // ERROR_SQL_STATE: // 5 characters if (packet.index < 5) { packet.sqlState += String.fromCharCode(c); @@ -279,20 +279,20 @@ Parser.prototype.write = function(buffer) { advance(Parser.ERROR_MESSAGE); } break; - case Parser.ERROR_MESSAGE: + case 16: // ERROR_MESSAGE: if (packet.received <= packet.length) { packet.errorMessage = (packet.errorMessage || '') + String.fromCharCode(c); } break; // OK_PACKET - case Parser.AFFECTED_ROWS: + case 17: // AFFECTED_ROWS: packet.affectedRows = lengthCoded(packet.affectedRows); break; - case Parser.INSERT_ID: + case 18: // INSERT_ID: packet.insertId = lengthCoded(packet.insertId); break; - case Parser.SERVER_STATUS: + case 19: // SERVER_STATUS: if (packet.index == 0) { packet.serverStatus = 0; } @@ -304,7 +304,7 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.WARNING_COUNT: + case 20: // WARNING_COUNT: if (packet.index == 0) { packet.warningCount = 0; } @@ -317,23 +317,23 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.MESSAGE: + case 21: // MESSAGE: if (packet.received <= packet.length) { packet.message += String.fromCharCode(c); } break; // RESULT_SET_HEADER_PACKET - case Parser.EXTRA_LENGTH: + case 22: // EXTRA_LENGTH: packet.extra = ''; self._lengthCodedStringLength = lengthCoded(self._lengthCodedStringLength); break; - case Parser.EXTRA_STRING: + case 23: // EXTRA_STRING: packet.extra += String.fromCharCode(c); break; // FIELD_PACKET or EOF_PACKET - case Parser.FIELD_CATALOG_LENGTH: + case 24: // FIELD_CATALOG_LENGTH: if (packet.index == 0) { if (c === 0xfe) { packet.type = Parser.EOF_PACKET; @@ -344,7 +344,7 @@ Parser.prototype.write = function(buffer) { } self._lengthCodedStringLength = lengthCoded(self._lengthCodedStringLength); break; - case Parser.FIELD_CATALOG_STRING: + case 25: // FIELD_CATALOG_STRING: if (packet.index == 0) { packet.catalog = ''; } @@ -354,13 +354,13 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_DB_LENGTH: + case 26: // FIELD_DB_LENGTH: self._lengthCodedStringLength = lengthCoded(self._lengthCodedStringLength); if (self._lengthCodedStringLength == 0) { advance(); } break; - case Parser.FIELD_DB_STRING: + case 27: // FIELD_DB_STRING: if (packet.index == 0) { packet.db = ''; } @@ -370,13 +370,13 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_TABLE_LENGTH: + case 28: // FIELD_TABLE_LENGTH: self._lengthCodedStringLength = lengthCoded(self._lengthCodedStringLength); if (self._lengthCodedStringLength == 0) { advance(); } break; - case Parser.FIELD_TABLE_STRING: + case 29: // FIELD_TABLE_STRING: if (packet.index == 0) { packet.table = ''; } @@ -386,13 +386,13 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_ORIGINAL_TABLE_LENGTH: + case 30: // FIELD_ORIGINAL_TABLE_LENGTH: self._lengthCodedStringLength = lengthCoded(self._lengthCodedStringLength); if (self._lengthCodedStringLength == 0) { advance(); } break; - case Parser.FIELD_ORIGINAL_TABLE_STRING: + case 31: // FIELD_ORIGINAL_TABLE_STRING: if (packet.index == 0) { packet.originalTable = ''; } @@ -402,10 +402,10 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_NAME_LENGTH: + case 32: // FIELD_NAME_LENGTH: self._lengthCodedStringLength = lengthCoded(self._lengthCodedStringLength); break; - case Parser.FIELD_NAME_STRING: + case 33: // FIELD_NAME_STRING: if (packet.index == 0) { packet.name = ''; } @@ -415,13 +415,13 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_ORIGINAL_NAME_LENGTH: + case 34: // FIELD_ORIGINAL_NAME_LENGTH: self._lengthCodedStringLength = lengthCoded(self._lengthCodedStringLength); if (self._lengthCodedStringLength == 0) { advance(); } break; - case Parser.FIELD_ORIGINAL_NAME_STRING: + case 35: // FIELD_ORIGINAL_NAME_STRING: if (packet.index == 0) { packet.originalName = ''; } @@ -431,11 +431,11 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_FILLER_1: + case 36: // FIELD_FILLER_1: // 1 bytes - 0x00 advance(); break; - case Parser.FIELD_CHARSET_NR: + case 37: // FIELD_CHARSET_NR: if (packet.index == 0) { packet.charsetNumber = 0; } @@ -447,7 +447,7 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_LENGTH: + case 38: // FIELD_LENGTH: if (packet.index == 0) { packet.fieldLength = 0; } @@ -459,11 +459,11 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_TYPE: + case 39: // FIELD_TYPE: // 1 byte packet.fieldType = c; advance(); - case Parser.FIELD_FLAGS: + case 40: // FIELD_FLAGS: if (packet.index == 0) { packet.flags = 0; } @@ -475,23 +475,23 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.FIELD_DECIMALS: + case 41: // FIELD_DECIMALS: // 1 byte packet.decimals = c; advance(); break; - case Parser.FIELD_FILLER_2: + case 42: // FIELD_FILLER_2: // 2 bytes - 0x00 if (packet.index == 1) { advance(); } break; - case Parser.FIELD_DEFAULT: + case 43: // FIELD_DEFAULT: // TODO: Only occurs for mysql_list_fields() break; // EOF_PACKET - case Parser.EOF_WARNING_COUNT: + case 44: // EOF_WARNING_COUNT: if (packet.index == 0) { packet.warningCount = 0; } @@ -503,7 +503,7 @@ Parser.prototype.write = function(buffer) { advance(); } break; - case Parser.EOF_SERVER_STATUS: + case 45: // EOF_SERVER_STATUS: if (packet.index == 0) { packet.serverStatus = 0; } @@ -519,7 +519,7 @@ Parser.prototype.write = function(buffer) { } } break; - case Parser.COLUMN_VALUE_LENGTH: + case 46: // COLUMN_VALUE_LENGTH: if (packet.index == 0) { packet.columnLength = 0; packet.type = Parser.ROW_DATA_PACKET; @@ -548,7 +548,7 @@ Parser.prototype.write = function(buffer) { } } break; - case Parser.COLUMN_VALUE_STRING: + case 47: // COLUMN_VALUE_STRING: var remaining = packet.columnLength - packet.index, read; if (i + remaining > buffer.length) { read = buffer.length - i; From c5540bf214a7c6910fa0606007799ca093eca72c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Wed, 3 Nov 2010 21:52:53 +0100 Subject: [PATCH 08/26] Document retrieval of last insert id --- Readme.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/Readme.md b/Readme.md index fd262f0a8..a24b460f7 100644 --- a/Readme.md +++ b/Readme.md @@ -223,6 +223,14 @@ itself will be made available soon. Emitted once the query is finished. In case there is no result set, a `result` parameter is provided which contains the information from the mysql OK packet. +## FAQ + +### How can I retrieve the id from the last inserted record? + + client.query('INSERT INTO my_table SET title = ?', function(err, info) { + console.log(info.insertId); + }); + ## Todo At this point the module is ready to be tried out, but a lot of things are yet to be done: From 1928c7800acc38cee2fe8c5b401b5afda64efc43 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 16:33:05 +0100 Subject: [PATCH 09/26] Make the module compatible with node HEAD again Constants seem to be a moving target in the API, so I added a feature detection mechanism, similar to that used for the old sys module which should make things work across all supported node versions. --- lib/mysql/client.js | 4 ++-- lib/mysql/net_constants.js | 22 ++++++++++++++++++++++ test/simple/test-client.js | 4 ++-- 3 files changed, 26 insertions(+), 4 deletions(-) create mode 100644 lib/mysql/net_constants.js diff --git a/lib/mysql/client.js b/lib/mysql/client.js index 4d7580e48..08659c0c5 100644 --- a/lib/mysql/client.js +++ b/lib/mysql/client.js @@ -7,7 +7,7 @@ var sys = require('./sys'), OutgoingPacket = require('./outgoing_packet'), Query = require('./query'), EventEmitter = require('events').EventEmitter, - netBinding = process.binding('net'); + netConstants = require('./net_constants'); function Client(properties) { if (!(this instanceof Client)) { @@ -50,7 +50,7 @@ Client.prototype.connect = function(cb) { connection .on('error', function(err) { - if (err.errno & (netBinding.ECONNREFUSED | netBinding.ENOTFOUND)) { + if (err.errno & (netConstants.ECONNREFUSED | netConstants.ENOTFOUND)) { if (cb) { cb(err); return; diff --git a/lib/mysql/net_constants.js b/lib/mysql/net_constants.js new file mode 100644 index 000000000..1355709ca --- /dev/null +++ b/lib/mysql/net_constants.js @@ -0,0 +1,22 @@ +// Constants have been changing through various node versions. +// First we try to look for them in the old location (in the net binding) +// If this fails, we try to get them from the constants module which +// was added in a later version. If that fails we raise an error; + +var NET_CONSTANTS_NOT_FOUND = 'Unable to detect constants location, please report this.'; + +module.exports = process.binding('net'); + +if ('ECONNREFUSED' in module.exports) { + return; +} + +try { + module.exports = require('constants'); +} catch (e) { + throw new Error(NET_CONSTANTS_NOT_FOUND); +} + +if (!('ECONNREFUSED' in module.exports)) { + throw new Error(NET_CONSTANTS_NOT_FOUND); +} diff --git a/test/simple/test-client.js b/test/simple/test-client.js index ca5cbee45..1d5db701f 100644 --- a/test/simple/test-client.js +++ b/test/simple/test-client.js @@ -4,7 +4,7 @@ var StreamStub = GENTLY.stub('net', 'Stream'), OutgoingPacketStub = GENTLY.stub('./outgoing_packet'), QueryStub = GENTLY.stub('./query'), Parser = require('mysql/parser'), - netBinding = process.binding('net'); + netConstants = require('mysql/net_constants'); for (var k in Parser) { ParserStub[k] = Parser[k]; @@ -119,7 +119,7 @@ test(function connect() { (function testConnectionRefusedError() { var ERR = new Error('ouch'); - ERR.errno = netBinding.ECONNREFUSED; + ERR.errno = netConstants.ECONNREFUSED; CB_DELEGATE = gently.expect(function connectCallback(err) { assert.strictEqual(err, ERR); From e17409640c91c8016089887a439ca4d1593087df Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 16:37:16 +0100 Subject: [PATCH 10/26] Add another FAQ entry --- Readme.md | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/Readme.md b/Readme.md index a24b460f7..12c4dd46c 100644 --- a/Readme.md +++ b/Readme.md @@ -225,6 +225,12 @@ parameter is provided which contains the information from the mysql OK packet. ## FAQ +### How do I compile this module? + +This module is written entirely in JavaScript. There is no dependency on external +C libraries such as libmysql. That means you don't have to compile this module +at all. + ### How can I retrieve the id from the last inserted record? client.query('INSERT INTO my_table SET title = ?', function(err, info) { From fa1dbce91d894b4889806f3d95bd777d511df69a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 16:42:09 +0100 Subject: [PATCH 11/26] Output --- benchmark/node-mysql/insert-select.js | 1 + benchmark/php/insert-select.php | 1 + 2 files changed, 2 insertions(+) diff --git a/benchmark/node-mysql/insert-select.js b/benchmark/node-mysql/insert-select.js index 9e5d2bd25..ce5dfa84d 100644 --- a/benchmark/node-mysql/insert-select.js +++ b/benchmark/node-mysql/insert-select.js @@ -41,6 +41,7 @@ client.query( var duration = (+new Date - selectStart) / 1000, rowsPerSecond = inserts / duration; console.log('%d rows / second', rowsPerSecond.toFixed(2)); + console.log('%d ms', +new Date - selectStart); client.end(); }); } diff --git a/benchmark/php/insert-select.php b/benchmark/php/insert-select.php index d63018662..6b9c21cf8 100644 --- a/benchmark/php/insert-select.php +++ b/benchmark/php/insert-select.php @@ -35,4 +35,5 @@ $duration = (microtime(true) - $start); $rowsPerSecond = $INSERTS / $duration; echo sprintf("%d rows / second\n", $rowsPerSecond); +echo sprintf("%d ms\n", $duration * 1000); ?> From 708825a36425e1e704fd535f9238de80f7aae740 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 16:43:10 +0100 Subject: [PATCH 12/26] Add total ms to benchmark output --- benchmark/node-mysql/insert-select.js | 1 + benchmark/php/insert-select.php | 1 + 2 files changed, 2 insertions(+) diff --git a/benchmark/node-mysql/insert-select.js b/benchmark/node-mysql/insert-select.js index ce5dfa84d..6983b384d 100644 --- a/benchmark/node-mysql/insert-select.js +++ b/benchmark/node-mysql/insert-select.js @@ -31,6 +31,7 @@ client.query( insertsPerSecond = inserts / duration; console.log('%d inserts / second', insertsPerSecond.toFixed(2)); + console.log('%d ms', +new Date - start); client.typeCast = false; var selectStart = +new Date; diff --git a/benchmark/php/insert-select.php b/benchmark/php/insert-select.php index 6b9c21cf8..c3c3a512d 100644 --- a/benchmark/php/insert-select.php +++ b/benchmark/php/insert-select.php @@ -27,6 +27,7 @@ $duration = (microtime(true) - $start); $insertsPerSecond = $INSERTS / $duration; echo sprintf("%d inserts / second\n", $insertsPerSecond); +echo sprintf("%d ms\n", $duration * 1000); $start = microtime(true); $q = mysql_query('SELECT * FROM '.$table); From 0b9d351867d6c51ad191b3e51e63501991ed131d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 17:24:27 +0100 Subject: [PATCH 13/26] Fix test to also use the new net_constants module This should have been part of 1928c7800acc38cee2fe8c5b401b5afda64efc43. --- test/system/test-client-connection-error.js | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/test/system/test-client-connection-error.js b/test/system/test-client-connection-error.js index b61f48fdc..0201a876b 100644 --- a/test/system/test-client-connection-error.js +++ b/test/system/test-client-connection-error.js @@ -2,8 +2,9 @@ require('../common'); var Client = require('mysql').Client, client = Client(TEST_CONFIG), gently = new Gently(), - ECONNREFUSED = process.binding('net').ECONNREFUSED; - ENOTFOUND = process.binding('net').ENOTFOUND; + netConstants = require('mysql/net_constants'); + ECONNREFUSED = netConstants.ECONNREFUSED, + ENOTFOUND = netConstants.ENOTFOUND; client.host = 'BADHOST'; From 6c0e7a6e82289549fbdbfae688694c4eb524fb2a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 17:39:11 +0100 Subject: [PATCH 14/26] Simplify code Returning home early is always a good idea. --- lib/mysql/query.js | 68 ++++++++++++++++++++++++---------------------- 1 file changed, 35 insertions(+), 33 deletions(-) diff --git a/lib/mysql/query.js b/lib/mysql/query.js index 983bc8c4f..7f879c0e6 100644 --- a/lib/mysql/query.js +++ b/lib/mysql/query.js @@ -65,43 +65,45 @@ Query.prototype._handlePacket = function(packet) { row[field.name] = null; } - if (remaining == 0) { - self._rowIndex++; - if (self.typeCast && buffer !== null) { - switch (field.fieldType) { - case Query.FIELD_TYPE_TIMESTAMP: - case Query.FIELD_TYPE_DATE: - case Query.FIELD_TYPE_DATETIME: - case Query.FIELD_TYPE_NEWDATE: - row[field.name] = new Date(row[field.name]+'Z'); - break; - case Query.FIELD_TYPE_TINY: - case Query.FIELD_TYPE_SHORT: - case Query.FIELD_TYPE_LONG: - case Query.FIELD_TYPE_LONGLONG: - case Query.FIELD_TYPE_INT24: - case Query.FIELD_TYPE_YEAR: - row[field.name] = parseInt(row[field.name], 10); - break; - case Query.FIELD_TYPE_DECIMAL: - case Query.FIELD_TYPE_FLOAT: - case Query.FIELD_TYPE_DOUBLE: - case Query.FIELD_TYPE_NEWDECIMAL: - row[field.name] = parseFloat(row[field.name]); - break; - } - } + if (remaining !== 0) { + return; + } - if (self._rowIndex == self._fields.length) { - delete self._row; - delete self._rowIndex; - self.emit('row', row); - return; + self._rowIndex++; + if (self.typeCast && buffer !== null) { + switch (field.fieldType) { + case Query.FIELD_TYPE_TIMESTAMP: + case Query.FIELD_TYPE_DATE: + case Query.FIELD_TYPE_DATETIME: + case Query.FIELD_TYPE_NEWDATE: + row[field.name] = new Date(row[field.name]+'Z'); + break; + case Query.FIELD_TYPE_TINY: + case Query.FIELD_TYPE_SHORT: + case Query.FIELD_TYPE_LONG: + case Query.FIELD_TYPE_LONGLONG: + case Query.FIELD_TYPE_INT24: + case Query.FIELD_TYPE_YEAR: + row[field.name] = parseInt(row[field.name], 10); + break; + case Query.FIELD_TYPE_DECIMAL: + case Query.FIELD_TYPE_FLOAT: + case Query.FIELD_TYPE_DOUBLE: + case Query.FIELD_TYPE_NEWDECIMAL: + row[field.name] = parseFloat(row[field.name]); + break; } + } - field = self._fields[self._rowIndex]; - row[field.name] = ''; + if (self._rowIndex == self._fields.length) { + delete self._row; + delete self._rowIndex; + self.emit('row', row); + return; } + + field = self._fields[self._rowIndex]; + row[field.name] = ''; }); break; } From 13ca3c4f2374f0d4f2ede34552e5a5b836a73f80 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 17:42:45 +0100 Subject: [PATCH 15/26] Remove some code duplication --- lib/mysql/query.js | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/lib/mysql/query.js b/lib/mysql/query.js index 7f879c0e6..b4aed2385 100644 --- a/lib/mysql/query.js +++ b/lib/mysql/query.js @@ -52,13 +52,16 @@ Query.prototype._handlePacket = function(packet) { } break; case Parser.ROW_DATA_PACKET: - var row = this._row = {}, - field = this._fields[0]; + var row = this._row = {}, field; this._rowIndex = 0; - row[field.name] = ''; packet.on('data', function(buffer, remaining) { + if (!field) { + field = self._fields[self._rowIndex]; + row[field.name] = ''; + } + if (buffer) { row[field.name] += buffer.toString('utf-8'); } else { @@ -102,8 +105,7 @@ Query.prototype._handlePacket = function(packet) { return; } - field = self._fields[self._rowIndex]; - row[field.name] = ''; + field = null; }); break; } From d583bcf7cff2903ff25595a91abbfebd9786ba95 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 18:15:34 +0100 Subject: [PATCH 16/26] Split insert / select benchmark --- .../{insert-select.js => insert.js} | 17 ++--------- benchmark/node-mysql/select.js | 30 +++++++++++++++++++ 2 files changed, 33 insertions(+), 14 deletions(-) rename benchmark/node-mysql/{insert-select.js => insert.js} (69%) create mode 100644 benchmark/node-mysql/select.js diff --git a/benchmark/node-mysql/insert-select.js b/benchmark/node-mysql/insert.js similarity index 69% rename from benchmark/node-mysql/insert-select.js rename to benchmark/node-mysql/insert.js index 6983b384d..d6ef00a17 100644 --- a/benchmark/node-mysql/insert-select.js +++ b/benchmark/node-mysql/insert.js @@ -10,8 +10,9 @@ client.query('CREATE DATABASE '+TEST_DB, function(err) { } }); client.query('USE '+TEST_DB); +client.query('DROP TABLE IF EXISTS '+TEST_TABLE); client.query( - 'CREATE TEMPORARY TABLE '+TEST_TABLE+' ('+ + 'CREATE TABLE '+TEST_TABLE+' ('+ 'id INT(11) AUTO_INCREMENT, '+ 'title VARCHAR(255), '+ 'text TEXT, '+ @@ -32,19 +33,7 @@ client.query( console.log('%d inserts / second', insertsPerSecond.toFixed(2)); console.log('%d ms', +new Date - start); - - client.typeCast = false; - var selectStart = +new Date; - client - .query('SELECT * FROM '+TEST_TABLE) - .on('row', function(row) {}) - .on('end', function() { - var duration = (+new Date - selectStart) / 1000, - rowsPerSecond = inserts / duration; - console.log('%d rows / second', rowsPerSecond.toFixed(2)); - console.log('%d ms', +new Date - selectStart); - client.end(); - }); + client.end(); } }); } diff --git a/benchmark/node-mysql/select.js b/benchmark/node-mysql/select.js new file mode 100644 index 000000000..fc7f0d6a8 --- /dev/null +++ b/benchmark/node-mysql/select.js @@ -0,0 +1,30 @@ +require('../../test/common'); +var Client = require('mysql/client'), + client = Client(TEST_CONFIG), + rows = 0; + +client.typeCast = false; + +client.connect(); +client.query('CREATE DATABASE '+TEST_DB, function(err) { + if (err && err.number != Client.ERROR_DB_CREATE_EXISTS) { + throw err; + } +}); + +client.query('USE '+TEST_DB); +var selectStart = +new Date; +client + .query('SELECT * FROM '+TEST_TABLE) + .on('row', function(row) { + rows++; + }) + .on('end', function() { + assert.strictEqual(rows, 10000); + + var duration = (+new Date - selectStart) / 1000, + rowsPerSecond = rows / duration; + console.log('%d rows / second', rowsPerSecond.toFixed(2)); + console.log('%d ms', +new Date - selectStart); + client.end(); + }); From 3a74f8e6a4ec978840c8be9aa5af3964b3323f28 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 18:38:11 +0100 Subject: [PATCH 17/26] Select 100k rows to run longer / better sampling --- benchmark/node-mysql/select.js | 34 +++++++++++++++++++++------------- 1 file changed, 21 insertions(+), 13 deletions(-) diff --git a/benchmark/node-mysql/select.js b/benchmark/node-mysql/select.js index fc7f0d6a8..e5895bd69 100644 --- a/benchmark/node-mysql/select.js +++ b/benchmark/node-mysql/select.js @@ -14,17 +14,25 @@ client.query('CREATE DATABASE '+TEST_DB, function(err) { client.query('USE '+TEST_DB); var selectStart = +new Date; -client - .query('SELECT * FROM '+TEST_TABLE) - .on('row', function(row) { - rows++; - }) - .on('end', function() { - assert.strictEqual(rows, 10000); - var duration = (+new Date - selectStart) / 1000, - rowsPerSecond = rows / duration; - console.log('%d rows / second', rowsPerSecond.toFixed(2)); - console.log('%d ms', +new Date - selectStart); - client.end(); - }); +function query() { + client + .query('SELECT * FROM '+TEST_TABLE) + .on('row', function(row) { + rows++; + }) + .on('end', function() { + if (rows < 100000) { + query(); + return; + } + + var duration = (+new Date - selectStart) / 1000, + rowsPerSecond = rows / duration; + console.log('%d rows / second', rowsPerSecond.toFixed(2)); + console.log('%d ms', +new Date - selectStart); + client.end(); + }); +} + +query(); From b5591f4a8cbb88f32681b455b1c48ec2ba6e3c86 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 6 Nov 2010 21:20:52 +0100 Subject: [PATCH 18/26] Add link to last v8 profile Also changed benchmark back to just do 10k rows for right now. --- benchmark/node-mysql/select.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/benchmark/node-mysql/select.js b/benchmark/node-mysql/select.js index e5895bd69..696d2b3cf 100644 --- a/benchmark/node-mysql/select.js +++ b/benchmark/node-mysql/select.js @@ -1,3 +1,5 @@ +// Last v8 profile when running this test for 500k rows: +// https://gist.github.com/f85c38010c038e5efe2e require('../../test/common'); var Client = require('mysql/client'), client = Client(TEST_CONFIG), @@ -22,7 +24,7 @@ function query() { rows++; }) .on('end', function() { - if (rows < 100000) { + if (rows < 10000) { query(); return; } From 4e3da13997bcf57ff6d1a1f586124c428e70cfed Mon Sep 17 00:00:00 2001 From: Bert Belder Date: Thu, 11 Nov 2010 11:57:29 +0100 Subject: [PATCH 19/26] Remove some dead code --- lib/mysql/client.js | 5 ----- 1 file changed, 5 deletions(-) diff --git a/lib/mysql/client.js b/lib/mysql/client.js index 08659c0c5..66cb18eb5 100644 --- a/lib/mysql/client.js +++ b/lib/mysql/client.js @@ -351,11 +351,6 @@ Client._packetToUserObject = function(packet) { } return userObject; - - packet.message = packet.errorMessage; - delete packet.errorMessage; - packet.number = packet.errorNumber; - delete packet.errorNumber; }; Client.prototype._debugPacket = function(packet) { From d96fedfb3b74514a7cc232e51d876a557ed768ac Mon Sep 17 00:00:00 2001 From: Bert Belder Date: Thu, 11 Nov 2010 11:50:37 +0100 Subject: [PATCH 20/26] Full sql statement in query error object --- lib/mysql/client.js | 5 ++++- lib/mysql/query.js | 1 + test/system/test-client-query-error.js | 25 +++++++++++++++++-------- 3 files changed, 22 insertions(+), 9 deletions(-) diff --git a/lib/mysql/client.js b/lib/mysql/client.js index 66cb18eb5..a3e405fec 100644 --- a/lib/mysql/client.js +++ b/lib/mysql/client.js @@ -94,7 +94,10 @@ Client.prototype.query = function(sql, params, cb) { cb = arguments[1]; } - var query = new Query({typeCast: this.typeCast}); + var query = new Query({ + typeCast: this.typeCast, + sql: sql + }); if (cb) { var rows = [], fields = {}; diff --git a/lib/mysql/query.js b/lib/mysql/query.js index b4aed2385..36a89a948 100644 --- a/lib/mysql/query.js +++ b/lib/mysql/query.js @@ -30,6 +30,7 @@ Query.prototype._handlePacket = function(packet) { this.emit('end', Client._packetToUserObject(packet)); break; case Parser.ERROR_PACKET: + packet.sql = this.sql; this.emit('error', Client._packetToUserObject(packet)); break; case Parser.FIELD_PACKET: diff --git a/test/system/test-client-query-error.js b/test/system/test-client-query-error.js index 90e0f0f8c..82ec38592 100644 --- a/test/system/test-client-query-error.js +++ b/test/system/test-client-query-error.js @@ -1,5 +1,7 @@ require('../common'); -var Client = require('mysql').Client; +var Client = require('mysql').Client, + INVALID_QUERY_1 = 'first invalid #*&% query', + INVALID_QUERY_2 = 'another #*&% wrong query'; (function testErrorCallback() { // The query callback should receive an error, @@ -12,8 +14,9 @@ var Client = require('mysql').Client; if (error) throw error; })); - client.query('invalid #*&% query', [], gently.expect(function queryCb(error) { + client.query(INVALID_QUERY_1, [], gently.expect(function queryCb(error) { assert.ok(error); + assert.strictEqual(error.sql, INVALID_QUERY_1); client.end(); gently.verify('testErrorCallback'); })); @@ -31,10 +34,11 @@ var Client = require('mysql').Client; if (error) throw error; })); - query = client.query('invalid #*&% query'); + query = client.query(INVALID_QUERY_2); query.on('error', gently.expect(function errCb(error) { assert.ok(error); + assert.strictEqual(error.sql, INVALID_QUERY_2); client.end(); gently.verify('testQueryError'); })); @@ -52,10 +56,11 @@ var Client = require('mysql').Client; if (error) throw error; })); - query = client.query('invalid #*&% query'); + query = client.query(INVALID_QUERY_1); client.on('error', gently.expect(function errCb(error) { assert.ok(error); + assert.strictEqual(error.sql, INVALID_QUERY_1); client.end(); gently.verify('testClientError'); })); @@ -76,13 +81,14 @@ var Client = require('mysql').Client; if (error) throw error; })); - query = client.query('invalid #*&% query'); + query = client.query(INVALID_QUERY_2); query.on('error', dummyHandler); query.removeListener('error', dummyHandler); client.on('error', gently.expect(function errCb(error) { assert.ok(error); + assert.strictEqual(error.sql, INVALID_QUERY_2); client.end(); gently.verify('testRemoveListener'); })); @@ -99,8 +105,9 @@ var Client = require('mysql').Client; if (error) throw error; })); - client.query('invalid #*&% query', [], gently.expect(function queryCb(error) { + client.query(INVALID_QUERY_1, [], gently.expect(function queryCb(error) { assert.ok(error); + assert.strictEqual(error.sql, INVALID_QUERY_1); })); client.query('SHOW STATUS', [], gently.expect(function queryCb(error, rows, fields) { @@ -109,12 +116,14 @@ var Client = require('mysql').Client; assert.equal(Object.keys(fields).length, 2); })); - client.query('invalid #*&% query', [], gently.expect(function queryCb(error) { + client.query(INVALID_QUERY_1, [], gently.expect(function queryCb(error) { assert.ok(error); + assert.strictEqual(error.sql, INVALID_QUERY_1); })); - client.query('invalid #*&% query', [], gently.expect(function errCb(error) { + client.query(INVALID_QUERY_2, [], gently.expect(function errCb(error) { assert.ok(error); + assert.strictEqual(error.sql, INVALID_QUERY_2); client.end(); gently.verify('testSerialError'); })); From 3aca246d6ce144b5c29bab48a6c02312df7418bb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Fri, 12 Nov 2010 10:42:49 +0100 Subject: [PATCH 21/26] Added missing unit tests for previous patch --- lib/mysql/query.js | 1 + test/simple/test-client.js | 1 + test/simple/test-query.js | 3 +++ 3 files changed, 5 insertions(+) diff --git a/lib/mysql/query.js b/lib/mysql/query.js index 36a89a948..3bcd01e61 100644 --- a/lib/mysql/query.js +++ b/lib/mysql/query.js @@ -8,6 +8,7 @@ var sys = require('./sys'), function Query(properties) { EventEmitter.call(this); + this.sql = null; this.typeCast = true; for (var key in properties) { diff --git a/test/simple/test-client.js b/test/simple/test-client.js index 1d5db701f..e5d6e099c 100644 --- a/test/simple/test-client.js +++ b/test/simple/test-client.js @@ -197,6 +197,7 @@ test(function query() { QUERY = this; assert.equal(properties.typeCast, client.typeCast); + assert.equal(properties.sql, FORMATED_SQL); var events = ['error', 'field', 'row', 'end']; gently.expect(QUERY, 'on', events.length, function (event, fn) { diff --git a/test/simple/test-query.js b/test/simple/test-query.js index 7a64cccd2..a62a089cd 100644 --- a/test/simple/test-query.js +++ b/test/simple/test-query.js @@ -16,6 +16,7 @@ function test(test) { test(function constructor() { assert.ok(query instanceof EventEmitter); assert.strictEqual(query.typeCast, true); + assert.strictEqual(query.sql, null); assert.equal(new Query({foo: 'bar'}).foo, 'bar'); }); @@ -41,6 +42,7 @@ test(function _handlePacket() { gently.expect(ClientStub, '_packetToUserObject', function (packet) { assert.strictEqual(packet, PACKET); + assert.strictEqual(packet.sql, query.sql); return USER_OBJECT; }); @@ -49,6 +51,7 @@ test(function _handlePacket() { assert.strictEqual(packet, USER_OBJECT); }); + query.sql = 'SELECT bla FROM foo'; query._handlePacket(PACKET); })(); From 5eecbdb10b459061e761d41ef518bdd6320472c4 Mon Sep 17 00:00:00 2001 From: Jason Woofenden Date: Mon, 15 Nov 2010 07:52:56 -0500 Subject: [PATCH 22/26] Readme.md: fix syntax in tutorial, cleanup * remove comma from after last array element (2x) * add declaration of config vars at the top * simplify name of database config var * add missing "err" argument to callback * fix member name err.errorNumber -> err.number * remove redundant semicolon at end of one query --- Readme.md | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/Readme.md b/Readme.md index 12c4dd46c..1e3a4bb85 100644 --- a/Readme.md +++ b/Readme.md @@ -68,18 +68,20 @@ However, using a current version of node is encouraged. client.user = 'root'; client.password = 'root'; + var TEST_DATABASE = 'nodejs_mysl_test', + TEST_TABLE = 'test'; client.connect(); - client.query('CREATE DATABASE '+TEST_CONFIG.database, function() { - if (err && err.errorNumber != Client.ERROR_DB_CREATE_EXISTS) { + client.query('CREATE DATABASE '+TEST_DATABASE, function(err) { + if (err && err.number != Client.ERROR_DB_CREATE_EXISTS) { throw err; } }); // If no callback is provided, any errors will be emitted as `'error'` // events by the client - client.query('USE '+TEST_CONFIG.database); + client.query('USE '+TEST_DATABASE); client.query( 'CREATE TEMPORARY TABLE '+TEST_TABLE+ @@ -87,13 +89,13 @@ However, using a current version of node is encouraged. 'title VARCHAR(255), '+ 'text TEXT, '+ 'created DATETIME, '+ - 'PRIMARY KEY (id));', + 'PRIMARY KEY (id))' ); client.query( 'INSERT INTO '+TEST_TABLE+' '+ 'SET title = ?, text = ?, created = ?', - ['super cool', 'this is a nice text', '2010-08-16 10:00:23'], + ['super cool', 'this is a nice text', '2010-08-16 10:00:23'] ); var query = client.query( From 0d3f5c4758854689e1df213873e485192a57b947 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Sat, 20 Nov 2010 14:11:16 +0100 Subject: [PATCH 23/26] Improve Readme example further Removed gently call and moved constant declaration up. --- Readme.md | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Readme.md b/Readme.md index 1e3a4bb85..49dd7400d 100644 --- a/Readme.md +++ b/Readme.md @@ -64,12 +64,12 @@ However, using a current version of node is encouraged. ## Tutorial var Client = require('mysql').Client, - client = new Client(); + client = new Client(), + TEST_DATABASE = 'nodejs_mysl_test', + TEST_TABLE = 'test'; client.user = 'root'; client.password = 'root'; - var TEST_DATABASE = 'nodejs_mysl_test', - TEST_TABLE = 'test'; client.connect(); @@ -106,7 +106,7 @@ However, using a current version of node is encouraged. client.query( 'SELECT * FROM '+TEST_TABLE, - gently.expect(function selectCb(err, results, fields) { + function selectCb(err, results, fields) { if (err) { throw err; } @@ -114,7 +114,7 @@ However, using a current version of node is encouraged. console.log(results); console.log(fields); client.end(); - }) + } ); ## API From 15b9872741b70e6061d9f09589388380cf0e9b67 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Thu, 25 Nov 2010 12:55:02 +0100 Subject: [PATCH 24/26] Make Makfile more portable --- Makefile | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Makefile b/Makefile index a3cf21c21..c9f15e0cc 100644 --- a/Makefile +++ b/Makefile @@ -1,3 +1,5 @@ +SHELL := /bin/bash + test-simple: @find test/simple/test-*.js | xargs -n 1 -t node test-system: From cbb1fc864daa72e0163411018770b2f2831d2518 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Tue, 4 Jan 2011 00:02:44 +0100 Subject: [PATCH 25/26] Add note about multiple queries in one sql query --- Readme.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/Readme.md b/Readme.md index 49dd7400d..a993a1d33 100644 --- a/Readme.md +++ b/Readme.md @@ -165,6 +165,9 @@ query. This method returns a `Query` object which can be used to stream incoming row data. +**Warning:** `sql` statements with multiple queries separated by semicolons +are not supported yet. + ### client.ping([cb]) Sends a ping command to the server. @@ -251,6 +254,7 @@ At this point the module is ready to be tried out, but a lot of things are yet t * Performance profiling * Handle re-connect after bad credential error (should query queue be kept?) * Deal with stale connections / other potential network issues +* Decide how to handle queries with multiple statements ## License From 0c93e66f4ec909c15786a6026db7b80b954d8644 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felix=20Geisend=C3=B6rfer?= Date: Tue, 4 Jan 2011 00:04:48 +0100 Subject: [PATCH 26/26] Bump version --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 3150ad4d8..ace6ea2b8 100644 --- a/package.json +++ b/package.json @@ -1,5 +1,5 @@ { "name" : "mysql" -, "version": "0.8.0" +, "version": "0.9.0" , "devDependencies": {"gently": ">=0.8.0"} , "main" : "./lib/mysql" , "scripts" : { "test" : "make test" } pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy