Skip to content

Commit

Permalink
HCK-7455: FE cross-target relationships in container level script (#223)
Browse files Browse the repository at this point in the history
  • Loading branch information
Vitalii4as authored Aug 1, 2024
1 parent af30aee commit 0816cd4
Show file tree
Hide file tree
Showing 3 changed files with 119 additions and 90 deletions.
84 changes: 44 additions & 40 deletions forward_engineering/api.js
Original file line number Diff line number Diff line change
Expand Up @@ -51,19 +51,21 @@ const { getDataForSampleGeneration } = require('./sampleGeneration/sampleGenerat
*/

const parseEntities = (entities, serializedItems) => {
return entities.reduce((result, entityId) => {
try {
return Object.assign({}, result, {
[entityId]: JSON.parse(serializedItems[entityId]),
});
} catch (e) {
return result;
}
}, {});
return (
entities?.reduce((result, entityId) => {
try {
return Object.assign({}, result, {
[entityId]: JSON.parse(serializedItems[entityId]),
});
} catch (e) {
return result;
}
}, {}) ?? {}
);
};

/**
* @param data {CoreData}
* @param {CoreData} data
* @return {{
* jsonSchema: unknown,
* modelDefinitions: ModelDefinitions | unknown,
Expand Down Expand Up @@ -97,7 +99,7 @@ const parseDataForEntityLevelScript = data => {
};

/**
* @param data {CoreData}
* @param {CoreData} data
* @return {{
* modelDefinitions: ModelDefinitions | unknown,
* internalDefinitions: InternalDefinitions | unknown,
Expand All @@ -115,6 +117,7 @@ const parseDataForContainerLevelScript = data => {
const externalDefinitions = JSON.parse(data.externalDefinitions);
const entitiesJsonSchema = parseEntities(data.entities, data.jsonSchema);
const internalDefinitions = parseEntities(data.entities, data.internalDefinitions);
const relatedSchemas = parseEntities(data.relatedEntities, data.relatedSchemas);
const { jsonData, entitiesData } = getDataForSampleGeneration(data, entitiesJsonSchema);

return {
Expand All @@ -126,12 +129,13 @@ const parseDataForContainerLevelScript = data => {
entitiesJsonSchema,
jsonData,
entitiesData,
relatedSchemas,
};
};

/**
* @param script {string}
* @param sample {string}
* @param {string} script
* @param {string} sample
* @return {Array<{ title: string, script: string, mode: string }>}
* */
const getScriptAndSampleResponse = (script, sample) => {
Expand All @@ -151,8 +155,8 @@ const getScriptAndSampleResponse = (script, sample) => {
};

/**
* @param data {CoreData}
* @param app {App}
* @param {CoreData} data
* @param {App} app
* @return {Promise<{
* container: string,
* entities: Array<{ name: string, script: string }>,
Expand Down Expand Up @@ -181,8 +185,8 @@ const getContainerScriptWithSeparateBuckets = async (app, data) => {
};

/**
* @param data {CoreData}
* @param app {App}
* @param {CoreData} data
* @param {App} app
* @return {Promise<string | Array<{ title: string, script: string, mode: string }>>}
* */
const getContainerScriptWithNotSeparateBuckets = async (app, data) => {
Expand Down Expand Up @@ -220,10 +224,10 @@ const getContainerScriptWithNotSeparateBuckets = async (app, data) => {

module.exports = {
/**
* @param data {CoreData}
* @param logger {Logger}
* @param callback {PluginCallback}
* @param app {App}
* @param {CoreData} data
* @param {Logger} logger
* @param {PluginCallback} callback
* @param {App} app
* */
generateScript(data, logger, callback, app) {
try {
Expand All @@ -248,10 +252,10 @@ module.exports = {
},

/**
* @param data {CoreData}
* @param logger {Logger}
* @param callback {PluginCallback}
* @param app {App}
* @param {CoreData} data
* @param {Logger} logger
* @param {PluginCallback} callback
* @param {App} app
* */
generateViewScript(data, logger, callback, app) {
try {
Expand Down Expand Up @@ -281,10 +285,10 @@ module.exports = {
},

/**
* @param data {CoreData}
* @param logger {Logger}
* @param callback {PluginCallback}
* @param app {App}
* @param {CoreData} data
* @param {Logger} logger
* @param {PluginCallback} callback
* @param {App} app
* */
async generateContainerScript(data, logger, callback, app) {
try {
Expand All @@ -308,10 +312,10 @@ module.exports = {
},

/**
* @param data {CoreData}
* @param logger {Logger}
* @param cb {PluginCallback}
* @param app {App}
* @param {CoreData} data
* @param {Logger} logger
* @param {PluginCallback} cb
* @param {App} app
* */
async applyToInstance(data, logger, cb, app) {
const connectionData = {
Expand All @@ -334,9 +338,9 @@ module.exports = {
},

/**
* @param connectionInfo {CoreData}
* @param logger {Logger}
* @param cb {PluginCallback}
* @param {CoreData} connectionInfo
* @param {Logger} logger
* @param {PluginCallback} cb
* */
async testConnection(connectionInfo, logger, cb) {
try {
Expand All @@ -362,10 +366,10 @@ module.exports = {
},

/**
* @param data {CoreData}
* @param logger {Logger}
* @param callback {PluginCallback}
* @param app {App}
* @param {CoreData} data
* @param {Logger} logger
* @param {PluginCallback} callback
* @param {App} app
* */
isDropInStatements(data, logger, callback, app) {
try {
Expand Down
23 changes: 17 additions & 6 deletions forward_engineering/helpers/feScriptBuilder.js
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,10 @@ const buildEntityLevelFEScript =
const relationshipsWithThisTableAsChild = modelData[1]?.relationships.filter(
relationship => relationship.childCollection === entityId,
);
relationshipScripts = getCreateRelationshipScripts(app)(relationshipsWithThisTableAsChild, jsonSchema);
relationshipScripts = getCreateRelationshipScripts(app)({
relationships: relationshipsWithThisTableAsChild,
jsonSchemas: jsonSchema,
});
}

return buildScript([
Expand Down Expand Up @@ -198,6 +201,7 @@ const getContainerLevelEntitiesScriptDtos =
areNotNullConstraintsAvailable,
includeRelationshipsInEntityScripts,
includeSamplesInEntityScripts,
relatedSchemas,
}) => {
const _ = app.require('lodash');
const scriptDtos = [];
Expand Down Expand Up @@ -226,10 +230,11 @@ const getContainerLevelEntitiesScriptDtos =
const relationshipsWithThisTableAsChild = data.relationships.filter(
relationship => relationship.childCollection === entityId,
);
relationshipScripts = getCreateRelationshipScripts(app)(
relationshipsWithThisTableAsChild,
entitiesJsonSchema,
);
relationshipScripts = getCreateRelationshipScripts(app)({
relationships: relationshipsWithThisTableAsChild,
jsonSchemas: entitiesJsonSchema,
relatedSchemas,
});
}

const sampleScript = await getSampleScriptForContainerLevelScript(_)({
Expand Down Expand Up @@ -283,6 +288,7 @@ const buildContainerLevelFEScriptDto =
containerData,
includeRelationshipsInEntityScripts,
includeSamplesInEntityScripts,
relatedSchemas,
}) => {
const _ = app.require('lodash');
const dbVersion = data.modelData[0].dbVersion;
Expand All @@ -305,11 +311,16 @@ const buildContainerLevelFEScriptDto =
areNotNullConstraintsAvailable,
includeRelationshipsInEntityScripts,
includeSamplesInEntityScripts,
relatedSchemas,
});

let relationshipScrips = [];
if (!includeRelationshipsInEntityScripts && arePkFkConstraintsAvailable) {
relationshipScrips = getCreateRelationshipScripts(app)(data.relationships, entitiesJsonSchema);
relationshipScrips = getCreateRelationshipScripts(app)({
relationships: data.relationships,
jsonSchemas: entitiesJsonSchema,
relatedSchemas,
});
}

return {
Expand Down
102 changes: 58 additions & 44 deletions forward_engineering/helpers/relationshipHelper.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ const getCollectionPropertyNamesByIds = _ => (collection, propertiesIds) => {
};

/**
* @param relationship {Object}
* @param {Object} relationship
* @return {Array<string>}
**/
const getChildFieldIds = relationship => {
Expand All @@ -28,7 +28,7 @@ const getChildFieldIds = relationship => {
};

/**
* @param relationship {Object}
* @param {Object} relationship
* @return {Array<string>}
**/
const getParentFieldIds = relationship => {
Expand All @@ -38,54 +38,68 @@ const getParentFieldIds = relationship => {
};

/**
* @return {(relationship: Object, entitiesJsonSchema: Object) => string}
**/
const createSingleRelationship = (_, ddlProvider) => (relationship, entitiesJsonSchema) => {
const parentTable = entitiesJsonSchema[relationship.parentCollection];
const childTable = entitiesJsonSchema[relationship.childCollection];
const childBucketName = prepareName(childTable?.bucketName);
const parentBucketName = prepareName(parentTable?.bucketName);
* @returns {({ relationship: Object, jsonSchemas: Record<string, Object>, relatedSchemas?: Record<string, Object> }) => string}
*/
const createSingleRelationship =
(_, ddlProvider) =>
({ relationship, jsonSchemas, relatedSchemas }) => {
const parentTable =
jsonSchemas[relationship.parentCollection] ?? relatedSchemas?.[relationship.parentCollection];
const childTable = jsonSchemas[relationship.childCollection];
const childBucketName = prepareName(childTable?.bucketName);
const parentBucketName = prepareName(parentTable?.bucketName);

if (!parentTable || !childTable) {
return '';
}
const childFieldIds = getChildFieldIds(relationship);
const parentFieldIds = getParentFieldIds(relationship);
if (!parentTable || !childTable) {
return '';
}
const childFieldIds = getChildFieldIds(relationship);
const parentFieldIds = getParentFieldIds(relationship);

const parentColumnNames = getCollectionPropertyNamesByIds(_)(parentTable, parentFieldIds);
const childColumnNames = getCollectionPropertyNamesByIds(_)(childTable, childFieldIds);
if (!parentColumnNames?.length || !childColumnNames?.length) {
return '';
}
const parentColumnNames = getCollectionPropertyNamesByIds(_)(parentTable, parentFieldIds);
const childColumnNames = getCollectionPropertyNamesByIds(_)(childTable, childFieldIds);
if (!parentColumnNames?.length || !childColumnNames?.length) {
return '';
}

const childBucketNameForDDL = replaceSpaceWithUnderscore(childBucketName);
const childTableNameForDDL = prepareName(replaceSpaceWithUnderscore(getName(childTable)));
const parentBucketNameForDDL = replaceSpaceWithUnderscore(parentBucketName);
const parentTableNameForDDL = prepareName(replaceSpaceWithUnderscore(getName(parentTable)));
const childBucketNameForDDL = replaceSpaceWithUnderscore(childBucketName);
const childTableNameForDDL = prepareName(replaceSpaceWithUnderscore(getName(childTable)));
const parentBucketNameForDDL = replaceSpaceWithUnderscore(parentBucketName);
const parentTableNameForDDL = prepareName(replaceSpaceWithUnderscore(getName(parentTable)));

const addFkScript = ddlProvider.addFkConstraint({
childTableName: getFullEntityName(childBucketNameForDDL, childTableNameForDDL),
childColumns: childColumnNames.map(name => prepareName(name)),
fkConstraintName: wrapInTicks(getRelationshipName(relationship)),
parentColumns: parentColumnNames.map(name => prepareName(name)),
parentTableName: getFullEntityName(parentBucketNameForDDL, parentTableNameForDDL),
});
if (relationship.isActivated === false) {
return commentDeactivatedStatements(addFkScript, false);
}
return addFkScript;
};
const addFkScript = ddlProvider.addFkConstraint({
childTableName: getFullEntityName(childBucketNameForDDL, childTableNameForDDL),
childColumns: childColumnNames.map(name => prepareName(name)),
fkConstraintName: wrapInTicks(getRelationshipName(relationship)),
parentColumns: parentColumnNames.map(name => prepareName(name)),
parentTableName: getFullEntityName(parentBucketNameForDDL, parentTableNameForDDL),
});
if (relationship.isActivated === false) {
return commentDeactivatedStatements(addFkScript, false);
}
return addFkScript;
};

/**
* @return {(relationships: Array<Object>, entitiesJsonSchema: Object) => Array<string>}
**/
const getCreateRelationshipScripts = app => (relationships, entitiesJsonSchema) => {
const _ = app.require('lodash');
const ddlProvider = require('../ddlProvider/ddlProvider')(app);
return relationships
.map(relationship => createSingleRelationship(_, ddlProvider)(relationship, entitiesJsonSchema))
.filter(Boolean);
};
* @returns {({ relationships: Object[], jsonSchemas: Record<string, Object>, relatedSchemas?: Record<string, Object> }) => Array<string>}
*/
const getCreateRelationshipScripts =
app =>
({ relationships, jsonSchemas, relatedSchemas }) => {
const _ = app.require('lodash');
const ddlProvider = require('../ddlProvider/ddlProvider')(app);
return relationships
.map(relationship =>
createSingleRelationship(
_,
ddlProvider,
)({
relationship,
jsonSchemas,
relatedSchemas,
}),
)
.filter(Boolean);
};

module.exports = {
getCreateRelationshipScripts,
Expand Down

0 comments on commit 0816cd4

Please sign in to comment.