190 lines
		
	
	
		
			5.9 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
			
		
		
	
	
			190 lines
		
	
	
		
			5.9 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
import { FirebaseGlob } from './FirebaseGlob';
 | 
						|
describe('FirebaseGlob', () => {
 | 
						|
 | 
						|
  describe('test', () => {
 | 
						|
    it('should match * parts', () => {
 | 
						|
      testGlob('asdf/*.jpg',
 | 
						|
        ['asdf/.jpg', 'asdf/asdf.jpg', 'asdf/asdf_asdf.jpg'],
 | 
						|
        ['asdf/asdf/asdf.jpg', 'xxxasdf/asdf.jpgxxx']);
 | 
						|
    });
 | 
						|
 | 
						|
    it('should match ** parts', () => {
 | 
						|
      testGlob('asdf/**.jpg', // treated like two consecutive single `*`s
 | 
						|
        ['asdf/.jpg', 'asdf/asdf.jpg', 'asdf/asdf_asdf.jpg'],
 | 
						|
        ['asdf/a/.jpg', 'asdf/a/b.jpg', '/asdf/asdf.jpg', 'asdff/asdf.jpg', 'xxxasdf/asdf.jpg', 'asdf/asdf.jpgxxx']);
 | 
						|
    });
 | 
						|
 | 
						|
    it('should match **/ and /**/', () => {
 | 
						|
      testGlob('**/*.js',
 | 
						|
        ['asdf.js', 'asdf/asdf.js', 'asdf/asdf/asdfasdf_asdf.js', '/asdf/asdf.js', '/asdf/aasdf-asdf.2.1.4.js'],
 | 
						|
        ['asdf/asdf.jpg', '/asdf/asdf.jpg']);
 | 
						|
      testGlob('aaa/**/bbb',
 | 
						|
        ['aaa/xxx/bbb', 'aaa/xxx/yyy/bbb', 'aaa/bbb'],
 | 
						|
        ['/aaa/xxx/bbb', 'aaa/x/bbb/', 'aaa/bbb/ccc']);
 | 
						|
    });
 | 
						|
 | 
						|
    it('should match choice groups', () => {
 | 
						|
      testGlob('aaa/*.@(bbb|ccc)',
 | 
						|
        ['aaa/aaa.bbb', 'aaa/aaa_aaa.ccc'],
 | 
						|
        ['/aaa/aaa.bbb', 'aaaf/aaa.bbb', 'aaa/aaa.ddd']);
 | 
						|
 | 
						|
      testGlob('aaa/*(bbb|ccc)',
 | 
						|
        ['aaa/', 'aaa/bbb', 'aaa/ccc', 'aaa/bbbbbb', 'aaa/bbbccc', 'aaa/cccbbb', 'aaa/bbbcccbbb'],
 | 
						|
        ['aaa/aaa', 'aaa/bbbb']);
 | 
						|
 | 
						|
      testGlob('aaa/+(bbb|ccc)',
 | 
						|
        ['aaa/bbb', 'aaa/ccc', 'aaa/bbbbbb', 'aaa/bbbccc', 'aaa/cccbbb', 'aaa/bbbcccbbb'],
 | 
						|
        ['aaa/', 'aaa/aaa', 'aaa/bbbb']);
 | 
						|
 | 
						|
      testGlob('aaa/?(bbb|ccc)',
 | 
						|
        ['aaa/', 'aaa/bbb', 'aaa/ccc'],
 | 
						|
        ['aaa/aaa', 'aaa/bbbb', 'aaa/bbbbbb', 'aaa/bbbccc', 'aaa/cccbbb', 'aaa/bbbcccbbb']);
 | 
						|
    });
 | 
						|
 | 
						|
    it('should error on non-supported choice groups', () => {
 | 
						|
      expect(() => new FirebaseGlob('/!(a|b)/c'))
 | 
						|
        .toThrowError('Error in FirebaseGlob: "/!(a|b)/c" - "not" expansions are not supported: "!(a|b)"');
 | 
						|
      expect(() => new FirebaseGlob('/(a|b)/c'))
 | 
						|
      .toThrowError('Error in FirebaseGlob: "/(a|b)/c" - unknown expansion type: "/" in "/(a|b)"');
 | 
						|
      expect(() => new FirebaseGlob('/&(a|b)/c'))
 | 
						|
        .toThrowError('Error in FirebaseGlob: "/&(a|b)/c" - unknown expansion type: "&" in "&(a|b)"');
 | 
						|
    });
 | 
						|
 | 
						|
    // Globs that contain params tested via the match tests below
 | 
						|
  });
 | 
						|
 | 
						|
  describe('match', () => {
 | 
						|
    it('should match patterns with no parameters', () => {
 | 
						|
      testMatch('/abc/def/*', {
 | 
						|
      }, {
 | 
						|
        '/abc/def/': {},
 | 
						|
        '/abc/def/ghi': {},
 | 
						|
        '/': undefined,
 | 
						|
        '/abc': undefined,
 | 
						|
        '/abc/def/ghi/jk;': undefined,
 | 
						|
      });
 | 
						|
    });
 | 
						|
 | 
						|
    it('should capture a simple named param', () => {
 | 
						|
      testMatch('/:abc', {
 | 
						|
        named: ['abc']
 | 
						|
      }, {
 | 
						|
        '/a': {abc: 'a'},
 | 
						|
        '/abc': {abc: 'abc'},
 | 
						|
        '/': undefined,
 | 
						|
        '/a/': undefined,
 | 
						|
        '/a/b/': undefined,
 | 
						|
        '/a/a/b': undefined,
 | 
						|
        '/a/a/b/': undefined,
 | 
						|
      });
 | 
						|
      testMatch('/a/:b', {
 | 
						|
        named: ['b']
 | 
						|
      }, {
 | 
						|
        '/a/b': {b: 'b'},
 | 
						|
        '/a/bcd': {b: 'bcd'},
 | 
						|
        '/a/': undefined,
 | 
						|
        '/a/b/': undefined,
 | 
						|
        '/a': undefined,
 | 
						|
        '/a//': undefined,
 | 
						|
        '/a/a/b': undefined,
 | 
						|
        '/a/a/b/': undefined,
 | 
						|
      });
 | 
						|
    });
 | 
						|
 | 
						|
    it('should capture a named param followed by non-word chars', () => {
 | 
						|
      testMatch('/a/:x-', {
 | 
						|
        named: ['x']
 | 
						|
      }, {
 | 
						|
        '/a/b-': {x: 'b'},
 | 
						|
        '/a/bcd-': {x: 'bcd'},
 | 
						|
        '/a/--': {x: '-'},
 | 
						|
        '/a': undefined,
 | 
						|
        '/a/-': undefined,
 | 
						|
        '/a/-/': undefined,
 | 
						|
        '/a/': undefined,
 | 
						|
        '/a/b/-': undefined,
 | 
						|
        '/a/b-c': undefined,
 | 
						|
      });
 | 
						|
    });
 | 
						|
 | 
						|
    it('should capture multiple named params', () => {
 | 
						|
      testMatch('/a/:b/:c', {
 | 
						|
        named: ['b', 'c']
 | 
						|
      }, {
 | 
						|
        '/a/b/c': {b: 'b', c: 'c'},
 | 
						|
        '/a/bcd/efg': {b: 'bcd', c: 'efg'},
 | 
						|
        '/a/b/c-': {b: 'b', c: 'c-'},
 | 
						|
        '/a/': undefined,
 | 
						|
        '/a/b/': undefined,
 | 
						|
        '/a/b/c/': undefined,
 | 
						|
      });
 | 
						|
      testMatch('/:a/b/:c', {
 | 
						|
        named: ['a', 'c']
 | 
						|
      }, {
 | 
						|
        '/a/b/c': {a: 'a', c: 'c'},
 | 
						|
        '/abc/b/efg': {a: 'abc', c: 'efg'},
 | 
						|
        '/a/b/c-': {a: 'a', c: 'c-'},
 | 
						|
        '/a/': undefined,
 | 
						|
        '/a/b/': undefined,
 | 
						|
        '/a/b/c/': undefined,
 | 
						|
      });
 | 
						|
    });
 | 
						|
 | 
						|
    it('should capture a simple rest param', () => {
 | 
						|
      testMatch('/:abc*', {
 | 
						|
        rest: ['abc']
 | 
						|
      }, {
 | 
						|
        '/a': {abc: 'a'},
 | 
						|
        '/a/b': {abc: 'a/b'},
 | 
						|
        '/a/bcd': {abc: 'a/bcd'},
 | 
						|
        '/a/': {abc: 'a/'},
 | 
						|
        '/a/b/': {abc: 'a/b/'},
 | 
						|
        '/a//': {abc: 'a//'},
 | 
						|
        '/a/b/c': {abc: 'a/b/c'},
 | 
						|
        '/a/b/c/': {abc: 'a/b/c/'},
 | 
						|
      });
 | 
						|
      testMatch('/a/:b*', {
 | 
						|
        rest: ['b']
 | 
						|
      }, {
 | 
						|
        '/a/b': {b: 'b'},
 | 
						|
        '/a/bcd': {b: 'bcd'},
 | 
						|
        '/a/': {b: ''},
 | 
						|
        '/a/b/': {b: 'b/'},
 | 
						|
        '/a': {b: undefined},
 | 
						|
        '/a//': {b: '/'},
 | 
						|
        '/a/a/b': {b: 'a/b'},
 | 
						|
        '/a/a/b/': {b: 'a/b/'},
 | 
						|
      });
 | 
						|
    });
 | 
						|
 | 
						|
    it('should capture a rest param mixed with a named param', () => {
 | 
						|
      testMatch('/:abc/:rest*', {
 | 
						|
        named: ['abc'],
 | 
						|
        rest: ['rest']
 | 
						|
      }, {
 | 
						|
        '/a': {abc: 'a', rest: undefined},
 | 
						|
        '/a/b': {abc: 'a', rest: 'b'},
 | 
						|
        '/a/bcd': {abc: 'a', rest: 'bcd'},
 | 
						|
        '/a/': {abc: 'a', rest: ''},
 | 
						|
        '/a/b/': {abc: 'a', rest: 'b/'},
 | 
						|
        '/a//': {abc: 'a', rest: '/'},
 | 
						|
        '/a/b/c': {abc: 'a', rest: 'b/c'},
 | 
						|
        '/a/b/c/': {abc: 'a', rest: 'b/c/'},
 | 
						|
      });
 | 
						|
    });
 | 
						|
  });
 | 
						|
});
 | 
						|
 | 
						|
function testGlob(pattern: string, matches: string[], nonMatches: string[]) {
 | 
						|
  const glob = new FirebaseGlob(pattern);
 | 
						|
  matches.forEach(url => expect(glob.test(url)).toBe(true, url));
 | 
						|
  nonMatches.forEach(url => expect(glob.test(url)).toBe(false, url));
 | 
						|
}
 | 
						|
 | 
						|
function testMatch(pattern: string, captures: { named?: string[], rest?: string[] }, matches: { [url: string]: object|undefined }) {
 | 
						|
  const glob = new FirebaseGlob(pattern);
 | 
						|
  expect(Object.keys(glob.namedParams)).toEqual(captures.named || []);
 | 
						|
  expect(Object.keys(glob.restParams)).toEqual(captures.rest || []);
 | 
						|
  Object.keys(matches).forEach(url => expect(glob.match(url)).toEqual(matches[url]));
 | 
						|
}
 |