I created a React project by entering the following command prompt commands
mkdir mysql-test && cd mysql-test
npm init –y
npm install mysql –save
Then I created a file called app.js and I put in the following code:
// app.js
const mysql = require('mysql');
// First you need to create a connection to the db
const con = mysql.createConnection({
host: 'rds-mysql-wmcw.cgz0te1dlkah.us-east-1.rds.amazonaws.com',
user: 'masterUsername',
password: 'masterPassword',
database : 'db_wmcw'
});
//try to connect to the mySql database. If an error occurs, display an
error message on the console
con.connect((err) => {
if(err){
console.log('Error connecting to Db');
return;
}
//a connection has been established to the database. Now, run a query against the table 'homepage'
//to retrieve each row and all columns of the table
console.log('Connection established');
con.query('SELECT * FROM homepage', (err,rows) => {
//if an error occurs when reading the data from the table, display the error on the console
if(err) {
console.log(err);
return;
}
//data has been retrieved from the table. display the data to the console
console.log('Data received from Db:\n');
console.log(rows);
});
});
con.end((err) => {
// The connection is terminated gracefully
// Ensures all previously enqueued queries are still
// before sending a COM_QUIT packet to the MySQL server.
});
Before I added the con.query command, when I type in app.js at the command prompt, the response back is Connection established. So I know that I am connecting to the mySql database. When I include the con.query command, and I type in app.js at the command prompt, I get the following error:
Connection established
{ Error: Cannot enqueue Query after invoking quit.
at Protocol._validateEnqueue (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\protocol\Protocol.js:203:16)
at Protocol._enqueue (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\protocol\Protocol.js:138:13)
at Connection.query (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\Connection.js:200:25)
at Handshake.con.connect (C:\jrs\codercamp\mysql-test\app.js:21:7)
at Handshake. (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\Connection.js:502:10)
at Handshake._callback (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\Connection.js:468:16)
at Handshake.Sequence.end (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\protocol\sequences\Sequence.js:83:24)
at Handshake.Sequence.OkPacket (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\protocol\sequences\Sequence.js:92:8)
at Protocol._parsePacket (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\protocol\Protocol.js:278:23)
at Parser.write (C:\jrs\codercamp\mysql-test\node_modules\mysql\lib\protocol\Parser.js:76:12) code: 'PROTOCOL_ENQUEUE_AFTER_QUIT', fatal: false }
Right at the top of the error it states Cannot enqueue Query after invoking quit. I don't understand why the system thinks I am executing the query after invoking quit. I am not invoking quit unless that is what happens when I execute con.end but con.end is the last statement to execute. It is way after the query call.
Any assistance is greatly appreciated.
Thank you.
PS - I have included the host name, user ID, password, and database name to make debugging easier. There is no real important data in the database
Okay, so the alternative solution would be uninstall mysql package and change with mysql2 package instead. As the author said:
MySQL2 is mostly API compatible with mysqljs and supports majority of features
This answer is for the questioner's comment on his post
If you really wanna reassign the one row of data, you can do:
const { product_detail, product_description } = results[0];
That's basic syntax :D (ES6 maybe)
Related
Whenever i try to connect my express.js app to the node server. I get an error(see below console message).
Earlier, before dockerizing my app everything used to run smoothly but after creating my mysql-image-container(docker) and running mysql through docker everything went well. But now, when i try to connect my app with SQL server and not through the docker-container i get the following error
(node:22136) UnhandledPromiseRejectionWarning: SequelizeAccessDeniedError: Access denied for user 'root'#'localhost' (using password: YES)
at ConnectionManager.connect (C:\Users\A\ARISE1\node_modules\sequelize\lib\dialects\mysql\connection-manager.js:94:17)
at processTicksAndRejections (internal/process/task_queues.js:95:5)
at async ConnectionManager._connect (C:\Users\A\ARISE1\node_modules\sequelize\lib\dialects\abstract\connection-manager.js:220:24)
at async C:\Users\A\ARISE1\node_modules\sequelize\lib\dialects\abstract\connection-manager.js:174:32
at async ConnectionManager.getConnection (C:\Users\A\ARISE1\node_modules\sequelize\lib\dialects\abstract\connection-manager.js:197:7)
at async C:\Users\A\ARISE1\node_modules\sequelize\lib\sequelize.js:304:26
at async MySQLQueryInterface.tableExists (C:\Users\A\ARISE1\node_modules\sequelize\lib\dialects\abstract\query-interface.js:102:17)
at async Function.sync (C:\Users\A\ARISE1\node_modules\sequelize\lib\model.js:939:21)
at async Sequelize.sync (C:\Users\A\ARISE1\node_modules\sequelize\lib\sequelize.js:376:9)
(Use node --trace-warnings ... to show where the warning was created)
(node:22136) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). To terminate the node process on unhandled promise rejection, use the CLI flag --unhandled-rejections=strict (see https://nodejs.org/api/cli.html#cli_unhandled_rejections_mode). (rejection id: 1)
(node:22136) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
I have tried deleting docker file, mysql-image-container(from docker) but am still unable to connect my app with local mysql server. And now if i even try to connect to my database through SQL-command line, i am unable to do so, even with correct credentials. Though I'm able to connect to the database through MySQL Workbench.
The docker command used to build-image/run the container is:
docker run -p 3306:3306 --name nodejs-mysql -e MYSQL_ROOT_PASSWORD=pass -e MYSQL_DATABASE=database -d mysql:5.7
before this, i used to right-click on the dockerfile and choose build image option.
I didn't completely understood the contents of Dockerfile and so i mixed some code from online sources.
Any help would be well appreciated.
const sequelize = new Sequelize( username, password, database, {
host: host,
dialect: dialect
});
Instead of above, it should be this
const sequelize = new Sequelize( database, username, password, {
host: host,
dialect: dialect
});
Please share your code.
Also see the the code below on how you establish a connection
const { Sequelize,DataTypes } = require('sequelize');
const config={
HOST:"localhost",// you can replace this with the url of where your server is hosted or an ip adress
USER:"root",
PASSWORD:"yourpassword",
DB:"yourDb",
dialect:"mysql",//sqlite, mariadb
pool:{
max:5,
min:0,
acquire:30000,
idle:10000
}
const sequelize= new Sequelize(
config.DB,
config.USER,
config.PASSWORD,
{
host:config.HOST,
dialect:config.dialect,
operatorAliases:false,
pool:{
max:config.pool.max,
min:config.pool.min,
acquire:config.pool.acquire,
idle:config.pool.idle
}
}
)
try {
await sequelize.authenticate();
console.log('Connection has been established successfully.');
} catch (error) {
console.error('Unable to connect to the database:', error);
}
I am trying to run a migration using Knex, to a Cloud Data Platform and I am coming across some issues.
I am following knex.org's documentation, so I added the following lines (with specific connection details which I have removed. I checked several times that the environment variables were correct.) to my knexfile.js file.
module.exports = {
development: {
client: 'mysql',
connection: {
port: 'port',
host: 'host',
database: 'database',
user: 'user',
password: 'password'
},
pool: {
min: 2,
max: 10,
},
migrations: {
tableName:'knex_migrations',
},
debug: false
}
};
My init file contains the following:
exports.up = function(knex) {
return knex.schema.createTable('person', table => {
table.increments('id');
table.string('email').notNullable().unique();
table.string('first_name').notNullable();
table.string('last_name').notNullable();
table.timestamps(true,true);
})
};
exports.down = function(knex) {
return knex.schema.dropTable('person');
};
When I run npx knex migrate:latest, from the terminal (Mac) as show here:
$ npx knex migrate:latest --knexfile database/knexfile.js
I obtain the following error, and I cannot seem to figure out where the error is coming from.
Working directory changed to ~/Desktop/knex-tutorial/database
Using environment: development
/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/protocol/Parser.js:437
throw err; // Rethrow non-MySQL errors
^
RangeError [ERR_OUT_OF_RANGE]: The value of "sourceStart" is out of range. It must be <= 9. Received 13
at new NodeError (node:internal/errors:388:5)
at _copy (node:buffer:237:11)
at Buffer.copy (node:buffer:780:12)
at Parser.parseBuffer (/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/protocol/Parser.js:272:16)
at HandshakeInitializationPacket.parse (/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/protocol/packets/HandshakeInitializationPacket.js:34:37)
at Protocol._parsePacket (/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/protocol/Protocol.js:272:12)
at Parser._parsePacket (/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/protocol/Parser.js:433:10)
at Parser.write (/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/protocol/Parser.js:43:10)
at Protocol.write (/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/protocol/Protocol.js:38:16)
at Socket.<anonymous> (/Users/user/Desktop/knex-tutorial/node_modules/mysql/lib/Connection.js:88:28) {
code: 'ERR_OUT_OF_RANGE'
}
Node.js v18.4.0
I have searched everywhere online and I came across these two posts (one points towards the other), and I did try this, but I had no success.
MySQL 8.0 - Client does not support authentication protocol requested by server; consider upgrading MySQL client
RangeError [ERR_OUT_OF_RANGE]: The value of "sourceStart" is out of range. It must be <= 9. Received 13
I am fairly new to all of this and I am learning.
I would appreciate any help possible.
If more info is needed, let me know what I can/should add for clarification.
I have my Express js connect to multiple dbs. Which works everytime I startup my app. But As soon as my connection to my database goes stale... the connection returns an error code of PROTOCOL_CONNECTION_LOST. Which is normal for a mysql when a connection is idle. My mysql server is deployed in AWS RDS which also works just fine.
The problem is, everytime my express app encounters the PROTOCOL_CONNECTION_LOST error, it should reconnect to the database, which in fact also works. BUUT when I try to make queries to my MYSQL db. It returns a Error: Cannot enqueue Query after fatal error. error. I've been dealing with this for a while, and my workaround is to restart the express app everytime. hope someone else has encountered this and could give an advice.
Here is my sample code for connecting to db:
var mysql = require('mysql');
var mysqlConn
// mysqlConn.connect();
function handleDisconnect() {
mysqlConn = mysql.createConnection({
host: 'aws_instance***',
user: '******',
password: '*****',
database: 'my_db',
multipleStatements: true
});
mysqlConn.connect(function (err) {
if (err) {
console.log('ERROR CONNECT admin:', err.code + '--' + err.address);
setTimeout(handleDisconnect, 2000);
} else {
console.log('Connected to DB')
}
});
mysqlConn.on('error', function (err) {
console.log('ERROR admin', err.code + '--' + err.address);
if (err.code === 'PROTOCOL_CONNECTION_LOST') { // Connection to the MySQL server is usually
console.log("Connection to db lost!")
handleDisconnect(); // lost due to either server restart, or a
} else {
console.log(err) // connnection idle timeout (the wait_timeout
throw err; // server variable configures this)
}
});
}
handleDisconnect();
module.exports = {
mysqlConn: mysqlConn,
};
Then here is my output logs as shown in my server logs.
ERROR db PROTOCOL_CONNECTION_LOST--undefined
Connection to db lost!
Connected to db
OPTIONS /verify-token/ 200 0.285 ms - 4
Error: Cannot enqueue Query after fatal error.
POST /verify-token/ 500 1.332 ms - 95
OPTIONS /auth/login 200 0.793 ms - 4
Error: Cannot enqueue Query after fatal error.
POST /login 500 1.564 ms - 58
OPTIONS /login 200 0.687 ms - 4
Error: Cannot enqueue Query after fatal error.
POST /login 500 1.467 ms - 58
While there are workarounds, they apparently don't work for everyone. The suggestion in the documentation is to use connection pooling instead of manually managing individual connections.
I have no trouble connecting to the live database locally using port forwarding, but when we go to connect from the openshift gear, we get errors. Let me begin with the code:
Here is the connection variable
var connectionpool = mysql.createPool({
host : process.env.OPENSHIFT_MYSQL_DB_HOST,
port : process.env.OPENSHIFT_MYSQL_DB_PORT,
user : process.env.OPENSHIFT_MYSQL_DB_USERNAME,
password : process.env.OPENSHIFT_MYSQL_DB_PASSWORD,
database : 'stembuds',
socket : process.env.OPENSHIFT_MYSQL_DB_SOCKET
});
Here is an example of a query:
app.get('/answerDB/:course?/:answerID?', function(req, res){
var course = req.param('course');
var answerID = req.param('answerID');
connectionpool.getConnection(function(err, connection){
if(err){
console.error('CONNECTION error: ',err);
res.statusCode = 503;
res.send({
result: 'error',
err: err.code
});
}
if (course === undefined && answerID === undefined) {
connection.query('SELECT * FROM questions WHERE counter = 0', function(err, rows, fields){
if (err) {
console.error(err);
res.statusCode = 500;
res.send({
result: 'error',
err: err.code
});
}
for(var i in rows){
var newCourse = rows[i].course;
newCourse = courses[newCourse];
rows[i].course = newCourse;
}
res.send(rows);
connection.release();
});
}
Here are some errors we receive.
First is an error in the console of Chrome:
GET http://**.rhcloud.com/answerDB 503 (Service Temporarily Unavailable)
But sometimes we get a proxy error:
GET http://**.rhcloud.com/exploreDB 502 (Proxy Error)
Additionally, I have been running the command rhc tail -a nodejs and here is the error I am receiving
CONNECTION error: { [Error: ER_ACCESS_DENIED_ERROR: Access denied for user 'adminMYXaSuf'#'127.11.28.130' (using password: YES)]
code: 'ER_ACCESS_DENIED_ERROR',
errno: 1045,
sqlState: '28000',
fatal: true }
TypeError: Cannot call method 'query' of undefined
at /var/lib/openshift/5303aee55973ca4092000084/app-root/runtime/repo/routes/site.js:172:15
at Pool.<anonymous> (/var/lib/openshift/5303aee55973ca4092000084/app- root/runtime/repo/node_modules/mysql/lib/Pool.js:49:16)
at Handshake.Sequence.end (/var/lib/openshift/5303aee55973ca4092000084/app-root/runtime/repo/node_modules/mysql/lib/protocol/sequences/Sequence.js:78:24)
at Handshake.ErrorPacket (/var/lib/openshift/5303aee55973ca4092000084/app-root/runtime/repo/node_modules/mysql/lib/protocol/sequences/Handshake.js:93:8)
at Protocol._parsePacket (/var/lib/openshift/5303aee55973ca4092000084/app-root/runtime/repo/node_modules/mysql/lib/protocol/Protocol.js:202:24)
at Parser.write (/var/lib/openshift/5303aee55973ca4092000084/app-root/runtime/repo/node_modules/mysql/lib/protocol/Parser.js:62:12)
at Protocol.write (/var/lib/openshift/5303aee55973ca4092000084/app-root/runtime/repo/node_modules/mysql/lib/protocol/Protocol.js:37:16)
at Socket.<anonymous> (/var/lib/openshift/5303aee55973ca4092000084/app-root/runtime/repo/node_modules/mysql/lib/Connection.js:72:28)
at Socket.EventEmitter.emit (events.js:95:17)
at Socket.<anonymous> (_stream_readable.js:720:14)
Now it says cannot call method query of undefined. We thought that was strange, so we changed 'connection.query' to 'connectionpool.query' and it then told us that it cannot call method release of undefined. So we changed 'connection.release()' to 'connectionpool.release()' and it told us that the object # has no method release. So I am taking that part of the error with a grain of salt.
We have no idea why it wont connect. Any information would be greatly appreciated - Thanks.
If your application code works locally while connecting to your remote OpenShift-hosted DB (using rhc port-forward), then I would suspect that your app may have some undocumented dependencies.
It could be that you've installed something locally (or globally) in your dev environment, without including that dep in your app's package.json file.
Make sure that everything your app needs in order to run in a fresh environment is included in your app's package.json file before pushing it to OpenShift.
npm install my_dependency --save
I've written up some additional notes that might be useful for testing locally with a port-forwarded connection to an OpenShift-hosted DB: https://www.openshift.com/blogs/set-up-local-access-to-openshift-hosted-services-with-port-forwarding
Did you create that database name? It should be the name of your application. You can use the OPENSHIFT_APP_NAME environment variable for your database name. Can you ssh into your gear and connect to mysql without any issues? Also, are you trying to connect to the database on your openshift gear from your local machine or from your openshift gear?
I use node.js, an asynchronous event base server with mysql module to select 122 rows of records from the database.
I ran a simple stress test using the command below:
ab -n 10 -c 2 http://localhost:8000/
the node.js finish the process, but mysql is still running, until it hits an error:
throw new Error('Socket is not writable');
^
Error: Socket is not writable
at Socket._writeOut (net.js:391:11)
at Socket.write (net.js:377:17)
at Client.write (/home/kelvin/node_modules/mysql/lib/client.js:142:16)
at Object.end [as fn] (/home/kelvin/node_modules/mysql/lib/client.js:240:10)
at Client._dequeue (/home/kelvin/node_modules/mysql/lib/client.js:274:18)
at Object.end [as fn] (/home/kelvin/node_modules/mysql/lib/client.js:247:10)
at Client._dequeue (/home/kelvin/node_modules/mysql/lib/client.js:274:18)
at Object.end [as fn] (/home/kelvin/node_modules/mysql/lib/client.js:247:10)
at Client._dequeue (/home/kelvin/node_modules/mysql/lib/client.js:274:18)
at Object.end [as fn] (/home/kelvin/node_modules/mysql/lib/client.js:247:10)
Now whenever I run the test again, I get the same error.
Is MySQL a good solution to use with Node.js or is it how I code?
Some node.js code:
var server = http.createServer(function (request, response) {
response.writeHead(200, {"Content-Type": "text/plain"});
client.query('USE ' + db);
client.query('SELECT * FROM ' + tbl,
function selectDb(err, results, fields) {
if (err) {
throw err;
}
console.log(results);
client.end();
}
);
response.end("END RESULT");
});
You share one mysql connection object for every connection: When two clients request a page simultanously you maybe destroy the internal state of your mysql library while it is not intended to send a new query when another query is right now executing.
Use one mysql connection for every request, you can use node-pool if you want pooling for mysql connections.