2017-10-28 99 views
1

我已經在谷歌雲上創建了一個mysql數據庫,我想從一個單獨的節點web應用程序(也在谷歌雲上運行)訪問。我首先在我的計算機上本地測試連接,並且在本地運行以下代碼時,我可以成功建立與數據庫的連接並查看其中的數據。ETIMEOUT錯誤|谷歌雲SQL數據庫與NodeJS

'use strict'; 

// [START app] 
const express = require('express'); 
const bodyParser = require('body-parser'); 
const path = require('path'); 
const app = express(); 
const mysql  = require('mysql'); 

var connection = mysql.createConnection({ 
    host  : 'Cloud SQL IP', 
    user  : 'username', 
    password : 'password', 
    database : 'db_name' 
}); 



// parse application/x-www-form-urlencoded 
app.use(bodyParser.urlencoded({ extended: false })) 

// parse application/json 
app.use(bodyParser.json()) 

// Make globals.js accessible 
app.use(express.static(__dirname + '/')); 


app.get('/', (req, res) => { 
    connection.connect(); 

    connection.query('SELECT * FROM Users', function (error, results, fields) { 
     if (error) throw error; 
     console.log(results); 
    }); 

    connection.end(); 
    res.status(200).send('Hello World!'); 
}); 

app.get('/login', (req, res) => { 
    res.status(200).send(); 
}); 

// [START server] 
const PORT = process.env.PORT || 8080; 
app.listen(PORT,() => { 
    console.log(`App listening on port ${PORT}`); 
    console.log('Press Ctrl+C to quit.'); 
}); 
// [END app] 

然而,當我在谷歌應用程序引擎(在端口8080上進行調試和全面部署上https://myapp.appspot.com)執行與此相同的代碼,我得到了以下超時錯誤:

{ Error: connect ETIMEDOUT 
    at Connection._handleConnectTimeout   (/home/megan_cooper2900/project/node_modules/mysql/lib/Connection.js:419:13) 
at Socket.g (events.js:292:16) 
at emitNone (events.js:86:13) 
at Socket.emit (events.js:185:7) 
at Socket._onTimeout (net.js:338:8) 
at ontimeout (timers.js:386:14) 
at tryOnTimeout (timers.js:250:5) 
at Timer.listOnTimeout (timers.js:214:5) 
-------------------- 
at Protocol._enqueue (/home/megan_cooper2900/project/node_modules/mysql/lib/protocol/Protocol.js:145:48) 
at Protocol.handshake (/home/megan_cooper2900/project/node_modules/mysql/lib/protocol/Protocol.js:52:23) 
at Connection.connect (/home/megan_cooper2900/project/node_modules/mysql/lib/Connection.js:130:18) 
at app.get (/home/megan_cooper2900/journeyma/app.js:31:13) 
at Layer.handle [as handle_request] (/home/megan_cooper2900/project/node_modules/express/lib/router/layer.js:95:5) 
at next (/home/megan_cooper2900/project/node_modules/express/lib/router/route.js:137:13) 
at Route.dispatch (/home/megan_cooper2900/project/node_modules/express/lib/router/route.js:112:3) 
at Layer.handle [as handle_request] (/home/megan_cooper2900/project/node_modules/express/lib/router/layer.js:95:5) 
at  /home/megan_cooper2900/project/node_modules/express/lib/router/index.js:281:22 
    at Function.process_params   (/home/megan_cooper2900/project/node_modules/express/lib/router/index.js:335:12) 
    errorno: 'ETIMEDOUT', 
    code: 'ETIMEDOUT', 
    syscall: 'connect', 
    fatal: true } 

這是爲什麼不工作在Google App Engine應用程序上?

+0

在主機屬性中添加您的實例連接名稱 – Fran

+0

主機值通常不是URL形式嗎? – Megan

+0

請查看關於從NodeJS連接的許多現有問題。 tl;您需要使用App Engine中的連接支持,而不是通過IP連接。例如https://stackoverflow.com/questions/46749817/cloud-sql-instance-connection-working-locally-but-not-on-app-engine。這個問題是關於postgres的,但解決方案是一樣的。 – Vadim

回答

0

在您的mysql連接配置中,host在App Engine上不起作用。你必須使用socketPath。 socketPath是unix域套接字連接的路徑。當使用的主機和端口被忽略。 (通過在App Engine flex上使用Loopback來傳遞知識,它使我頭撞了幾天大聲笑)。它的值是您的Cloud SQL實例連接名稱

你的情況

所以,它應該是這樣的:/ CLOUDSQL /我的項目-12345:美國central1:MYDATABASE

var connection = mysql.createConnection({ sockePath : '/cloudsql/my-project-12345:us-central1:mydatabase', user : 'username', password : 'password', database : 'db_name' });

這是一個類似過程如果您在GCloud上使用Postgres並已回答here