feat(filter): add isExcluded helper with unit tests

Glob-based entity_id matcher used by the upcoming exclude-filter feature.
Single wildcard `*` (matches any sequence including dots), all other characters
matched literally with regex metacharacters escaped. Case-sensitive, anchored.

Empty pattern array always returns false, so the helper is a no-op when the
adapter is not configured to filter anything.

New mocha unit-test suite invoked via `npm run test:unit` (separate from the
existing js-controller-backed test:integration).
This commit is contained in:
mokusone
2026-05-14 11:40:28 +02:00
parent 1f0e93d357
commit 9b95ece284
3 changed files with 73 additions and 0 deletions
+47
View File
@@ -0,0 +1,47 @@
const { expect } = require('chai');
const { isExcluded } = require('../build/lib/entityFilter');
describe('entityFilter.isExcluded', () => {
it('returns false for an empty pattern list', () => {
expect(isExcluded('switch.iob_anything', [])).to.equal(false);
});
it('matches a simple glob with leading wildcard', () => {
expect(isExcluded('switch.iob_shelly_xyz', ['*.iob_*'])).to.equal(true);
});
it('matches the bridge mirror naming pattern', () => {
expect(isExcluded('light.iob_ha_eg_wz1__e_licht_decke', ['*.iob_*__*'])).to.equal(true);
});
it('handles entities that miss a required literal segment', () => {
// *.iob_*__* requires the literal `__` segment — entities without it do not match
expect(isExcluded('switch.iob_', ['*.iob_*__*'])).to.equal(false);
expect(isExcluded('switch.iob_foo', ['*.iob_*__*'])).to.equal(false);
// Naming-Convention safety: similarly named entities without `__` are safe
expect(isExcluded('sensor.scheune_temperatur', ['*.sc_*__*'])).to.equal(false);
});
it('matches multiple patterns (OR semantic)', () => {
const patterns = ['*.iob_*__*', '*.knx_*', '*.ha_*__*'];
expect(isExcluded('switch.knx_foo', patterns)).to.equal(true);
expect(isExcluded('switch.ha_eg_wz1__e_licht_decke', patterns)).to.equal(true);
expect(isExcluded('switch.something_else', patterns)).to.equal(false);
});
it('is case sensitive', () => {
expect(isExcluded('switch.IOB_foo', ['*.iob_*'])).to.equal(false);
expect(isExcluded('switch.iob_foo', ['*.IOB_*'])).to.equal(false);
});
it('treats * as matching any characters including dots', () => {
// We use full entity_id including the leading domain, so this is fine.
expect(isExcluded('switch.iob_foo', ['*foo*'])).to.equal(true);
});
it('escapes regex metacharacters in patterns', () => {
// `.` in pattern matches literal `.`, not "any char"
expect(isExcluded('switch.iob_foo', ['switch.iob_foo'])).to.equal(true);
expect(isExcluded('switchXiob_foo', ['switch.iob_foo'])).to.equal(false);
});
});