Cómo agregar <canvas> apoyo a mis pruebas en broma?

votos
9

En mi broma prueba unitaria estoy prestación de un componente con un ColorPicker . El ColorPickercomponente crea un objeto de la lona y el contexto 2d pero vuelve 'undefined'lo que arroja un errorCannot set property 'fillStyle' of undefined

if (typeof document == 'undefined') return null; // Dont Render On Server
var canvas = document.createElement('canvas'); 
canvas.width = canvas.height = size * 2;
var ctx = canvas.getContext('2d'); // returns 'undefined'
ctx.fillStyle = c1; // Cannot set property 'fillStyle' of undefined

Estoy teniendo problemas para averiguar por qué no puedo conseguir un contexto 2d. Tal vez hay un problema con mi configuración de prueba?

jest: {
  scriptPreprocessor: <rootDir>/node_modules/babel-jest,
  unmockedModulePathPatterns: [
    <rootDir>/node_modules/react,
    <rootDir>/node_modules/react-dom,
    <rootDir>/node_modules/react-addons-test-utils,
    <rootDir>/node_modules/react-tools
  ],
  moduleFileExtensions: [
    jsx,
    js,
    json,
    es6
  ],
  testFileExtensions: [
    jsx
  ],
  collectCoverage: true
}
Publicado el 21/10/2015 a las 17:57
fuente por usuario
En otros idiomas...                            


9 respuestas

votos
8

Se debe a que la prueba no se ejecuta en un navegador real. Broma utiliza jsdompara burlarse de las partes necesarias del DOM para poder ejecutar las pruebas en el nodo, evitando así el cálculo estilo y la prestación de un navegador que haría normalmente. Esto es genial, porque esto hace que las pruebas rápidas.

Por otro lado, si necesita API navegador en sus componentes, es más difícil entonces en el navegador. Por suerte, jsdomtiene soporte para la lona . Sólo tienes que configurarlo:

jsdom incluye soporte para el uso de la lona paquete para extender cualquier <canvas>elementos con el API de la lona. Para que esto funcione, es necesario incluir la lona como una dependencia en su proyecto, como un par de jsdom. Si jsdom puede encontrar el paquete de la lona, se va a usar, pero si no está presente, entonces <canvas>los elementos se comportará como <div>s.

Como alternativa, puede sustituir a la broma con algo de corredor de prueba basada en navegador como Karma . La broma es bastante buggy de todos modos.

Respondida el 22/10/2015 a las 07:18
fuente por usuario

votos
1

Yo tuve exactamente el mismo problema. Estoy a desplegar gitlab ci ejecutar mis pruebas, y desde la lona NPM requiere una instalación de El Cairo, utilizando esa no era una opción viable.

Todo lo que realmente quería hacer era simulacro de la implementación a través de la broma por lo que en realidad no tratar de crear un contexto real. He aquí cómo lo resolví:

añadido a package.json

"jest": {
  "setupFiles": ["./tests/setup.js"],
}

pruebas / setup.js

import sinon from 'sinon';

const createElement = global.document.createElement;
const FAKECanvasElement = {
  getContext: jest.fn(() => {
    return {
      fillStyle: null,
      fillRect: jest.fn(),
      drawImage: jest.fn(),
      getImageData: jest.fn(),
    };
  }),
};

/**
 * Using Sinon to stub the createElement function call with the original method
 * unless we match the 'canvas' argument.  If that's the case, return the Fake 
 * Canvas object.
 */
sinon.stub(global.document, 'createElement')
  .callsFake(createElement)
  .withArgs('canvas')
  .returns(FAKECanvasElement);
Respondida el 03/10/2017 a las 19:35
fuente por usuario

votos
1

Para mi caso de uso sencillo que hice parches mono como esto

beforeEach(() => {
    const createElement = document.createElement.bind(document);
    document.createElement = (tagName) => {
        if (tagName === 'canvas') {
            return {
                getContext: () => ({}),
                measureText: () => ({})
            };
        }
        return createElement(tagName);
    };
});

No es necesario instalar una lona de pre-compilados o sinon.

Respondida el 26/10/2017 a las 09:01
fuente por usuario

votos
0

Creo que es necesario broma-lona-simulacro .

Instalar

Esto sólo se debe instalar como una dependencia de desarrollo (devDependencies), ya que sólo está diseñado para la prueba.

NPM i --save-dev-broma tela simulada

Preparar

En su package.json bajo la broma, crear una matriz SetupFiles y añadir broma-lona-maqueta a la matriz.

{
    "jest": {
        "setupFiles": ["jest-canvas-mock"]
    }
}

Si ya tiene un SetupFiles atribuir también se puede añadir broma-lona-maqueta a la matriz.

{
    "jest": {
        "setupFiles": ["./__setups__/other.js", "jest-canvas-mock"]
    }
}
Respondida el 25/12/2017 a las 09:49
fuente por usuario

votos
0

Para aquellos que buscan crear ejemplos usando reaccionar aplicación

Instalar

yarn add --dev jest-canvas-mock

Crear un nuevo ${rootDir}/src/setupTests.jscon

import 'jest-canvas-mock';
Respondida el 13/03/2019 a las 14:39
fuente por usuario

votos
0
npm install -D canvas-prebuilt@1

Esto proporciona apoyo a la lona para jest.This funciona incluso si alguien está recibiendo el error debido a Lottie.js.

Respondida el 04/04/2019 a las 06:53
fuente por usuario

votos
0

Para probar la salida de la lona en broma que tiene que hacer lo siguiente:

Asegúrese de que está utilizando al menos jsdom 13. Usted puede hacer esto mediante la inclusión del paquete jsom de broma, por 14 que es:

jest-environment-jsdom-fourteen

Y configuración de broma utilizar este

jest --env=jest-environment-jsdom-fourteen

o en el package.json

"jest": {
   ...
   "testEnvironment": "jest-environment-jsdom-fourteen",

Incluya el canvaspaquete de NPM. (a partir de 2.x esto incluye la versión incorporada de modo lona prebuilt está en desuso).

Respondida el 13/09/2019 a las 12:03
fuente por usuario

votos
0

Me las arreglé para crear una prueba de imagen de la instantánea de un lienzo en broma con-prueba reaccionar-biblioteca y broma de imágenes instantáneas. En cierto modo es buzzwordy pero funcionó muy bien.

Si usted es capaz de configurar correctamente su prueba broma con el nodo-lona (no broma-lona-maqueta o similar), entonces puede literalmente llama toDataURL en el elemento canvas.


  import {render, waitForElement} from 'react-testing-library'
  import React from 'react'
  import { toMatchImageSnapshot } from 'jest-image-snapshot'

  expect.extend({ toMatchImageSnapshot })

  test('open a canvas', async () => {
    const { getByTestId } = render(
      <YourCanvasContainer />,
    )
    const canvas = await waitForElement(() =>
      getByTestId('your_canvas'),
    )
    const img = canvas.toDataURL()
    const data = img.replace(/^data:image\/\w+;base64,/, '')
    const buf = Buffer.from(data, 'base64')
    expect(buf).toMatchImageSnapshot({
      failureThreshold: 0.001,
      failureThresholdType: 'percent',
    })
  })

Me pareció que tenía que utilizar un umbral bajo en lugar de comparar directamente la imagen / png URL datos, ya que había dos píxeles que eran simplemente al azar diferente cuando se ejecuta en travis-CI

También considere actualizar manualmente broma jsdom entorno a broma, medio ambiente y jsdom-trece o broma, medio ambiente y jsdom-catorce (otras respuestas en esta página sugieren similar) y se refieren a https://github.com/jsdom/jsdom/issues/1782

Respondida el 30/11/2019 a las 17:58
fuente por usuario

votos
0

broma-lona-maqueta funcionará bien.

1) Instalar por **npm i --save-dev jest-canvas-mock**

2) En sus broma de jest.config.js añadir "setupFiles": ["jest-canvas-mock"]atributo. (Si ya tiene un SetupFiles atribuir también puede anexar broma-lona-maqueta a la matriz, por ejemplo "setupFiles": ["something-xyz.js", "jest-canvas-mock"]).

Todo listo.

Respondida el 20/01/2020 a las 18:48
fuente por usuario

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more