Jest: Teste se objeto, array ou string.

Criado em 3 mai. 2017  ·  29Comentários  ·  Fonte: facebook/jest

Existe uma maneira de verificar se um componente é um objeto, array ou string? Isso seria semelhante ao 'should.be.a' do chai Ex .: validationResult.SSN [0] .should.be.a ('string').

Comentários muito úteis

Uma extensão toBeType simples para quem a deseja

expect.extend({
    toBeType(received, argument) {
        const initialType = typeof received;
        const type = initialType === "object" ? Array.isArray(received) ? "array" : initialType : initialType;
        return type === argument ? {
            message: () => `expected ${received} to be type ${argument}`,
            pass: true
        } : {
            message: () => `expected ${received} to be type ${argument}`,
            pass: false
        };
    }
});

describe("testing extended expect", () => {
    it("tests normal types correctly", () => {
        expect("").toBeType("string");
        expect({}).toBeType("object");
        expect(1).toBeType("number");
    });
    it("tests array types correctly", () => {
        expect([]).toBeType("array");
    });
    it("works with promises", () => {
        expect(Promise.resolve([])).resolves.toBeType("array");
    });
});

Muito simples de implementar. Realmente deveria estar no core tbh.

Nota - se você está colocando essa extensão em seus arquivos de configuração, então você quer em setupTestFrameworkScriptFile NOT setupFiles (uma vez que a extensão está disponível apenas no primeiro)

Todos 29 comentários

Não, não existe. Você encontrará a lista de todos os matchers disponíveis aqui: https://facebook.github.io/jest/docs/en/expect.html

Você também pode usar JavaScript simples ou biblioteca auxiliar como lodash para isso:

test('name', () => {
  // array
  expect(Array.isArray(['value'])).toBe(true);
  // string
  expect(typeof 'value').toBe('string');
  // object
  expect({value: 'value'}).toBeTruthy();
  expect(typeof {value: 'value'}).toBe('object');
})

Ponto menor - isso não ajuda com resultados promissores.

expect(somePromise).resolves.toBe(...) neste ponto, não há como verificar o tipo. Se você não se importa o que os conteúdos são, mas apenas que é uma string. Eu esperava que expects.stringContaining("") fosse uma solução alternativa, mas também não funcionou.

@abritinthebay Estou exatamente nessa situação e esse é o primeiro resultado no Google, talvez deva ser reaberto?

Certamente, deve-se pensar um pouco mais. Minha solução alternativa foi adicionar à cadeia de modo que faça a parte typeof . por exemplo:

expect(somePromise.then(data => typeof data)).resolves.toBe("object");

funciona, mas não está exatamente limpo.

@thymikee Verificar tipos de coisas é um caso de uso comum o suficiente (universal) que não há realmente nenhuma desculpa para uma estrutura de teste que não os possui. Suas alternativas são inaceitáveis, pois perdemos todo o contexto do que estamos testando.

Este expect(Array.isArray(['value'])).toBe(false); falha com

expect(received).toBe(expected)
    Expected value to be (using ===):
      false
    Received:
      true. 

Portanto, ou recebemos mensagens de afirmação terríveis ou temos que estender o Jest para suportar esse tipo de verificação. Não faz mais sentido para os mantenedores de Jest fazer isso uma vez, em vez de cada pessoa que usa requer que esses recursos os implementem por conta própria?

Crie seus próprios matchers com expect.extend e publique como um módulo npm. Se ficar popular, podemos mesclá-lo com o núcleo do Jest eventualmente;)

Uma extensão toBeType simples para quem a deseja

expect.extend({
    toBeType(received, argument) {
        const initialType = typeof received;
        const type = initialType === "object" ? Array.isArray(received) ? "array" : initialType : initialType;
        return type === argument ? {
            message: () => `expected ${received} to be type ${argument}`,
            pass: true
        } : {
            message: () => `expected ${received} to be type ${argument}`,
            pass: false
        };
    }
});

describe("testing extended expect", () => {
    it("tests normal types correctly", () => {
        expect("").toBeType("string");
        expect({}).toBeType("object");
        expect(1).toBeType("number");
    });
    it("tests array types correctly", () => {
        expect([]).toBeType("array");
    });
    it("works with promises", () => {
        expect(Promise.resolve([])).resolves.toBeType("array");
    });
});

Muito simples de implementar. Realmente deveria estar no core tbh.

Nota - se você está colocando essa extensão em seus arquivos de configuração, então você quer em setupTestFrameworkScriptFile NOT setupFiles (uma vez que a extensão está disponível apenas no primeiro)

Obrigado @abritinthebay

Então, eu envolvi isso em um módulo npm, se as pessoas quiserem:

https://www.npmjs.com/package/jest-tobetype

describe("assertion framework", ()=> {
 it("should check primitive types", () => {
   expect(expect.toBeA).toBeA("function")
  })
})

Falha: esperar (...). ToBeA não é uma funçãoTypeError: expect (...). ToBeA não é uma função

https://github.com/jest-community/jest-extended tem todos os matchers de tipo que você deseja (eu acho).

Tenho usado toBeInstanceOf em meus testes:

expect($wrapper.vm.countries).toBeInstanceOf(Array);

Crie seus próprios matchers com expect.extend e publique como um módulo npm. Se ficar popular, podemos mesclá-lo com o núcleo do Jest eventualmente;)

Sim, e pode escrever sua própria estrutura de brincadeira, enquanto você está nisso.

Esta pode ser uma das piores respostas que você pode obter no GitHub.

Portanto, @abritinthebay fez exatamente o que foi solicitado por @thymikee (que era muito mais do que a solicitação de pull padrão).

Agora que aquela alma corajosa fez todo o trabalho, quando o resto de nós pode finalmente obter este matcher (sem ter que instalar outra biblioteca)? Os mantenedores ainda estão promovendo a ideia de que isso não pertence a Jest ou isso simplesmente sumiu de seu radar?

Somos bastante rígidos com o que o torna no núcleo e normalmente não adicionamos combinações de açúcar. Jest core é uma arquitetura bastante grande e cada matcher que adicionamos aumenta o custo de manutenção

Para açúcar, geralmente recomendamos https://github.com/jest-community/jest-extended

O açúcar de um homem é a característica realmente útil e lógica de outro homem (ou, neste caso, pelo menos sete outras pessoas) que pertence à biblioteca central.

Obviamente, como mantenedor, seu voto supera todos os nossos, e você tem todos os tipos de preocupações que nós não temos, então eu respeito isso totalmente. Mas eu simplesmente pediria que você olhasse por que todos aqui consideram esse recurso como pertencente à biblioteca central (com tanta força que uma pessoa passou por vários obstáculos para escrever o código para você). Há uma necessidade aqui, e se você ignorá-la, os usuários da

.to.be.an.instanceOf não vai ser quantos usuários pensam em verificar os tipos, então para esses usuários, mesmo que você veja isso como um açúcar, você está efetivamente negando a eles a capacidade de verificar os tipos no Jest sem uma biblioteca adicional.

Sim, eu ouvi você. Para ser claro, por "açúcar" eu quis dizer sintaxe projetada para tornar as coisas mais fáceis de ler ou expressar . O açúcar, por definição, é uma variação de um recurso que já existe

Nesse caso, temos:

// Supported
expect(typeof foo).toBe('string');

// Proposed Sugar
expect(foo).toBeType('string');

Portanto, não é que não oferecemos suporte a tipos de verificação. Nós fazemos. Apoiamos a primeira opção. Esta opção usa o matcher toBe qual passamos muito tempo corrigindo os bugs e aprimorando a mensagem, para que os usuários tenham uma boa experiência

Existem cerca de 60 combinadores em brincadeira, e muitos deles são puro açúcar. Para qualquer um desses matchers você provavelmente encontrará pelo menos 7 outras pessoas que os acharão realmente úteis, então se essa fosse a heurística que usamos para adicionar ao núcleo, provavelmente gastaríamos todo o nosso tempo apenas mantendo matchers

Para ser completamente justo - a maioria dos combinadores são "açúcar" em algum nível. Quero dizer, toBeGreaterThanOrEqual é apenas açúcar por expect(foo >= bar).toBe(true);

Matchers são realmente _quase_tudo_ açucarado em torno de declarações booleanas;)

(Digo isso não para cavar, apenas para apontar que é ... uma linha muito borrada)

Como sugeriu abritinthebay, não se trata realmente de açúcar, mas de açúcar "necessário" e "desnecessário" (para a biblioteca central). Você tem um monte de pessoas neste tópico dizendo "ei, ser capaz de verificar todos os tipos é algo que deveria estar no núcleo de uma biblioteca de teste" (ou seja, é necessário).

Ouça-nos ou não, novamente, como mantenedor, você tem muitas outras preocupações. Mas não acho que a resposta certa seja dizer "o seu é apenas açúcar inerentemente desnecessário" (sou eu tentando parafrasear você, não tentando colocar palavras na sua boca) quando não é inerente: é 100% sua decisão, seja Brincadeira pode marcar todos os tipos ou não fora da caixa.

que tal, não é difícil: P?

expect(Array.isArray(['your', 'array'])).toBe(true);

expect(typeof something === "object").toBe(true); 
// - or -
expect(something instanceof Object).toBe(true);

expect(typeof something === "string").toBe(true); 

@nahumzs Embora funcione, o problema é que na saída do seu teste, ao falhar, aparecerá 'esperado que falso seja verdadeiro', o que não é muito útil;)

Eu acho que esse é o caminho a percorrer :)

describe('type check', () => {
    test('should be type string', () => {
        expect(typeof '').toBe('string')
    })

    test('should be type number', () => {
        expect(typeof 10).toBe('number')
    })

    test('should be type boolean', () => {
        expect(typeof true).toBe('boolean')
    })

    test('should be type undefined', () => {
        expect(typeof undefined).toBe('undefined')
    })

    test('should be type object', () => {
        expect(typeof { foo: 'bar' }).toBe('object')
    })

    test('should be type function', () => {
        expect(typeof function() {}).toBe('function')
    })

    test('should be type null', () => {
        expect(typeof null).toBe('object')
    })
})

Refatorei a implementação fornecida por @abritinthebay. Parece-me um pouco confortável para trabalhar.

`` `javascript
expect.extend ({
/ ** @param { } recebido
* @param {string | string []} arg
* @return {{passagem: booleano, mensagem: (função (): string)}}
* /
toBeType (recebido, arg) {
const isCorrectType = arg => {
const receivedType = typeof recebido;

        const checkForSingle = arg => {
            const type = receivedType === 'object'
                ? Array.isArray(received)
                    ? 'array'
                    : receivedType
                : receivedType;

            return type === arg;
        };

        const checkForArr = arg => {
            const reducer = (prev, curr) => prev || isCorrectType(curr).isCorrect;

            return arg.reduce(reducer, false);
        };

        return {
            receivedType,
            isCorrect: Array.isArray(arg)
                ? checkForArr(arg)
                : checkForSingle(arg)
        };
    };

    const {isCorrect, receivedType} = isCorrectType(arg);

    return {
        pass: isCorrect,
        message: () => {
            const toBe = Array.isArray(arg)
                ? arg.join(`' or '`)
                : arg;

            return `Expected '${received}' of '${receivedType}' type to be of '${toBe}' type(s)`;
        }
    };
}

});

Você deve verificar meu módulo (link acima). Faz um pouco mais do que isso. Mas se isso funcionar para você: use-o!

Eu acho que esse é o caminho a percorrer :)

describe('type check', () => {
    test('should be type string', () => {
        expect(typeof '').toBe('string')
    })

    test('should be type number', () => {
        expect(typeof 10).toBe('number')
    })

    test('should be type boolean', () => {
        expect(typeof true).toBe('boolean')
    })

    test('should be type undefined', () => {
        expect(typeof undefined).toBe('undefined')
    })

    test('should be type object', () => {
        expect(typeof { foo: 'bar' }).toBe('object')
    })

    test('should be type function', () => {
        expect(typeof function() {}).toBe('function')
    })

    test('should be type null', () => {
        expect(typeof null).toBe('object')
    })
})

Funciona perfeitamente, além de ser mais legível e de fácil manutenção para o futuro.

Eu acho que esse é o caminho a percorrer :)

describe('type check', () => {
    test('should be type string', () => {
        expect(typeof '').toBe('string')
    })

    test('should be type number', () => {
        expect(typeof 10).toBe('number')
    })

    test('should be type boolean', () => {
        expect(typeof true).toBe('boolean')
    })

    test('should be type undefined', () => {
        expect(typeof undefined).toBe('undefined')
    })

    test('should be type object', () => {
        expect(typeof { foo: 'bar' }).toBe('object')
    })

    test('should be type function', () => {
        expect(typeof function() {}).toBe('function')
    })

    test('should be type null', () => {
        expect(typeof null).toBe('object')
    })
})
    test('should be type object', () => {
        expect(typeof { foo: 'bar' }).toBe('object')
        // passes
        expect(typeof ['foo', 'bar']).toBe('object')
        // passes
        expect(typeof null).toBe('object')
    })

😞

É por isso que sugiro meu addon acima: cuide disso.

InstanceOf é um pouco melhor, mas propenso a problemas semelhantes.

Link para ele:

https://www.npmjs.com/package/jest-tobetype

obrigado pela solução @abritinthebay

Outra solução:

expect('example').toEqual(expect.any(String));
expect(123).toEqual(expect.any(String));

O segundo iria falhar com:

    Expected: Any<String>
    Received: 123
Esta página foi útil?
0 / 5 - 0 avaliações

Questões relacionadas

StephanBijzitter picture StephanBijzitter  ·  3Comentários

kgowru picture kgowru  ·  3Comentários

kentor picture kentor  ·  3Comentários

jardakotesovec picture jardakotesovec  ·  3Comentários

gustavjf picture gustavjf  ·  3Comentários