Skip to content

Commit

Permalink
more performance gains
Browse files Browse the repository at this point in the history
  • Loading branch information
Lars-Erik Roald committed Jul 10, 2024
1 parent 30f831e commit e881a7d
Show file tree
Hide file tree
Showing 10 changed files with 215 additions and 119 deletions.
219 changes: 117 additions & 102 deletions src/getManyDto.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,62 +19,92 @@ async function getManyDto(table, filter, strategy, spanFromParent) {
return decode(strategy, span, await res[0]);
}

// function newCreateRow(span) {
// let columnsMap = span.columns;
// const columns = span.table._columns.filter(column => !columnsMap || columnsMap.get(column));
// const protoRow = createProto(columns, span);
// const manyNames = [];

// const c = {};
// c.visitJoin = () => { };
// c.visitOne = () => { };
// c.visitMany = function(leg) {
// manyNames.push(leg.name);
// };

// span.legs.forEach(onEachLeg);
// return createRow;

// function onEachLeg(leg) {
// leg.accept(c);
// }

// function createRow() {
// const obj = Object.create(protoRow);
// for (let i = 0; i < manyNames.length; i++) {
// obj[manyNames[i]] = [];
// }
// return obj;
// }
// }


function newCreateRow(span) {
let columnsMap = span.columns;
const columnsMap = span.columns;
const columns = span.table._columns.filter(column => !columnsMap || columnsMap.get(column));
const protoRow = createProto(columns, span);
const ProtoRow = createProto(columns, span);
const manyNames = [];

const c = {};
c.visitJoin = () => { };
c.visitOne = () => { };
c.visitMany = function(leg) {
manyNames.push(leg.name);
const c = {
visitJoin: () => { },
visitOne: () => { },
visitMany: function(leg) {
manyNames.push(leg.name);
}
};

span.legs.forEach(onEachLeg);
return createRow;
span.legs.forEach(leg => leg.accept(c));

function onEachLeg(leg) {
leg.accept(c);
}
return createRow;

function createRow() {
const obj = Object.create(protoRow);
for (let i = 0; i < manyNames.length; i++) {
obj[manyNames[i]] = [];
}
const obj = new ProtoRow();
manyNames.forEach(name => {
obj[name] = [];
});
return obj;
}
}

function createProto(columns, span) {
let obj = {};
for (let i = 0; i < columns.length; i++) {
obj[columns[i].alias] = null;
}
for (let key in span.aggregates) {
obj[key] = null;
}
const c = {};
function ProtoRow() {
columns.forEach(column => {
this[column.alias] = null;
});

c.visitJoin = function(leg) {
obj[leg.name] = null;
};
c.visitOne = c.visitJoin;
c.visitMany = function(leg) {
obj[leg.name] = null;
};
for (const key in span.aggregates) {
this[key] = null;
}

span.legs.forEach(onEachLeg);
const c = {
visitJoin: (leg) => {
this[leg.name] = null;
},
visitOne: (leg) => {
this[leg.name] = null;
},
visitMany: (leg) => {
this[leg.name] = null;
}
};

function onEachLeg(leg) {
leg.accept(c);
span.legs.forEach(leg => leg.accept(c));
}

return obj;
return ProtoRow;
}


function hasManyRelations(span) {
let result;
const c = {};
Expand All @@ -92,7 +122,7 @@ function hasManyRelations(span) {
}
}

async function decode(strategy, span, rows, keys = rows.length > 0 ? Object.keys(rows[0]) : []) {
async function decode(strategy, span, rows, keys = rows.length > 0 ? Object.keys(rows[0]) : [], parentRows, parentProp) {
const table = span.table;
let columnsMap = span.columns;
const columns = table._columns.filter(column => !columnsMap || columnsMap.get(column));
Expand Down Expand Up @@ -132,9 +162,11 @@ async function decode(strategy, span, rows, keys = rows.length > 0 ? Object.keys
}

outRows[i] = outRow;
if (parentRows)
parentRows[i][parentProp] = outRow;
if (shouldCreateMap) {
fkIds[i] = getIds(outRow);
addToMap(rowsMap, primaryColumns, outRow);
addToMap(rowsMap, fkIds[i], outRow);
}
}
span._rowsMap = rowsMap;
Expand Down Expand Up @@ -185,18 +217,38 @@ async function decodeManyRelations(strategy, span) {
const name = leg.name;
const table = span.table;
const relation = table._relations[name];
const filter = createOneFilter(relation, span._ids);
const rowsMap = span._rowsMap;

const filter = createOneFilter(relation, span._ids);
const extractKey = createExtractKey(leg);
const extractFromMap = createExtractFromMap(rowsMap, table._primaryColumns);
const p = getManyDto(relation.childTable, filter, strategy[name], leg.span).then(subRows => {
for (let i = 0; i < subRows.length; i++) {
const key = leg.columns.map(column => subRows[i][column.alias]);
const parentRow = getFromMap(rowsMap, table._primaryColumns, key);
const key = extractKey(subRows[i]);
const parentRow = extractFromMap(key);
parentRow[name].push(subRows[i]);
}
});
promises.push(p);
};

function createExtractKey(leg) {
if (leg.columns.length === 1) {
const alias = leg.columns[0].alias;
return (row) => row[alias];
}
else {
const aliases = leg.columns.map(column => column.alias);
return (row) => aliases.map(alias => row[alias]);
}
}
function createExtractFromMap(map, primaryColumns) {
if (primaryColumns.length === 1)
return (key) => map.get(key);
else
return getFromMap.bind(null, map, primaryColumns);
}

span.legs.forEach(onEachLeg);

function onEachLeg(leg) {
Expand All @@ -211,11 +263,7 @@ async function decodeRelations2(strategy, span, rawRows, resultRows, keys) {
const c = {};
c.visitJoin = function(leg) {
const name = leg.name;
const p = decode(strategy[name], leg.span, rawRows, keys).then((rows) => {
for (let i = 0; i < rows.length; i++) {
resultRows[i][name] = rows[i];
}
});
const p = decode(strategy[name], leg.span, rawRows, keys, resultRows, name);
promises.push(p);
};

Expand All @@ -233,47 +281,6 @@ async function decodeRelations2(strategy, span, rawRows, resultRows, keys) {
await Promise.all(promises);
}


// async function decodeRelations(strategy, span, rawRows, resultRows, keys) {
// const promises = [];
// const c = {};
// c.visitJoin = function (leg) {
// const name = leg.name;
// const p = decode(strategy[name], leg.span, rawRows, keys).then((rows) => {
// for (let i = 0; i < rows.length; i++) {
// resultRows[i][name] = rows[i];
// }
// });
// promises.push(p);
// };

// c.visitOne = c.visitJoin;

// c.visitMany = function (leg) {
// const name = leg.name;
// const table = span.table;
// const relation = table._relations[name];
// const filter = createOneFilter(relation, span._ids);
// const rowsMap = span._rowsMap;
// const p = getManyDto(relation.childTable, filter, strategy[name], leg.span).then(subRows => {
// for (let i = 0; i < subRows.length; i++) {
// const key = leg.columns.map(column => subRows[i][column.alias]);
// const parentRow = getFromMap(rowsMap, table._primaryColumns, key);
// parentRow[name].push(subRows[i]);
// }
// });
// promises.push(p);
// };

// span.legs.forEach(onEachLeg);

// function onEachLeg(leg) {
// leg.accept(c);
// }

// await Promise.all(promises);
// }

function createOneFilter(relation, ids) {
const columns = relation.joinRelation.columns;

Expand All @@ -299,28 +306,36 @@ function createOneFilter(relation, ids) {
}
}

function addToMap(map, primaryColumns, row) {

const lastIndex = primaryColumns.length - 1;
for (let i = 0; i < lastIndex; i++) {
const id = row[primaryColumns[i].alias];
if (map.has(id))
map = map.get(id);
else {
const next = new Map();
map.set(id, next);
map = next;
function addToMap(map, values, row) {
if (Array.isArray(values)) {

const lastIndex = values.length - 1;
for (let i = 0; i < lastIndex; i++) {
const id = values[i];
if (map.has(id))
map = map.get(id);
else {
const next = new Map();
map.set(id, next);
map = next;
}
}
map.set(values[lastIndex], row);
}
map.set(row[primaryColumns[lastIndex].alias], row);
else
map.set(values, row);
}

function getFromMap(map, primaryColumns, values) {
const length = primaryColumns.length;
for (let i = 0; i < length; i++) {
map = map.get(values[i]);
if (Array.isArray(values)) {
const length = primaryColumns.length;
for (let i = 0; i < length; i++) {
map = map.get(values[i]);
}
return map;
}
return map;
else
return map.get(values);
}


Expand Down
7 changes: 7 additions & 0 deletions src/table/column/binary/newEncode.js
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,13 @@ function _new(_column) {
return Buffer.from(value, 'base64');
};

encode.direct = function(value) {
value = purify(value);
if (value === null)
return null;
return Buffer.from(value, 'base64');
};

return encode;
}

Expand Down
12 changes: 12 additions & 0 deletions src/table/column/boolean/newEncode.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,18 @@ function _new(column) {
return encodeCore(value);
};

encode.direct = function(value) {
value = purify(value);
if (value === null) {
if (column.dbNull === null)
return null;
return column.dbNull ;
}
var encodeCore = getSessionSingleton('encodeBoolean');

return encodeCore(value);
};

return encode;
}

Expand Down
15 changes: 13 additions & 2 deletions src/table/column/date/newEncode.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,19 @@ function _new(column) {
value = purify(value);
if (value == null) {
if (column.dbNull === null)
return newPara('null');
return newPara('\'' + column.dbNull + '\'');
'null';
return '\'' + column.dbNull + '\'';
}
var encodeCore = getSessionSingleton('encodeDate') || encodeDate;
return encodeCore(value);
};

encode.direct = function(value) {
value = purify(value);
if (value == null) {
if (column.dbNull === null)
null;
return column.dbNull;
}
var encodeCore = getSessionSingleton('encodeDate') || encodeDate;
return encodeCore(value);
Expand Down
10 changes: 10 additions & 0 deletions src/table/column/dateWithTimeZone/newEncode.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,16 @@ function _new(column) {
return encodeDate(value);
};

encode.direct = function(value) {
value = purify(value);
if (value == null) {
if (column.dbNull === null)
return null;
return column.dbNull;
}
return encodeDate(value);
};

return encode;


Expand Down
10 changes: 10 additions & 0 deletions src/table/column/guid/newEncode.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,16 @@ function _new(column) {
return '\'' + value + '\'';
};

encode.direct = function(candidate) {
var value = purify(candidate);
if (value == null) {
if (column.dbNull === null)
return null;
return column.dbNull;
}
return value ;
};


return encode;
}
Expand Down
Loading

0 comments on commit e881a7d

Please sign in to comment.