Skip to content

Commit

Permalink
feat: support custom separator on set
Browse files Browse the repository at this point in the history
  • Loading branch information
mdvorak committed Apr 15, 2023
1 parent 164b627 commit e494d09
Show file tree
Hide file tree
Showing 2 changed files with 172 additions and 149 deletions.
315 changes: 168 additions & 147 deletions src/properties.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -102,168 +102,189 @@ describe('data access', () => {
['foo23', 'bar23']
]

it.each(samplePairs)('should get property "%s"', (key, expected) => {
const result = properties.get(sample, key)
expect(result).toBe(expected)
})

it.each([
['foo6'],
['foo7']
])('should not get commented property "%s"', (key) => {
const result = properties.get(sample, key)
expect(result).toBeUndefined()
})
describe('get value', () => {
it.each(samplePairs)('should get property "%s"', (key, expected) => {
const result = properties.get(sample, key)
expect(result).toBe(expected)
})

it.each([
['foo6'],
['foo7']
])('should not get commented property "%s"', (key) => {
const result = properties.get(sample, key)
expect(result).toBeUndefined()
})

it('should return last value of duplicate key', () => {
const config: properties.Properties = {
lines: [
'key1=foo1',
'key2=foo2',
'key1=foo3'
]
}

const result = properties.get(config, 'key1')
expect(result).toBe('foo3')
})
it('should return last value of duplicate key', () => {
const config: properties.Properties = {
lines: [
'key1=foo1',
'key2=foo2',
'key1=foo3'
]
}

it.each([
['foo1', 'bar', 'foo1=bar'],
['foo8:', 'bar8', 'foo8\\:=bar8'],
['foo9=', 'bar9', 'foo9\\==bar9'],
['foo10=', 'bar10', 'foo10\\==bar10'],
['foo11 ', 'bar11', 'foo11\\ =bar11'],
[' foo12', 'bar12 ', '\\ foo12=bar12 '],
['#foo13', 'bar13', '\\#foo13=bar13'],
['!foo14#', 'bar14', '\\!foo14\\#=bar14'],
['foo15', '#bar15', 'foo15=\\#bar15'],
['f o o18', ' bar18', 'f\\ o\\ \\ o18=\\ bar18'],
['foo19\n', 'bar\t\f\r19\n', 'foo19\\n=bar\\t\\f\\r19\\n'],
['foo20', '', 'foo20='],
['foo22', '\\', 'foo22=\\\\']
])('should format key pair for "%s"', (key, value, expected) => {
const config = properties.empty()
properties.set(config, key, value)
expect(config.lines).toEqual([expected])
const result = properties.get(config, 'key1')
expect(result).toBe('foo3')
})
})

it.each([
['foo=bar', 'a=b'],
['foo = bar', 'a = b'],
['foo:bar', 'a:b'],
['foo: bar', 'a: b'],
['foo bar', 'a b'],
['# comment', 'a=b']
])('should reuse last separator from "%s"', (line, expected) => {
const config: properties.Properties = {
lines: [line]
}
properties.set(config, 'a', 'b')
expect(config.lines).toEqual([line, expected])
})
describe('set value', () => {
it.each([
['foo1', 'bar', 'foo1=bar'],
['foo8:', 'bar8', 'foo8\\:=bar8'],
['foo9=', 'bar9', 'foo9\\==bar9'],
['foo10=', 'bar10', 'foo10\\==bar10'],
['foo11 ', 'bar11', 'foo11\\ =bar11'],
[' foo12', 'bar12 ', '\\ foo12=bar12 '],
['#foo13', 'bar13', '\\#foo13=bar13'],
['!foo14#', 'bar14', '\\!foo14\\#=bar14'],
['foo15', '#bar15', 'foo15=\\#bar15'],
['f o o18', ' bar18', 'f\\ o\\ \\ o18=\\ bar18'],
['foo19\n', 'bar\t\f\r19\n', 'foo19\\n=bar\\t\\f\\r19\\n'],
['foo20', '', 'foo20='],
['foo22', '\\', 'foo22=\\\\']
])('should format key pair for "%s"', (key, value, expected) => {
const config = properties.empty()
properties.set(config, key, value)
expect(config.lines).toEqual([expected])
})

it('should replace key pairs', () => {
const keys = [
'foo0',
'foo1',
'foo2',
'foo3',
'foo4',
'foo5',
'foo6',
'foo8:',
'foo9=',
'foo10=',
'foo11 ',
' foo12',
'#foo13',
'!foo14#',
'foo15',
'foo16',
'foo17',
'f o o18',
'foo19\n',
'foo20',
'foo21',
'foo22',
'foo23'
]
keys.forEach(key => properties.set(sample, key, 'x'))

expect(sample.lines).toEqual([
'foo0=x',
'foo1=x',
'foo2:x',
'foo3 x',
'foo4 x',
'foo5 = x',
'# foo6 = bar6',
' ! foo7 = bar7',
'foo8\\::x',
'foo9\\==x',
'foo10\\=:x',
'foo11\\ x',
'\\ foo12 = x',
'\\#foo13 = x',
'\\!foo14\\# = x',
'foo15 = x',
'foo16 = x',
'foo17 = x',
'f\\ o\\ \\ o18 =x',
'foo19\\n= x',
'foo20 = x',
'foo21 =x',
'foo22 =x',
'foo23 x',
'foo6 x'
])
})
it.each([
['foo=bar', 'a=b'],
['foo = bar', 'a = b'],
['foo:bar', 'a:b'],
['foo: bar', 'a: b'],
['foo bar', 'a b'],
['# comment', 'a=b']
])('should reuse last separator from "%s"', (line, expected) => {
const config: properties.Properties = {
lines: [line]
}
properties.set(config, 'a', 'b')
expect(config.lines).toEqual([line, expected])
})

it('should remove duplicate keys on set', () => {
const config: properties.Properties = {
lines: [
'key1=foo1',
'key2=foo2',
'key1=foo3'
it('should replace key pairs', () => {
const keys = [
'foo0',
'foo1',
'foo2',
'foo3',
'foo4',
'foo5',
'foo6',
'foo8:',
'foo9=',
'foo10=',
'foo11 ',
' foo12',
'#foo13',
'!foo14#',
'foo15',
'foo16',
'foo17',
'f o o18',
'foo19\n',
'foo20',
'foo21',
'foo22',
'foo23'
]
}
keys.forEach(key => properties.set(sample, key, 'x'))

expect(sample.lines).toEqual([
'foo0=x',
'foo1=x',
'foo2:x',
'foo3 x',
'foo4 x',
'foo5 = x',
'# foo6 = bar6',
' ! foo7 = bar7',
'foo8\\::x',
'foo9\\==x',
'foo10\\=:x',
'foo11\\ x',
'\\ foo12 = x',
'\\#foo13 = x',
'\\!foo14\\# = x',
'foo15 = x',
'foo16 = x',
'foo17 = x',
'f\\ o\\ \\ o18 =x',
'foo19\\n= x',
'foo20 = x',
'foo21 =x',
'foo22 =x',
'foo23 x',
'foo6 x'
])
})

properties.set(config, 'key1', 'test')
expect(config.lines).toEqual([
'key1=test',
'key2=foo2'
])
})
it('should use custom separator', () => {
const config: properties.Properties = {
lines: [
'key1=foo1',
'key2=foo2'
]
}

it('should remove existing key with set undefined', () => {
const config: properties.Properties = {
lines: ['foo=bar']
}
properties.set(config, 'foo', undefined)
expect(config.lines).toEqual([])
})
properties.set(config, 'key1', 'test', {separator: ': '})
expect(config.lines).toEqual([
'key1: test',
'key2=foo2'
])
})

it('should remove existing key with remove', () => {
const config: properties.Properties = {
lines: ['foo=bar']
}
properties.remove(config, 'foo')
expect(config.lines).toEqual([])
it('should remove duplicate keys on set', () => {
const config: properties.Properties = {
lines: [
'key1=foo1',
'key2=foo2',
'key1=foo3'
]
}

properties.set(config, 'key1', 'test')
expect(config.lines).toEqual([
'key1=test',
'key2=foo2'
])
})
})

it('should remove all duplicate keys with remove', () => {
const config: properties.Properties = {
lines: [
'key1=foo1',
'key2=foo2',
'key1=foo3'
]
}
describe('remove value', () => {
it('should remove existing key with set undefined', () => {
const config: properties.Properties = {
lines: ['foo=bar']
}
properties.set(config, 'foo', undefined)
expect(config.lines).toEqual([])
})

it('should remove existing key with remove', () => {
const config: properties.Properties = {
lines: ['foo=bar']
}
properties.remove(config, 'foo')
expect(config.lines).toEqual([])
})

properties.remove(config, 'key1')
expect(config.lines).toEqual(['key2=foo2'])
it('should remove all duplicate keys with remove', () => {
const config: properties.Properties = {
lines: [
'key1=foo1',
'key2=foo2',
'key1=foo3'
]
}

properties.remove(config, 'key1')
expect(config.lines).toEqual(['key2=foo2'])
})
})

describe('list', () => {
Expand Down
6 changes: 4 additions & 2 deletions src/properties.ts
Original file line number Diff line number Diff line change
Expand Up @@ -138,19 +138,21 @@ export const toMap = (config: Properties): Map<string, string> => {
* @param config Java properties set.
* @param key Key name.
* @param value New value. If undefined or null, key will be removed.
* @param options Optionally override set behavior.
*/
export const set = (
config: Properties,
key: string,
value: string | undefined | null
value: string | undefined | null,
options?: {separator?: string}
): void => {
// Find existing
const {start, len, sep} = findValue(config.lines, key)

// Prepare value
const items =
typeof value === 'string'
? [`${escapeKey(key)}${sep || '='}${escapeValue(value)}`]
? [`${escapeKey(key)}${options?.separator || sep || '='}${escapeValue(value)}`]
: []

// If found
Expand Down

0 comments on commit e494d09

Please sign in to comment.