traxxx/src/tags.js

88 lines
2.3 KiB
JavaScript
Raw Normal View History

'use strict';
const knex = require('./knex');
const slugify = require('./utils/slugify');
const bulkInsert = require('./utils/bulk-insert');
async function matchReleaseTags(releases) {
const rawTags = releases
.map(release => release.tags).flat()
.filter(Boolean);
const casedTags = [...new Set(
rawTags
.concat(rawTags.map(tag => tag.toLowerCase()))
.concat(rawTags.map(tag => tag.toUpperCase())),
)];
const tagEntries = await knex('tags')
.select('tags.id', 'tags.name', 'tags.alias_for')
.whereIn('tags.name', casedTags);
const tagIdsBySlug = tagEntries
.reduce((acc, tag) => ({
...acc,
[slugify(tag.name)]: tag.alias_for || tag.id,
}), {});
return tagIdsBySlug;
}
async function getEntityTags(releases) {
const entityIds = releases.map(release => release.entity?.id).filter(Boolean);
const entityTags = await knex('entities_tags').whereIn('entity_id', entityIds);
const entityTagIdsByEntityId = entityTags.reduce((acc, entityTag) => {
if (!acc[entityTag.entity_id]) {
acc[entityTag.entity_id] = [];
}
acc[entityTag.entity_id].push(entityTag.tag_id);
return acc;
}, {});
return entityTagIdsByEntityId;
}
function buildReleaseTagAssociations(releases, tagIdsBySlug, entityTagIdsByEntityId, type) {
const tagAssociations = releases
.map((release) => {
const entityTagIds = entityTagIdsByEntityId[release.entity?.id] || [];
const releaseTags = release.tags || [];
const releaseTagIds = releaseTags.every(tag => typeof tag === 'number')
? releaseTags // obsolete scraper returned pre-matched tags
: releaseTags.map(tag => tagIdsBySlug[slugify(tag)]);
const tags = [...new Set(
// filter duplicates and empties
releaseTagIds
.concat(entityTagIds)
.filter(Boolean),
)]
.map(tagId => ({
[`${type}_id`]: release.id,
tag_id: tagId,
}));
return tags;
})
.flat();
return tagAssociations;
}
2020-01-13 22:45:09 +00:00
async function associateReleaseTags(releases, type = 'release') {
const tagIdsBySlug = await matchReleaseTags(releases);
const EntityTagIdsByEntityId = await getEntityTags(releases);
const tagAssociations = buildReleaseTagAssociations(releases, tagIdsBySlug, EntityTagIdsByEntityId, type);
await bulkInsert(`${type}s_tags`, tagAssociations, false);
}
module.exports = {
associateReleaseTags,
};