diff --git a/content.js b/content.js index ff44d06..051d711 100644 --- a/content.js +++ b/content.js @@ -2209,8 +2209,10 @@ class YTMBlockController { * Sanitizes and normalizes artist name values. */ normalizeArtist(name) { - if (!name) return ''; - return name.trim().toLowerCase(); + if (!name || typeof name !== 'string') return ''; + return name.trim().toLowerCase() + .replace(/\s+/g, ' ') + .replace(/[^\w\s-]/gi, ''); } // --- CORE PLAYER EXTRACTION METHODS --- @@ -2795,5 +2797,11 @@ class YTMBlockController { } // Instantiate and initialize the controller -const ytmBlockController = new YTMBlockController(); -ytmBlockController.init(); +if (typeof window !== 'undefined') { + const ytmBlockController = new YTMBlockController(); + ytmBlockController.init(); +} + +if (typeof module !== 'undefined' && module.exports) { + module.exports = { YTMBlockController }; +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..25cc70a --- /dev/null +++ b/package.json @@ -0,0 +1,10 @@ +{ + "name": "ytm-block", + "version": "1.2.0", + "description": "YouTube Music track, artist, and album blocking extension", + "scripts": { + "test": "node --test" + }, + "private": true, + "license": "MIT" +} diff --git a/tests/normalizeArtist.test.js b/tests/normalizeArtist.test.js new file mode 100644 index 0000000..f69974c --- /dev/null +++ b/tests/normalizeArtist.test.js @@ -0,0 +1,40 @@ +const test = require('node:test'); +const assert = require('node:assert'); + +// Require YTMBlockController from content.js +const { YTMBlockController } = require('../content.js'); + +test('YTMBlockController - normalizeArtist', async (t) => { + const controller = new YTMBlockController(); + + await t.test('handles empty, null, and undefined values', () => { + assert.strictEqual(controller.normalizeArtist(null), ''); + assert.strictEqual(controller.normalizeArtist(undefined), ''); + assert.strictEqual(controller.normalizeArtist(''), ''); + }); + + await t.test('normalizes standard artist names (lowercasing and whitespace trimming)', () => { + assert.strictEqual(controller.normalizeArtist('Dua Lipa'), 'dua lipa'); + assert.strictEqual(controller.normalizeArtist(' Coldplay '), 'coldplay'); + assert.strictEqual(controller.normalizeArtist('THE WEEKND'), 'the weeknd'); + }); + + await t.test('collapses multiple internal whitespaces', () => { + assert.strictEqual(controller.normalizeArtist('Taylor Swift'), 'taylor swift'); + assert.strictEqual(controller.normalizeArtist(' Kendrick \t Lamar \n '), 'kendrick lamar'); + }); + + await t.test('removes special characters except hyphens and spaces', () => { + assert.strictEqual(controller.normalizeArtist('P!nk'), 'pnk'); + assert.strictEqual(controller.normalizeArtist('Ke$ha'), 'keha'); + assert.strictEqual(controller.normalizeArtist('AC/DC'), 'acdc'); + assert.strictEqual(controller.normalizeArtist('Jay-Z'), 'jay-z'); + assert.strictEqual(controller.normalizeArtist('Panic! At The Disco'), 'panic at the disco'); + }); + + await t.test('handles non-string values gracefully', () => { + assert.strictEqual(controller.normalizeArtist(123), ''); + assert.strictEqual(controller.normalizeArtist({}), ''); + assert.strictEqual(controller.normalizeArtist([]), ''); + }); +});