Empresas
Empregos
  • Sobre nós
  • Soluções
    • Publicação de vagas
      Publique sua vaga e receba candidatos qualificados em 48h.
    • Avaliações de candidatos
      Mais de 500 testes técnicos e psicológicos, mais anti-fraude.
    • Headhunting
      Busca executiva personalizada do início ao fim.
    • Folha de Pagamento + EOR
      Dispersão de folha e EOR em mais de 15 países da LATAM.
  • Preços
  • Empregos

0

76
Visualizações
Testing actions reliably

I'm using xstate to implement a login flow. I have a machine where the initialState invokes a Promise, and if it's rejected it will redirect to a state that has an entry action. I would like to test that the action is called at the right time properly.

machine.ts

{
  id: 'entrance',
  initial: States.FETCHING_SESSION,
  states: {
    [States.FETCHING_SESSION]: {
      invoke: {
        src: 'fetchSession',
        onError: {
          target: States.LOGGED_OUT,
        }
      }
    },
    [States.LOGGED_OUT]: {
      entry: ['navigateToLogin']
      type: 'final'
    },
  }
}

machine.spec.ts

    const mockFetchSession = jest.fn()
      .mockRejectedValueOnce({ error: new Error('401 unauthorized') })
    const mockNavigateToLogin = jest.fn()

    const service = interpret(entranceMachine.withConfig({
      services: {
        fetchSession: mockFetchSession
      },
      actions: {
        navigateToLogin: mockNavigateToLogin
      }
    }))

    it('Goes to login page on fail', (done) => {
      service.onTransition((state) => {
        expect(state.matches(States.LOGGED_OUT))
        expect(mockNavigateToLogin).toHaveBeenCalled() // <- this test case always fails
        done()
      })
      service.start()
    })

I managed to make it work in kinda of an ugly way by wrapping expect around a setTimout.

setTimeout(() => expect(mockNavigateToLogin).toHaveBeenCalled(), 100)

I wonder if there is a better option? Thanks

about 4 years ago · Juan Pablo Isaza
1 Respostas
Responde à pergunta

0

First, I suspect setTimeout just skips the expect..

I ran into the same issue using withConfig. The actions at least, are not called at all even if they appear in machine.options.actions.

My code looks like this:

const myAction = jest.fn();
const actions = { myAction };
const withCfg = machine.withConfig({
  actions,
});
const spy = jest
  .spyOn(actions, 'myAction')
  .mockImplementation(() => myAction());
// ...

expect(spy).toHaveBeenCalledTimes(1);

Note that in application those actions are executed just fine

about 4 years ago · Juan Pablo Isaza Relatório
Responde à pergunta
Encontrar trabalhos remotos

Descubra a nova forma de encontrar um emprego!

melhores empregos
Principais categorias de trabalho
Empresas
Postar vaga Preços Comercial
Jurídico
Termos e Condições Política de privacidade
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Recomende algumas ofertas para mim
Preciso de ajuda