Skip to content

Commit

Permalink
Merge branch 'update-next' into next
Browse files Browse the repository at this point in the history
  • Loading branch information
jsumners committed Jul 9, 2024
2 parents fc2b267 + 16f52a3 commit 1c922e2
Show file tree
Hide file tree
Showing 9 changed files with 206 additions and 2 deletions.
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
"standard": "^17.1.0",
"tap": "^18.7.1",
"tinybench": "^2.6.0",
"tsd": "^0.30.7",
"tsd": "^0.31.0",
"typescript": "^5.4.3"
},
"keywords": [
Expand Down
28 changes: 28 additions & 0 deletions test/basename.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
'use strict'

const { test } = require('tap')
const basename = require('../lib/utils/basename')

test('basename', (t) => {
const testCases = [
{ description: 'returns an empty string if the path is not a string', path: {}, expected: '' },
{ description: 'returns an empty string if the path includes a \' and the char after is a .', path: 'path\\.', expected: '' },
{ description: 'returns an empty string if the path includes a / and the char after is a .', path: 'path/.', expected: '' },
{ description: 'returns an empty string if the path includes a \' and the chars after are a ..', path: 'path\\..', expected: '' },
{ description: 'returns an empty string if the path includes a / and the chars after are a ..', path: 'path/..', expected: '' },
{ description: 'returns the path if the path includes a \' and the rest is anything other than dots', path: 'path\\subpath', expected: 'subpath' },
{ description: 'returns the path if the path includes a / and the rest is anything other than dots', path: 'path/subpath', expected: 'subpath' },
{ description: 'returns an empty string if the path is a .', path: '.', expected: '' },
{ description: 'returns an empty string if the path is a ..', path: '..', expected: '' },
{ description: 'returns the path if the path is anything other than dots', path: 'subpath', expected: 'subpath' }
]

t.plan(testCases.length)

testCases.forEach((testCase, index) => {
t.test(testCase.description, t => {
t.plan(1)
t.equal(basename(testCase.path), testCase.expected, `Test case ${index + 1}`)
})
})
})
17 changes: 17 additions & 0 deletions test/busboy-emit.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
'use strict'

const Busboy = require('../lib/main')
const { test } = require('tap')

test('busboy, emit', t => {
t.plan(1)

t.test('returns undefined when the event is called a second time and the busboy was already finished', t => {
const busboy = new Busboy({ headers: { 'content-type': 'application/x-www-form-urlencoded' } })
busboy._finished = true
busboy.emit('finish')

t.equal(busboy.emit('finish'), undefined)
t.end()
})
})
5 changes: 5 additions & 0 deletions test/decoder.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,11 @@ test('Decoder', t => {
expected: 'Hello world',
what: 'One full encoded byte'
},
{
source: ['%20Hello World'],
expected: ' Hello World',
what: 'Start with full encoded byte'
},
{
source: ['Hello%20world%21'],
expected: 'Hello world!',
Expand Down
19 changes: 19 additions & 0 deletions test/dicer-write.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
'use strict'

const { test } = require('tap')
const { Dicer } = require('../lib/main')

test('dicer _write method', t => {
t.plan(1)

t.test('calls the callback cb() when headerFirst is set and all the data have been written', t => {
t.plan(1)
const dicer = new Dicer({ headerFirst: true })

dicer._write(Buffer.from('Content-Type: text/plain'), null, () => {
dicer._write(Buffer.from('Content-Type: text/plain'), null, () => {
t.pass('write method called')
})
})
})
})
16 changes: 16 additions & 0 deletions test/multipart-constructor.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
'use strict'

const Multipart = require('../lib/types/multipart')
const Busboy = require('../lib/main')
const { test } = require('tap')

test('multipart constructor', t => {
t.plan(1)

t.test('throws if the boundary is not a string', t => {
const busboy = new Busboy({ headers: { 'content-type': 'application/x-www-form-urlencoded' } })

t.throws(() => new Multipart(busboy, { boundary: 123 }), new Error('Multipart: Boundary not found'))
t.end()
})
})
10 changes: 10 additions & 0 deletions test/parse-params.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,11 @@ test('parse-params', t => {
expected: ['text/plain', ['greeting', 'hello "world"']],
what: 'Quotes within quoted'
},
{
source: 'text/plain; greeting="hello \\\\world\\\\"',
expected: ['text/plain', ['greeting', 'hello \\world\\']],
what: 'Escape within quoted'
},
{
source: 'text/plain; encoding=""',
expected: ['text/plain', ['encoding', '']],
Expand Down Expand Up @@ -86,6 +91,11 @@ test('parse-params', t => {
expected: ['text/plain', ['filename', '£ rates'], ['altfilename', 'foobarbaz']],
what: 'Mixed regular and extended parameters (RFC 5987)'
},
{
source: "text/plain; filename*=iso-8859-1'en';",
expected: ['text/plain', ['filename', '']],
what: 'Mixed regular and extended parameters (RFC 5987) with separator'
},
{
source: "text/plain; filename=\"foobarbaz\"; altfilename*=iso-8859-1'en'%A3%20rates",
expected: ['text/plain', ['filename', 'foobarbaz'], ['altfilename', '£ rates']],
Expand Down
36 changes: 35 additions & 1 deletion test/streamsearch.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ const { test } = require('tap')
const Streamsearch = require('../deps/streamsearch/sbmh')

test('streamsearch', t => {
t.plan(17)
t.plan(18)

t.test('should throw an error if the needle is not a String or Buffer', t => {
t.plan(1)
Expand Down Expand Up @@ -335,6 +335,40 @@ test('streamsearch', t => {
s.push(chunks[3])
})

t.test('should process four chunks with repeted starting overflowing needle', t => {
t.plan(13)

const expected = [
[false, Buffer.from('\n\n\0'), 0, 1],
[true, undefined, undefined, undefined],
[false, Buffer.from('\r\nhello'), 1, 7]
]
const needle = '\n\n\r'
const s = new Streamsearch(needle)
const chunks = [
Buffer.from('\n'),
Buffer.from('\n'),
Buffer.from('\n'),
Buffer.from('\r\nhello')
]
let i = 0
s.on('info', (isMatched, data, start, end) => {
t.strictSame(isMatched, expected[i][0])
t.strictSame(data, expected[i][1])
t.strictSame(start, expected[i][2])
t.strictSame(end, expected[i][3])
i++
if (i >= 3) {
t.pass()
}
})

s.push(chunks[0])
s.push(chunks[1])
s.push(chunks[2])
s.push(chunks[3])
})

t.test('should process four chunks with a potentially overflowing needle', t => {
t.plan(17)

Expand Down
75 changes: 75 additions & 0 deletions test/types-urlencoded.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,13 @@ const tests = [
what: 'Unassigned and assigned value',
plan: 5
},
{
source: ['foo&baz=bla'],
expected: [['foo', '', false, false]],
what: 'Unassigned and assigned value with limit',
limits: { fields: 1 },
plan: 4
},
{
source: ['foo=bar&baz'],
expected: [['foo', 'bar', false, false],
Expand Down Expand Up @@ -80,6 +87,13 @@ const tests = [
what: 'Two assigned values, one with encoded bytes',
plan: 5
},
{
source: ['foo=bar&baz=bla', 'foo=bar'],
expected: [],
what: 'Exceeded limits',
limits: { fields: 0 },
plan: 3
},
{
source: ['foo=bar&baz=bla'],
expected: [],
Expand Down Expand Up @@ -110,6 +124,22 @@ const tests = [
limits: { fieldNameSize: 2 },
plan: 5
},
{
source: ['f%20=bar&baz=bla'],
expected: [['f ', 'bar', false, false],
['ba', 'bla', true, false]],
what: 'Limits: truncated field name with encoded bytes',
limits: { fieldNameSize: 2 },
plan: 5
},
{
source: ['foo=b%20&baz=bla'],
expected: [['foo', 'b ', false, false],
['baz', 'bl', false, true]],
what: 'Limits: truncated field value with encoded bytes',
limits: { fieldSize: 2 },
plan: 5
},
{
source: ['foo=bar&baz=bla'],
expected: [['foo', 'ba', false, true],
Expand Down Expand Up @@ -208,3 +238,48 @@ tests.forEach((v) => {
busboy.end()
})
})

test('Call parser end twice', t => {
t.plan(1)

let finishes = 0
const busboy = new Busboy({
headers: {
'content-type': 'application/x-www-form-urlencoded; charset=utf-8'
}
})

busboy.on('finish', function () {
t.ok(++finishes === 1, 'finish emitted')
})

busboy.write(Buffer.from('Hello world', 'utf8'), EMPTY_FN)

busboy._parser.end()
busboy._parser.end()
})

test('Call emit finish twice', t => {
t.plan(2)

let fields = 0
let finishes = 0

const busboy = new Busboy({
headers: {
'content-type': 'application/x-www-form-urlencoded; charset=utf-8'
}
})
busboy.on('field', function () {
t.ok(++fields === 1, 'field emitted')
})

busboy.on('finish', function () {
t.ok(++finishes === 1, 'finish emitted')
})

busboy.write(Buffer.from('Hello world', 'utf8'), EMPTY_FN)

busboy.emit('finish')
busboy.emit('finish')
})

0 comments on commit 1c922e2

Please sign in to comment.