var Types = require('../constants/types'); var Charsets = require('../constants/charsets'); var Field = require('./Field'); var IEEE_754_BINARY_64_PRECISION = Math.pow(2, 53); module.exports = RowDataPacket; function RowDataPacket() { } Object.defineProperty(RowDataPacket.prototype, 'parse', { configurable : true, enumerable : false, value : parse }); Object.defineProperty(RowDataPacket.prototype, '_typeCast', { configurable : true, enumerable : false, value : typeCast }); function parse(parser, fieldPackets, typeCast, nestTables, connection) { var self = this; var next = function () { return self._typeCast(fieldPacket, parser, connection.config.timezone, connection.config.supportBigNumbers, connection.config.bigNumberStrings, connection.config.dateStrings); }; for (var i = 0; i < fieldPackets.length; i++) { var fieldPacket = fieldPackets[i]; var value; if (typeof typeCast === 'function') { value = typeCast.apply(connection, [ new Field({ packet: fieldPacket, parser: parser }), next ]); } else { value = (typeCast) ? this._typeCast(fieldPacket, parser, connection.config.timezone, connection.config.supportBigNumbers, connection.config.bigNumberStrings, connection.config.dateStrings) : ( (fieldPacket.charsetNr === Charsets.BINARY) ? parser.parseLengthCodedBuffer() : parser.parseLengthCodedString() ); } if (typeof nestTables === 'string' && nestTables.length) { this[fieldPacket.table + nestTables + fieldPacket.name] = value; } else if (nestTables) { this[fieldPacket.table] = this[fieldPacket.table] || {}; this[fieldPacket.table][fieldPacket.name] = value; } else { this[fieldPacket.name] = value; } } } function typeCast(field, parser, timeZone, supportBigNumbers, bigNumberStrings, dateStrings) { var numberString; switch (field.type) { case Types.TIMESTAMP: case Types.TIMESTAMP2: case Types.DATE: case Types.DATETIME: case Types.DATETIME2: case Types.NEWDATE: var dateString = parser.parseLengthCodedString(); if (typeMatch(field.type, dateStrings)) { return dateString; } if (dateString === null) { return null; } var originalString = dateString; if (field.type === Types.DATE) { dateString += ' 00:00:00'; } if (timeZone !== 'local') { dateString += ' ' + timeZone; } var dt = new Date(dateString); if (isNaN(dt.getTime())) { return originalString; } return dt; case Types.TINY: case Types.SHORT: case Types.LONG: case Types.INT24: case Types.YEAR: case Types.FLOAT: case Types.DOUBLE: numberString = parser.parseLengthCodedString(); return (numberString === null || (field.zeroFill && numberString[0] === '0')) ? numberString : Number(numberString); case Types.NEWDECIMAL: case Types.LONGLONG: numberString = parser.parseLengthCodedString(); return (numberString === null || (field.zeroFill && numberString[0] === '0')) ? numberString : ((supportBigNumbers && (bigNumberStrings || (Number(numberString) >= IEEE_754_BINARY_64_PRECISION) || Number(numberString) <= -IEEE_754_BINARY_64_PRECISION)) ? numberString : Number(numberString)); case Types.BIT: return parser.parseLengthCodedBuffer(); case Types.STRING: case Types.VAR_STRING: case Types.TINY_BLOB: case Types.MEDIUM_BLOB: case Types.LONG_BLOB: case Types.BLOB: return (field.charsetNr === Charsets.BINARY) ? parser.parseLengthCodedBuffer() : parser.parseLengthCodedString(); case Types.GEOMETRY: return parser.parseGeometryValue(); default: return parser.parseLengthCodedString(); } } function typeMatch(type, list) { if (Array.isArray(list)) { return list.indexOf(Types[type]) !== -1; } else { return Boolean(list); } }