Skip to content

Commit

Permalink
Add GCF SQL samples (#723)
Browse files Browse the repository at this point in the history
* Initial commit of SQL samples

* Move some deps to devDeps
  • Loading branch information
Ace Nassri authored Aug 27, 2018
1 parent 85b1c39 commit 19ec919
Show file tree
Hide file tree
Showing 3 changed files with 218 additions and 0 deletions.
91 changes: 91 additions & 0 deletions functions/sql/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
/**
* Copyright 2018, Google LLC.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

'use strict';

const process = require('process'); // Allow env variable mocking

// [START functions_sql_mysql]
const mysql = require('mysql');
// [END functions_sql_mysql]

// [START functions_sql_postgres]
const pg = require('pg');
// [END functions_sql_postgres]

// [START functions_sql_mysql]
// [START functions_sql_postgres]

/**
* TODO(developer): specify SQL connection details
*/
const connectionName = process.env.INSTANCE_CONNECTION_NAME || '<YOUR INSTANCE CONNECTION NAME>';
const dbUser = process.env.SQL_USER || '<YOUR DB USER>';
const dbPassword = process.env.SQL_PASSWORD || '<YOUR DB PASSWORD>';
const dbName = process.env.SQL_NAME || '<YOUR DB NAME>';

// [END functions_sql_postgres]
// [END functions_sql_mysql]

// [START functions_sql_mysql]
const mysqlConfig = {
connectionLimit: 1,
user: dbUser,
password: dbPassword,
database: dbName
};
if (process.env.NODE_ENV === 'production') {
mysqlConfig.socketPath = `/cloudsql/${connectionName}`;
}

const mysqlPool = mysql.createPool(mysqlConfig);

exports.mysqlDemo = (req, res) => {
mysqlPool.query('SELECT NOW() AS now', (err, results) => {
if (err) {
console.error(err);
res.status(500).send(err);
} else {
res.send(JSON.stringify(results));
}
});
};
// [END functions_sql_mysql]

// [START functions_sql_postgres]
const pgConfig = {
max: 1,
user: dbUser,
password: dbPassword,
database: dbName
};

if (process.env.NODE_ENV === 'production') {
pgConfig.socketPath = `/cloudsql/${connectionName}`;
}

const pgPool = new pg.Pool(pgConfig);

exports.postgresDemo = (req, res) => {
pgPool.query('SELECT NOW() as now', (err, results) => {
if (err) {
console.error(err);
res.status(500).send(err);
} else {
res.send(JSON.stringify(results));
}
});
};
// [END functions_sql_postgres]
47 changes: 47 additions & 0 deletions functions/sql/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
{
"name": "nodejs-docs-samples-functions-sql",
"version": "0.0.1",
"private": true,
"license": "Apache-2.0",
"author": "Google Inc.",
"repository": {
"type": "git",
"url": "https://github.com/GoogleCloudPlatform/nodejs-docs-samples.git"
},
"engines": {
"node": ">=4.3.2"
},
"scripts": {
"start-proxy-mysql": "cloud_sql_proxy -instances=$INSTANCE_CONNECTION_NAME-mysql=tcp:3306 &",
"start-proxy-pg": "cloud_sql_proxy -instances=$INSTANCE_CONNECTION_NAME-pg=tcp:5432 &",
"start-proxy": "! pgrep cloud_sql_proxy > /dev/null && npm run start-proxy-pg && npm run start-proxy-mysql || exit 0",
"kill-proxy": "killall cloud_sql_proxy",
"lint": "repo-tools lint",
"pretest": "npm run lint",
"ava": "ava -T 20s --verbose test/*.test.js",
"test": "npm run start-proxy && npm run ava && npm run kill-proxy"
},
"dependencies": {
"mysql": "^2.16.0",
"pg": "^7.4.3"
},
"devDependencies": {
"@google-cloud/nodejs-repo-tools": "^2.3.3",
"ava": "0.25.0",
"proxyquire": "^2.1.0",
"semistandard": "^12.0.1",
"sinon": "4.4.2"
},
"cloud-repo-tools": {
"requiresKeyFile": true,
"requiresProjectId": true,
"requiredEnvVars": [
"MYSQL_USER",
"MYSQL_PASSWORD",
"MYSQL_DATABASE",
"POSTGRES_USER",
"POSTGRES_PASSWORD",
"POSTGRES_DATABASE"
]
}
}
80 changes: 80 additions & 0 deletions functions/sql/test/index.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
/**
* Copyright 2018, Google LLC.
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

'use strict';

const sinon = require(`sinon`);
const test = require(`ava`);
const proxyquire = require(`proxyquire`);

const INSTANCE_PREFIX = `nodejs-docs-samples:us-central1:integration-tests-instance`;

const getProgram = (env) => {
return proxyquire(`../`, {
process: {
env: env
}
});
};

test(`should query MySQL`, async (t) => {
const program = getProgram({
INSTANCE_CONNECTION_NAME: `${INSTANCE_PREFIX}-mysql`,
SQL_USER: process.env.MYSQL_USER,
SQL_PASSWORD: process.env.MYSQL_PASSWORD,
SQL_NAME: process.env.MYSQL_DATABASE
});

const resMock = {
status: sinon.stub().returnsThis(),
send: sinon.stub()
};

program.mysqlDemo(null, resMock);

// Give the query time to complete
await new Promise(resolve => { setTimeout(resolve, 1500); });

t.false(resMock.status.called);
t.true(resMock.send.calledOnce);

const response = resMock.send.firstCall.args[0];
t.regex(response, /\d{4}-\d{1,2}-\d{1,2}/);
});

test(`should query Postgres`, async (t) => {
const program = getProgram({
INSTANCE_CONNECTION_NAME: `${INSTANCE_PREFIX}-pg`,
SQL_USER: process.env.POSTGRES_USER,
SQL_PASSWORD: process.env.POSTGRES_PASSWORD,
SQL_NAME: process.env.POSTGRES_DATABASE
});

const resMock = {
status: sinon.stub().returnsThis(),
send: sinon.stub()
};

program.postgresDemo(null, resMock);

// Give the query time to complete
await new Promise(resolve => { setTimeout(resolve, 1500); });

t.false(resMock.status.called);
t.true(resMock.send.calledOnce);

const response = resMock.send.firstCall.args[0];
t.regex(response, /\d{4}-\d{1,2}-\d{1,2}/);
});

0 comments on commit 19ec919

Please sign in to comment.