question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

mockStatic of enum class is unstable - impacted by earlier use of the class (unrelated to mockStatic)

See original GitHub issue

OS: Windows 10 Mockito: 3.7.0 JUnit5: 5.7.0 Java: 8 (8u202)

We have two tests. A and B. When run in the order [B, A] they pass. When run in the order [A, B] B fails. Failure is related to “switch” java statement with enum usage.

package com;

import org.junit.jupiter.api.MethodOrderer;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.TestMethodOrder;
import org.mockito.MockedStatic;
import org.springframework.test.util.ReflectionTestUtils;

import static com.MyEnum.A_VALUE;
import static com.MyEnum.B_VALUE;
import static com.MyEnum.C_VALUE;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.mockStatic;
import static org.mockito.Mockito.when;

@TestMethodOrder(MethodOrderer.MethodName.class)
class MyFactoryClassWithEnumTest {
    @Test
    void aTest() {
        MyFactoryClass factory = MyFactoryClass.create();

        assertThat(factory.valuesVisible()).isEqualTo(new MyEnum[] {
                A_VALUE,
                B_VALUE,
                C_VALUE
        });
        factory.switchEval(A_VALUE);
    }

    @Test
    void bTest() {
        MyEnum mockInstance = mock(MyEnum.class);
        when(mockInstance.ordinal()).thenReturn(MyEnum.values().length);
        ReflectionTestUtils.setField(mockInstance, "ordinal", MyEnum.values().length);

        try (MockedStatic<MyEnum> mockedDropType = mockStatic(MyEnum.class)) {
            mockedDropType.when(MyEnum::values).thenReturn(new MyEnum[]{
                    A_VALUE,
                    B_VALUE,
                    C_VALUE,
                    mockInstance
            });

            MyFactoryClass factory = MyFactoryClass.create();
            assertThat(factory.valuesVisible()).isEqualTo(new MyEnum[] {
                    A_VALUE,
                    B_VALUE,
                    C_VALUE,
                    mockInstance});
            factory.switchEval(mockInstance);
        }
    }
}

While classes are as simple as possible:

package com;

public enum MyEnum {
    A_VALUE,
    B_VALUE,
    C_VALUE
}
package com;

import lombok.AllArgsConstructor;

@AllArgsConstructor(staticName = "create")
public class MyFactoryClass {
    public void switchEval(MyEnum myEnum) {
        switch (myEnum) {
            default:
                System.out.println("DONE!");
        }
    }

    public MyEnum[] valuesVisible() {
        return MyEnum.values();
    }
}

MyFactoryClass is the class that should return in (here absent) method “of” appropriate object related to enum value. We want to test “default” scenario (if someone would be so nice to “override” our enum by his own enum by injecting it “earlier” in the classpath, or just when there’s an incompatibility somewhere along the line).

Obviously if there’s a better way to test such a scenario, we could change our approach accordingly.

Issue Analytics

  • State:open
  • Created 3 years ago
  • Comments:8 (2 by maintainers)

github_iconTop GitHub Comments

1reaction
GregoryBevancommented, Apr 6, 2022

I encountered the samed problem while mocking an Enum and found a workaround by moving the test that contains the MockedStatic call in an inner static class. This cause isolation of the test and doesn’t interfere with other tests.

Not a solution, just a workaround…

0reactions
roli2otletcommented, Jul 27, 2022

Still struggling with the same issue. Inner static class was not helping at all to us unfortunately.

Read more comments on GitHub >

github_iconTop Results From Across the Web

How to mock a method in an ENUM class? - Stack Overflow
You need Powermock, because Mockito is not able to mock static mehtods: ... mockStatic(DatacenterEnum.class); when(DatacenterEnum.
Read more >
Re: PowerMock : can i mock enums? - Google Groups
An enum will result in a corresponding final Java class, created by the compiler. Mocking an enum means mocking ... needs to call...
Read more >
Where should I put my enum classes?
The primary reasons to put a type into a class/struct is for template metaprogramming, or if the type is private to the class....
Read more >
Enum Statement - Visual Basic - Microsoft Learn
If you use enumerations, your code is less likely to fail if in the ... An enumeration declared at class, structure, module, or...
Read more >
Using Enums (Enumerations) In Javascript - < Soham Kamani />
For a basic implementation of enums, we can define an object to encapsulate the enum type, and assign a key for each enum...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found