Android单元测试,从资源中获取字符串getString

33

我正在尝试为Android应用程序进行单元测试,我需要从res.string资源中获取一个字符串。我想要测试的类是一个POJO类。由于我正在使用两种语言编写应用程序,因此需要从资源中获取一个字符串。问题是我无法获取上下文或活动,这可能吗?我知道可以通过Instrumentation测试来实现,但我需要在进行仪器测试(黑盒测试)之前测试一些函数(白盒测试)。

public void setDiaByText(String textView) {
    getll_diaSeleccionado().clear();
    if (textView.contains(context.getResources().getString(R.string.sInicialLunes))) {
        getll_diaSeleccionado().add(0);
        getIsSelectedArray()[0] = true;
        getI_idiaSeleccionado()[0] =1;

    } else
    {
        getIsSelectedArray()[0] = false;
        getI_idiaSeleccionado()[0] =0;
    }
}

这是测试内容:

@Test
public void setDiaByTextView() {
    String texto = "L,M,X,J,V,S,D";

    alertaPOJO.setDiaByText(texto);

    assertEquals(alertaPOJO.getIsSelectedArray()[0], true);
    assertEquals(alertaPOJO.getI_idiaSeleccionado()[0], 1);
}

尝试执行 context.getResources().getString(R.string.sInicialLunes)) 时出现崩溃。

如果我将其替换为'Mon'或'L',它可以完美运行,所以有可能获取上下文或活动以便访问资源文件夹吗?

我正在使用Mockito进行测试,setUp函数如下:

@Before
public void setUp() throws Exception {

    MockitoAnnotations.initMocks(this);
    mContext = Mockito.mock(Alerta.class);
    Mockito.when(mContext.getApplicationContext()).thenReturn(mContext);

    alertaPOJO = new AlertaPOJO();
}

谢谢

4个回答

23
如果您仅使用Context获取String资源,我建议只模拟像这样的getResources().getString()部分(请参阅JUnit4符号):
@RunWith(MockitoJUnitRunner.class)
public class AlertaPOJOTest {

  @Mock
  Context mMockContext;

  @Test
  public void setDiaByTextView() {
     String texto = "L,M,X,J,V,S,D";
     when(mMockContext.getString(R.string.sInicialLunes))
       .thenReturn(INITIAL_LUNES);


     alertaPOJO.setDiaByText(texto);

     assertEquals(alertaPOJO.getIsSelectedArray()[0], true);
     assertEquals(alertaPOJO.getI_idiaSeleccionado()[0], 1);
   } 
}

有许多原因选择使用JVM测试,其中最重要的原因是它们运行速度更快。


由于以下原因引发异常: Caused by: io.mockk.proxy.MockKAgentException: 无法为类java.lang.String创建代理。 class java.lang.String是排除的类之一。 - tinto mathew
@tintomathew,关于MockK,请看下面我的回答。 - CoolMind

11

未经测试:使用下面的内容,可能会同时针对目标上下文吗?

android {
   testOptions {
     unitTests {
        includeAndroidResources = true
     }
  }
}

5

在使用JVM单元测试时,您没有真正的Android上下文。对于您的情况,也许您可以尝试使用Android Instrumentation测试,通常它是在项目的“androidTest”目录中实现的。


谢谢@Sherlock,我猜这是正确的答案,因为我已经阅读过了,但由于我是Android的初学者,我需要确认一下。 - Huan

1
如果您使用MockK,那么它是一样的。
@RunWith(AndroidJUnit4::class)
class YourClassUnitTest : TestCase() {

    @MockK
    private lateinit var resources: Resources

    @Before
    public override fun setUp() {
        MockKAnnotations.init(this)
    }

    @Test
    fun test() {
        every {
            resources.getQuantityString(R.plurals.age, YEARS, YEARS)
        } returns AGE
        every {
            resources.getString(
                R.string.surname,
                SURNAME
            )
        } returns TITLE

        // Assume you test this method that returns data class 
        // (fields are calculated with getQuantityString and getString)
        val data = getData(YEARS, SURNAME)

        assertEquals(AGE, data.age)
        assertEquals(TITLE, data.title)
    }

    companion object {
        const val YEARS = 10
        const val AGE = "$YEARS years"
        const val SURNAME = "Johns"
        const val TITLE = "Mr. $SURNAME"
    }
}

参见 Skip a parameter in MockK unit test, Kotlin,获取任何数据的字符串资源结果。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接