From 3dad2bf4df2b16932af8c271f570f31b35764c55 Mon Sep 17 00:00:00 2001 From: biniam Date: Mon, 29 May 2017 15:11:21 -0400 Subject: [PATCH] switch long and lat for geopoint type MySQL expects reverse order of latitude and longitude from the way we use it in LoopBack, so switch the order when saving and loading Point spatial type we use for Point/GeoPoint. --- lib/mysql.js | 6 ++--- test/datatypes.test.js | 54 ++++++++++++++++++++++++++++++++++-------- 2 files changed, 47 insertions(+), 13 deletions(-) diff --git a/lib/mysql.js b/lib/mysql.js index 7ec1f27..ca490b3 100644 --- a/lib/mysql.js +++ b/lib/mysql.js @@ -365,7 +365,7 @@ MySQL.prototype.toColumnValue = function(prop, val) { if (prop.type.name === 'GeoPoint') { return new ParameterizedSQL({ sql: 'Point(?,?)', - params: [val.lat, val.lng], + params: [val.lng, val.lat], }); } if (prop.type === Buffer) { @@ -426,8 +426,8 @@ MySQL.prototype.fromColumnValue = function(prop, val) { case 'GeoPoint': case 'Point': val = { - lat: val.x, - lng: val.y, + lng: val.x, + lat: val.y, }; break; case 'List': diff --git a/test/datatypes.test.js b/test/datatypes.test.js index 24dd4bf..d3611e6 100644 --- a/test/datatypes.test.js +++ b/test/datatypes.test.js @@ -9,6 +9,7 @@ var assert = require('assert'); var _ = require('lodash'); var db, BlobModel, EnumModel, ANIMAL_ENUM, City, Account; + var mysqlVersion; describe('MySQL specific datatypes', function() { @@ -58,7 +59,7 @@ describe('MySQL specific datatypes', function() { it('create an instance', function(done) { Account.create(data, function(err, result) { - assert(!err); + if (err) return done(err); assert(result); assert(_.isEqual(data.length, result.length)); assert(_.isEqual(data[0].amount, result[0].amount)); @@ -69,7 +70,7 @@ describe('MySQL specific datatypes', function() { it('find an instance', function(done) { Account.find(function(err, result) { - assert(!err); + if (err) return done(err); assert(result); assert(_.isEqual(data.length, result.length)); assert(_.isEqual(data[0].amount, result[0].amount)); @@ -82,7 +83,7 @@ describe('MySQL specific datatypes', function() { it('find an instance by id', function(done) { Account.findById(1, function(err, result) { - assert(!err); + if (err) return done(err); assert(result); assert(_.isEqual(data[0].amount, result.amount)); assert(_.isEqual(dateForTransactions[0], result.lastTransaction)); @@ -97,7 +98,7 @@ describe('MySQL specific datatypes', function() { users: {}, }; Account.update({id: 1}, updatedData, function(err, result) { - assert(!err); + if (err) return done(err); assert(result); assert(result.count); assert.equal(1, result.count); @@ -125,10 +126,10 @@ describe('MySQL specific datatypes', function() { it('should create a model instance with Enums', function(done) { var em = EnumModel.create({animal: ANIMAL_ENUM.CAT, condition: 'sleepy', mood: 'happy'}, function(err, obj) { - assert.ok(!err); + if (err) return done(err); assert.equal(obj.condition, 'sleepy'); EnumModel.findOne({where: {animal: ANIMAL_ENUM.CAT}}, function(err, found) { - assert.ok(!err); + if (err) return done(err); assert.equal(found.mood, 'happy'); assert.equal(found.animal, ANIMAL_ENUM.CAT); done(); @@ -153,10 +154,10 @@ describe('MySQL specific datatypes', function() { var extras = {c: 3, d: '4'}; var em = EnumModel.create({animal: ANIMAL_ENUM.DOG, condition: 'sleepy', mood: 'happy', note: note, extras: extras}, function(err, obj) { - assert.ok(!err); + if (err) return done(err); assert.equal(obj.condition, 'sleepy'); EnumModel.findOne({where: {animal: ANIMAL_ENUM.DOG}}, function(err, found) { - assert.ok(!err); + if (err) return done(err); assert.equal(found.mood, 'happy'); assert.equal(found.animal, ANIMAL_ENUM.DOG); assert.deepEqual(found.note, note); @@ -170,15 +171,43 @@ describe('MySQL specific datatypes', function() { var name = 'bob'; var bob = {name: name, bin: new Buffer.from(str)}; BlobModel.create(bob, function(err, obj) { - assert.ok(!err); + if (err) return done(err); assert.equal(obj.bin.toString(), str); BlobModel.findOne({where: {name: name}}, function(err, found) { - assert.ok(!err); + if (err) return done(err); assert.equal(found.bin.toString(), str); done(); }); }); }); + it('should create a model instance with geopoint type', function(done) { + var city1 = { + name: 'North York', + loc: { + lat: 43.761539, + lng: -79.411079, + }, + }; + var xcor, ycor; + City.create(city1, function(err, res) { + if (err) return done(err); + res.loc.should.deepEqual(city1.loc); + res.name.should.equal(city1.name); + var sqlStmt = 'select ST_X(loc),ST_Y(loc) from City where id=1'; + db.connector.execute(sqlStmt, function(err, res) { + if (err) return done(err); + xcor = res[0]['ST_X(loc)']; + ycor = res[0]['ST_Y(loc)']; + City.find({where: {name: city1.name}}, function(err, found) { + if (err) return done(err); + found[0].name.should.equal(city1.name); + found[0].loc.lng.should.equal(xcor); + found[0].loc.lat.should.equal(ycor); + done(); + }); + }); + }); + }); it('should disconnect when done', function(done) { db.disconnect(); done(); @@ -203,6 +232,11 @@ function setup(done) { bin: {type: Buffer, dataType: 'blob', null: false}, name: {type: String}, }); + + City = db.define('City', { + name: {type: String}, + loc: {type: 'GeoPoint'}, + }); query('SELECT VERSION()', function(err, res) { mysqlVersion = res && res[0] && res[0]['VERSION()']; blankDatabase(db, done);