mirror of
https://github.com/hanzoai/sentinel.git
synced 2026-09-29 22:34:33 +00:00
270 lines
7.1 KiB
TypeScript
270 lines
7.1 KiB
TypeScript
import {ProjectFixture} from 'sentry-fixture/project';
|
|
|
|
import {
|
|
deepFreeze,
|
|
descopeFeatureName,
|
|
escapeDoubleQuotes,
|
|
explodeSlug,
|
|
extractMultilineFields,
|
|
parseRepo,
|
|
sortProjects,
|
|
valueIsEqual,
|
|
} from 'sentry/utils';
|
|
|
|
describe('utils.valueIsEqual', function () {
|
|
it('should return true when objects are deeply equal', function () {
|
|
const isEqual = valueIsEqual(
|
|
{
|
|
username: 'foo',
|
|
teams: ['bar', 'baz'],
|
|
avatar: {
|
|
avatarType: 'gravatar',
|
|
avatarUuid: null,
|
|
},
|
|
},
|
|
{
|
|
username: 'foo',
|
|
teams: ['bar', 'baz'],
|
|
avatar: {
|
|
avatarType: 'gravatar',
|
|
avatarUuid: null,
|
|
},
|
|
},
|
|
true
|
|
);
|
|
expect(isEqual).toBe(true);
|
|
});
|
|
|
|
it('should return false when objects are not deeply equal', function () {
|
|
const isEqual = valueIsEqual(
|
|
{
|
|
username: 'foo',
|
|
teams: ['bar', 'baz'],
|
|
avatar: {
|
|
avatarType: 'gravatar',
|
|
avatarUuid: null,
|
|
},
|
|
},
|
|
{
|
|
username: 'foo',
|
|
teams: ['bar', 'baz'],
|
|
avatar: {
|
|
avatarType: 'notGravatar',
|
|
avatarUuid: null,
|
|
},
|
|
},
|
|
true
|
|
);
|
|
expect(isEqual).toBe(false);
|
|
});
|
|
|
|
it('should return true when objects are shallowly equal', function () {
|
|
const isEqual = valueIsEqual(
|
|
{
|
|
username: 'foo',
|
|
team: 'bar',
|
|
avatar: 'gravatar',
|
|
},
|
|
{
|
|
username: 'foo',
|
|
team: 'bar',
|
|
avatar: 'gravatar',
|
|
},
|
|
false
|
|
);
|
|
expect(isEqual).toBe(true);
|
|
});
|
|
|
|
it('should return false when objects are not shallowly equal', function () {
|
|
const isEqual = valueIsEqual(
|
|
{
|
|
username: 'foo',
|
|
team: 'bar',
|
|
avatar: 'gravatar',
|
|
},
|
|
{
|
|
username: 'foo',
|
|
team: 'bar',
|
|
avatar: 'notGravatar',
|
|
},
|
|
false
|
|
);
|
|
expect(isEqual).toBe(false);
|
|
});
|
|
|
|
it('should not blow up when comparing null value to an object', function () {
|
|
let isEqual = valueIsEqual(null, {username: 'foo'}, true);
|
|
expect(isEqual).toBe(false);
|
|
|
|
isEqual = valueIsEqual(
|
|
{
|
|
username: 'foo',
|
|
teams: ['bar', 'baz'],
|
|
avatar: null,
|
|
},
|
|
{
|
|
username: 'foo',
|
|
teams: ['bar', 'baz'],
|
|
avatar: {
|
|
avatarType: 'notGravatar',
|
|
avatarUuid: null,
|
|
},
|
|
},
|
|
true
|
|
);
|
|
expect(isEqual).toBe(false);
|
|
});
|
|
});
|
|
|
|
describe('utils.extractMultilineFields', function () {
|
|
it('should work for basic, simple values', function () {
|
|
expect(extractMultilineFields('one\ntwo\nthree')).toEqual(['one', 'two', 'three']);
|
|
});
|
|
|
|
it('should return an empty array if only whitespace', function () {
|
|
expect(extractMultilineFields(' \n \n\n\n \n')).toEqual([]);
|
|
});
|
|
|
|
it('should trim values and ignore empty lines', function () {
|
|
expect(
|
|
extractMultilineFields(
|
|
`one
|
|
two
|
|
|
|
three
|
|
four
|
|
|
|
five`
|
|
)
|
|
).toEqual(['one', 'two', 'three', 'four', 'five']);
|
|
});
|
|
});
|
|
|
|
describe('utils.parseRepo', function () {
|
|
it('should work for simple github url', function () {
|
|
expect(parseRepo('github.com/example/example')).toEqual('example/example');
|
|
});
|
|
it('should work for full github url', function () {
|
|
expect(parseRepo('https://github.com/example/example')).toEqual('example/example');
|
|
});
|
|
it('should work for trailing slash', function () {
|
|
expect(parseRepo('https://github.com/example/example/')).toEqual('example/example');
|
|
});
|
|
it('should work for simple BitBucket url', function () {
|
|
expect(parseRepo('bitbucket.org/example/example')).toEqual('example/example');
|
|
});
|
|
it('should work for full BitBucket url', function () {
|
|
expect(parseRepo('https://bitbucket.org/example/example')).toEqual('example/example');
|
|
});
|
|
it('should work for trailing Bitbucket slash', function () {
|
|
expect(parseRepo('https://bitbucket.org/example/example/')).toEqual(
|
|
'example/example'
|
|
);
|
|
});
|
|
it('should work for repo only', function () {
|
|
expect(parseRepo('example/example')).toEqual('example/example');
|
|
});
|
|
it('should parse repo from url with extra info', function () {
|
|
expect(parseRepo('github.com/example/example/commits/adsadsa')).toEqual(
|
|
'example/example'
|
|
);
|
|
});
|
|
});
|
|
|
|
describe('utils.explodeSlug', function () {
|
|
it('replaces slug special chars with whitespace', function () {
|
|
expect(explodeSlug('test--slug__replace-')).toEqual('test slug replace');
|
|
});
|
|
});
|
|
|
|
describe('utils.projectDisplayCompare', function () {
|
|
it('sorts by bookmark and project slug', function () {
|
|
const projects = [
|
|
ProjectFixture({isBookmarked: true, slug: 'm'}),
|
|
ProjectFixture({isBookmarked: false, slug: 'm'}),
|
|
ProjectFixture({isBookmarked: false, slug: 'a'}),
|
|
ProjectFixture({isBookmarked: true, slug: 'a'}),
|
|
ProjectFixture({isBookmarked: true, slug: 'z'}),
|
|
ProjectFixture({isBookmarked: false, slug: 'z'}),
|
|
];
|
|
|
|
const expected = [
|
|
expect.objectContaining({isBookmarked: true, slug: 'a'}),
|
|
expect.objectContaining({isBookmarked: true, slug: 'm'}),
|
|
expect.objectContaining({isBookmarked: true, slug: 'z'}),
|
|
expect.objectContaining({isBookmarked: false, slug: 'a'}),
|
|
expect.objectContaining({isBookmarked: false, slug: 'm'}),
|
|
expect.objectContaining({isBookmarked: false, slug: 'z'}),
|
|
];
|
|
|
|
const sortedProjects = sortProjects(projects);
|
|
|
|
expect(sortedProjects).toEqual(expected);
|
|
});
|
|
});
|
|
|
|
describe('utils.descopeFeatureName', function () {
|
|
it('descopes the feature name', () => {
|
|
[
|
|
['organizations:feature', 'feature'],
|
|
['projects:feature', 'feature'],
|
|
['unknown-scope:feature', 'unknown-scope:feature'],
|
|
['', ''],
|
|
].forEach(([input, expected]) => expect(descopeFeatureName(input)).toEqual(expected));
|
|
});
|
|
});
|
|
|
|
describe('deepFreeze', function () {
|
|
it('throws error on attempt to mutate frozen object', function () {
|
|
const testObj = deepFreeze({foo: [1, 2, 3]});
|
|
|
|
[
|
|
() => {
|
|
testObj.foo.push(4);
|
|
},
|
|
() => {
|
|
// @ts-expect-error
|
|
testObj.bar = '';
|
|
},
|
|
() => {
|
|
// @ts-expect-error
|
|
delete testObj.foo;
|
|
},
|
|
].forEach(fn => {
|
|
expect(fn).toThrow();
|
|
});
|
|
});
|
|
});
|
|
|
|
describe('utils.escapeDoubleQuotes', function () {
|
|
// test cases from https://gist.github.com/getify/3667624
|
|
|
|
it('should escape any unescaped double quotes', function () {
|
|
const cases = [
|
|
['a"b', 'a\\"b'], //
|
|
['a\\"b', 'a\\"b'], //
|
|
['a\\\\"b', 'a\\\\\\"b'],
|
|
['a"b"c', 'a\\"b\\"c'],
|
|
['a""b', 'a\\"\\"b'],
|
|
['""', '\\"\\"'],
|
|
];
|
|
|
|
for (const testCase of cases) {
|
|
const [input, expected] = testCase;
|
|
expect(escapeDoubleQuotes(input)).toBe(expected);
|
|
}
|
|
|
|
// should return the same input as the output
|
|
|
|
const cases2 = ['ab', 'a\\"b', 'a\\\\\\"b'];
|
|
|
|
for (const test of cases2) {
|
|
expect(escapeDoubleQuotes(test)).toBe(test);
|
|
}
|
|
|
|
// don't unnecessarily escape
|
|
const actual = escapeDoubleQuotes(escapeDoubleQuotes(escapeDoubleQuotes('a"b')));
|
|
expect(actual).toBe('a\\"b');
|
|
});
|
|
});
|