Skip to content
This repository has been archived by the owner on Feb 12, 2024. It is now read-only.

Commit

Permalink
chore: fix tests for add input
Browse files Browse the repository at this point in the history
  • Loading branch information
achingbrain committed Sep 28, 2021
1 parent 8ca99b0 commit 0887fdb
Show file tree
Hide file tree
Showing 5 changed files with 178 additions and 103 deletions.
19 changes: 13 additions & 6 deletions packages/ipfs-core-utils/src/files/normalise-candidate-multiple.js
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,10 @@ export async function * normaliseCandidateMultiple (input, normaliseContent) {
// String
// Uint8Array|ArrayBuffer|TypedArray
// Blob|File
if (typeof input === 'string' || input instanceof String || isBytes(input) || isBlob(input)) {
throw errCode(new Error('Unexpected input: single item passed'), 'ERR_UNEXPECTED_INPUT')
// fs.ReadStream
// @ts-expect-error _readableState is a property of a node fs.ReadStream
if (typeof input === 'string' || input instanceof String || isBytes(input) || isBlob(input) || input._readableState) {
throw errCode(new Error('Unexpected input: single item passed - if you are using ipfs.allAll, please use ipfs.add instead'), 'ERR_UNEXPECTED_INPUT')
}

// Browser ReadableStream
Expand All @@ -57,8 +59,8 @@ export async function * normaliseCandidateMultiple (input, normaliseContent) {

// (Async)Iterable<Number>
// (Async)Iterable<Bytes>
if (Number.isInteger(value) || isBytes(value)) {
throw errCode(new Error('Unexpected input: single item passed'), 'ERR_UNEXPECTED_INPUT')
if (Number.isInteger(value)) {
throw errCode(new Error('Unexpected input: single item passed - if you are using ipfs.allAll, please use ipfs.add instead'), 'ERR_UNEXPECTED_INPUT')
}

// (Async)Iterable<fs.ReadStream>
Expand All @@ -68,11 +70,16 @@ export async function * normaliseCandidateMultiple (input, normaliseContent) {
return
}

if (isBytes(value)) {
yield toFileObject({ content: peekable }, normaliseContent)
return
}

// (Async)Iterable<(Async)Iterable<?>>
// (Async)Iterable<ReadableStream<?>>
// ReadableStream<(Async)Iterable<?>>
// ReadableStream<ReadableStream<?>>
if (isFileObject(value) || value[Symbol.iterator] || value[Symbol.asyncIterator] || isReadableStream(value)) {
if (isFileObject(value) || value[Symbol.iterator] || value[Symbol.asyncIterator] || isReadableStream(value) || isBlob(value)) {
yield * map(peekable, (/** @type {ImportCandidate} */ value) => toFileObject(value, normaliseContent))
return
}
Expand All @@ -82,7 +89,7 @@ export async function * normaliseCandidateMultiple (input, normaliseContent) {
// Note: Detected _after_ (Async)Iterable<?> because Node.js fs.ReadStreams have a
// `path` property that passes this check.
if (isFileObject(input)) {
throw errCode(new Error('Unexpected input: single item passed'), 'ERR_UNEXPECTED_INPUT')
throw errCode(new Error('Unexpected input: single item passed - if you are using ipfs.allAll, please use ipfs.add instead'), 'ERR_UNEXPECTED_INPUT')
}

throw errCode(new Error('Unexpected input: ' + typeof input), 'ERR_UNEXPECTED_INPUT')
Expand Down
13 changes: 3 additions & 10 deletions packages/ipfs-core-utils/src/files/normalise-candidate-single.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import errCode from 'err-code'
import browserStreamToIt from 'browser-readablestream-to-it'
import itPeekable from 'it-peekable'
import map from 'it-map'
import {
isBytes,
isBlob,
Expand Down Expand Up @@ -66,19 +65,13 @@ export async function * normaliseCandidateSingle (input, normaliseContent) {

// (Async)Iterable<Number>
// (Async)Iterable<Bytes>
if (Number.isInteger(value) || isBytes(value)) {
// (Async)Iterable<String>
if (Number.isInteger(value) || isBytes(value) || typeof value === 'string' || value instanceof String) {
yield toFileObject(peekable, normaliseContent)
return
}

// (Async)Iterable<fs.ReadStream>
if (value._readableState) {
// @ts-ignore Node fs.ReadStreams have a `.path` property so we need to pass it as the content
yield * map(peekable, (/** @type {ImportCandidate} */ value) => toFileObject({ content: value }, normaliseContent))
return
}

throw errCode(new Error('Unexpected input: multiple items passed'), 'ERR_UNEXPECTED_INPUT')
throw errCode(new Error('Unexpected input: multiple items passed - if you are using ipfs.add, please use ipfs.addAll instead'), 'ERR_UNEXPECTED_INPUT')
}

// { path, content: ? }
Expand Down
129 changes: 85 additions & 44 deletions packages/ipfs-core-utils/test/files/normalise-input-multiple.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ const NEWSTRING = () => new String('hello world') // eslint-disable-line no-new-
const BUFFER = () => uint8ArrayFromString(STRING())
const ARRAY = () => Array.from(BUFFER())
const TYPEDARRAY = () => Uint8Array.from(ARRAY())
const FILE = () => new File([BUFFER()], 'test-file.txt')
/** @type {() => Blob} */
let BLOB

Expand Down Expand Up @@ -54,6 +55,14 @@ async function testContent (input) {
await verifyNormalisation(result)
}

/**
* @param {*} input
* @param {RegExp} message
*/
async function testFailure (input, message) {
await expect(all(normaliseInput(input))).to.eventually.be.rejectedWith(message)
}

/**
* @template T
* @param {T} thing
Expand Down Expand Up @@ -90,14 +99,14 @@ describe('normalise-input-multiple', function () {
/**
* @param {() => any} content
* @param {string} name
* @param {boolean} isBytes
* @param {{ acceptStream: boolean, acceptContentStream: boolean }} options
*/
function testInputType (content, name, isBytes) {
it(name, async function () {
await testContent(content())
function testInputType (content, name, { acceptStream, acceptContentStream }) {
it(`Failure ${name}`, async function () {
await testFailure(content(), /single item passed/)
})

if (isBytes) {
if (acceptStream) {
if (ReadableStream) {
it(`ReadableStream<${name}>`, async function () {
await testContent(browserReadableStreamOf(content()))
Expand All @@ -111,43 +120,35 @@ describe('normalise-input-multiple', function () {
it(`AsyncIterable<${name}>`, async function () {
await testContent(asyncIterableOf(content()))
})
}

it(`{ path: '', content: ${name} }`, async function () {
await testContent({ path: '', content: content() })
})

if (isBytes) {
} else {
if (ReadableStream) {
it(`{ path: '', content: ReadableStream<${name}> }`, async function () {
await testContent({ path: '', content: browserReadableStreamOf(content()) })
it(`Failure ReadableStream<${name}>`, async function () {
await testFailure(browserReadableStreamOf(content()), /single item passed/)
})
}

it(`{ path: '', content: Iterable<${name}> }`, async function () {
await testContent({ path: '', content: iterableOf(content()) })
it(`Failure Iterable<${name}>`, async function () {
await testFailure(iterableOf(content()), /single item passed/)
})

it(`{ path: '', content: AsyncIterable<${name}> }`, async function () {
await testContent({ path: '', content: asyncIterableOf(content()) })
it(`Failure AsyncIterable<${name}>`, async function () {
await testFailure(asyncIterableOf(content()), /single item passed/)
})
}

if (ReadableStream) {
it(`ReadableStream<${name}>`, async function () {
await testContent(browserReadableStreamOf(content()))
})
}
it(`Failure { path: '', content: ${name} }`, async function () {
await testFailure({ path: '', content: content() }, /single item passed/)
})

it(`Iterable<{ path: '', content: ${name} }`, async function () {
it(`Iterable<{ path: '', content: ${name} }>`, async function () {
await testContent(iterableOf({ path: '', content: content() }))
})

it(`AsyncIterable<{ path: '', content: ${name} }`, async function () {
it(`AsyncIterable<{ path: '', content: ${name} }>`, async function () {
await testContent(asyncIterableOf({ path: '', content: content() }))
})

if (isBytes) {
if (acceptContentStream) {
if (ReadableStream) {
it(`Iterable<{ path: '', content: ReadableStream<${name}> }>`, async function () {
await testContent(iterableOf({ path: '', content: browserReadableStreamOf(content()) }))
Expand Down Expand Up @@ -175,40 +176,85 @@ describe('normalise-input-multiple', function () {
it(`AsyncIterable<{ path: '', content: AsyncIterable<${name}> }>`, async function () {
await testContent(asyncIterableOf({ path: '', content: asyncIterableOf(content()) }))
})
} else {
if (ReadableStream) {
it(`Failure Iterable<{ path: '', content: ReadableStream<${name}> }>`, async function () {
await testFailure(iterableOf({ path: '', content: browserReadableStreamOf(content()) }), /Unexpected input/)
})
}

it(`Failure Iterable<{ path: '', content: Iterable<${name}> }>`, async function () {
await testFailure(iterableOf({ path: '', content: iterableOf(content()) }), /Unexpected input/)
})

it(`Failure Iterable<{ path: '', content: AsyncIterable<${name}> }>`, async function () {
await testFailure(iterableOf({ path: '', content: asyncIterableOf(content()) }), /Unexpected input/)
})

if (ReadableStream) {
it(`Failure AsyncIterable<{ path: '', content: ReadableStream<${name}> }>`, async function () {
await testFailure(asyncIterableOf({ path: '', content: browserReadableStreamOf(content()) }), /Unexpected input/)
})
}

it(`Failure AsyncIterable<{ path: '', content: Iterable<${name}> }>`, async function () {
await testFailure(asyncIterableOf({ path: '', content: iterableOf(content()) }), /Unexpected input/)
})

it(`Failure AsyncIterable<{ path: '', content: AsyncIterable<${name}> }>`, async function () {
await testFailure(asyncIterableOf({ path: '', content: asyncIterableOf(content()) }), /Unexpected input/)
})
}
}

describe('String', () => {
testInputType(STRING, 'String', true)
testInputType(NEWSTRING, 'new String()', true)
testInputType(STRING, 'String', {
acceptStream: true,
acceptContentStream: true
})
testInputType(NEWSTRING, 'new String()', {
acceptStream: true,
acceptContentStream: true
})
})

describe('Buffer', () => {
testInputType(BUFFER, 'Buffer', true)
testInputType(BUFFER, 'Buffer', {
acceptStream: true,
acceptContentStream: true
})
})

describe('Blob', () => {
if (!Blob) {
return
}

testInputType(BLOB, 'Blob', false)
testInputType(BLOB, 'Blob', {
acceptStream: true,
acceptContentStream: false
})
})

describe('@web-std/file', () => {
it('normalizes File input', async () => {
const FILE = new File([BUFFER()], 'test-file.txt')

await testContent(FILE)
testInputType(FILE, 'File', {
acceptStream: true,
acceptContentStream: false
})
})

describe('Iterable<Number>', () => {
testInputType(ARRAY, 'Iterable<Number>', false)
testInputType(ARRAY, 'Iterable<Number>', {
acceptStream: true,
acceptContentStream: false
})
})

describe('TypedArray', () => {
testInputType(TYPEDARRAY, 'TypedArray', true)
testInputType(TYPEDARRAY, 'TypedArray', {
acceptStream: true,
acceptContentStream: true
})
})

if (isNode) {
Expand All @@ -226,14 +272,9 @@ describe('normalise-input-multiple', function () {
return fs.createReadStream(path)
}

testInputType(NODEFSREADSTREAM, 'Node fs.ReadStream', false)

it('Iterable<Node fs.ReadStream>', async function () {
await testContent(iterableOf(NODEFSREADSTREAM()))
})

it('AsyncIterable<Node fs.ReadStream>', async function () {
await testContent(asyncIterableOf(NODEFSREADSTREAM()))
testInputType(NODEFSREADSTREAM, 'Node fs.ReadStream', {
acceptStream: true,
acceptContentStream: false
})
})
}
Expand Down
Loading

0 comments on commit 0887fdb

Please sign in to comment.