4 Frontend Test Guidelines
Marcus Efraimsson edited this page 2018-08-14 13:47:56 +02:00

General

  • A test for component dir/a.ts resides in dir/specs/a.test.ts.
  • A test for React component dir/a.tsx resides in dir/a.test.tsx
  • Tests are unit tests and should not instantiate the whole app.
  • Learn from other, recently written tests.
  • Tests are written in Jest.

Guidelines

  • Pure functions are easier to test than object members. Try writing the code accordingly.
  • When instantiating classes try to provide the absolute minimum in the constructor.
  • Keep the tests as framework-agnostic as possible, e.g.,:
    • remove angular-specific mocks
    • replace ctx.$q.when() with Promise.resolve(). Use the q package to handle cases where .finally() is a problem: q.when().

Structure

  • Execute the function that's being tested in the test block, not in setup or beforeEach.
  • Make clear what's being tested:
import MyComponent, { processData } from '../MyComponent';

describe('MyComponent', () => {
  // Component-wide tests
  it('should do something', () => {
  });

  // Component-member tests
  describe('modifyComponent()', () => {
    it('should modify the component like this', () => {
      const component = new MyComponent();

      let options = {};
      component.modifyComponent(options);
      expect(component.x).toBe(..);

      options = { foo: 42 };
      component.modifyComponent(options);
      expect(component.x).toBe(..);
    });
  });
});

// Pure functions
describe('processData()', () => {
  it('should transform input to output', () => {
  });
});

Examples

Setups stubs and passes them as parameters into the constructor:

These tests use the simple backend_srv stub(https://github.com/grafana/grafana/blob/master/public/test/mocks/backend_srv.ts):

This test uses a Jest mock to test if an event has been emitted which can be useful sometimes. Most of the time you should use a stub rather than a mock but this is a case where you have to use a mock: