2014-03-04 52 views
18

您好我是新来的Android Junit的测试:安卓:java.lang.SecurityException异常:注射到另一个应用程序需要INJECT_EVENTS许可

我已经写在MainActivityFunctionalTest.java一些测试代码文件

MainActivityFunctionalTest.java :

package com.example.myfirstapp2.test; 

public class MainActivityFunctionalTest extends ActivityInstrumentationTestCase2<Login>{ 

private static final String TAG = "MainActivityFunctionalTest"; 
private Login activity; 

    public MainActivityFunctionalTest() { 
    super(Login.class); 
    } 


    @Override 
    protected void setUp() throws Exception { 
    Log.d(TAG,"Set-Up"); 
    super.setUp(); 
    setActivityInitialTouchMode(false); 
    activity = getActivity(); 
    } 

    public void testStartSecondActivity() throws Exception { 
     // add monitor to check for the second activity 
     ActivityMonitor monitor = 
      getInstrumentation(). 
       addMonitor(DisplayMessageActivity.class.getName(), null, false); 
     //addMonitor(MainActivity.class.getName(), null, false); 
    // find button and click it 
     Button view = (Button) activity.findViewById(R.id.btnLogin); 

     // TouchUtils handles the sync with the main thread internally 
     TouchUtils.clickView(this, view); 

     // to click on a click, e.g., in a listview 
     // listView.getChildAt(0); 

     // wait 2 seconds for the start of the activity 
     DisplayMessageActivity startedActivity = (DisplayMessageActivity) 

    monitor 
      .waitForActivityWithTimeout(5000); 
     assertNotNull(startedActivity); 

     // search for the textView 
     TextView textView = (TextView) startedActivity.findViewById(R.id.Email); 

     // check that the TextView is on the screen 
     ViewAsserts.assertOnScreen(startedActivity.getWindow().getDecorView(), 
      textView); 
     // validate the text on the TextView 
     assertEquals("Text incorrect", "1http://www.vogella.com", 

     textView.getText().toString()); 

     // press back and click again 
     this.sendKeys(KeyEvent.KEYCODE_BACK); 

     TouchUtils.clickView(this, view); 

    } 


    } 

但是,我得到一个错误: java.lang.SecurityException异常:注射到另一个应用程序需要INJECT_EVENTS许可

在com.example.myfirstapp2.test.MainActivityFunctionalTest.testStartSecondActivity(MainActivityFunctionalTest.java:70)

TouchUtils.clickView(this, view); 

请帮

+0

INJECT_EVENTS权限将被添加到清单文件中。 –

+0

嗨,我已经这样做了,但它仍然不起作用 – user3238961

+1

http://stackoverflow.com/questions/5383401/android-inject-events-permission?rq=1看看这个链接 –

回答

7

我面临这个同样的问题我自己,这里是我发现了什么关于这个问题。

1)将INJECT_EVENTS权限添加到您的应用程序中,使Android Studio指出此权限“仅授予系统应用程序”。而且,对于manifest.permissions,Google's reference guide声明此权限“不适用于第三方应用程序”。

现在,很可能您的应用与我的一样,不是系统应用。因此添加此权限绝对不是一件好事,而且幸运的是不会适用于您的第三方项目。至少在Android Studio上开发时。

2)我可以看到,在你的setUp方法中,你调用了setActivityInitialTouchMode(false);正如Google's best practices for UI testing所指出的那样,在测试UI时,必须将触摸模式设置为true。否则,您的测试夹具将无法与UI元素交互。

3)还有一件事。这是一个模拟用户对应用程序的操作的自动化测试。如果我们与设备进行交互(真实或虚拟,无关紧要),我们很可能会让其他事情获得关注(即使在测试中的应用程序内部),然后会与触摸模式设置发生冲突,即setUp方法已经表演过。

最终,这就是发生在我身上的事情。我简单地通过不点击/触摸/与正在运行测试的设备交互来解决了我的问题。

6

这是因为您的设备被锁定/任何其他打开的对话框打开 /任何阻止测试点击按钮的能力。例如。如果电话被锁定 - 当测试尝试点击按钮时,它不能因为设备被锁定。

我在模拟器上遇到麻烦,因为它总是显示“启动器崩溃”。因此,无论何时尝试点击该按钮,都不会因为警报对话框打开。

总之。确保您的屏幕已解锁,并且没有消息框干扰测试,并且可以点击按钮。

-1

一些更多的方式来解决“注入到另一个应用程序需要INJECT_EVENTS许可”与TouchUtils发生......

EG。官方Android开发者网站显示:

// Stop the activity - The onDestroy() method should save the state of the Spinner 
mActivity.finish(); 

// Re-start the Activity - the onResume() method should restore the state of the Spinner 
mActivity = getActivity(); 

然而,如果在测试方法,这是由TouchUtils.clickView直接跟着这可能会导致错误:

// Stop the activity - The onDestroy() method should save the state of the Spinner 
mActivity.finish(); 

// Re-start the Activity - the onResume() method should restore the state of the Spinner 
mActivity = getActivity(); 

// Possible inject error! 
TouchUtils.clickView(this, someView); 

然而,拆分为两个测试方法并允许setUp()在中间运行似乎可以解决问题(注意,这是由方法名称在测试按字母顺序运行时由方法名称控制):

*在调用intent后仍然可能失败,但不会在完成之后更长的时间被称为

public void testYTestFinishing() { 

    TouchUtils.clickView(this, someView); 

    // Finish & restart the activity 
    activity.finish(); 
} 

// ------------------------------------------- 
// Called before every test case method 
@Override 
protected void setUp() throws Exception { 
    super.setUp(); 

    setActivityInitialTouchMode(true); 

    activity = getActivity(); 

    getViews(); 
} 
// ------------------------------------------- 

public void testZOnReturn() { 

    TouchUtils.clickView(this, someView); 

} 

有趣的是,把什么是在设置()之前TouchUtils既可以失败,并且工作:

public void testYTestFinishing() { 

    TouchUtils.clickView(this, someView); 

    // Finish & restart the activity 
    activity.finish(); 

    setActivityInitialTouchMode(true); 

    activity = getActivity(); 

    getViews(); 

    // SORRY, this fails here on some builds and succeeds on others 
    TouchUtils.clickView(this, someView); 
} 

您也可以在TouchUtils之前直接尝试waitForActivity超时可*修复它在其他时间如意图被调用后:

*注入错误仍然可能发生,如果在相同的测试方法中使用...将需要拆分成另一种方法,如上所示。

Instrumentation.ActivityMonitor monitor = getInstrumentation() 
     .addMonitor(Instrumentation.ActivityMonitor.class.getName(), 
     null, false); 

    // Wait for activity to fix inject error; Increase or decrease as needed 
    monitor.waitForActivityWithTimeout(2000); 

    // Should no longer fail 
    TouchUtils.clickView(this, someView); 
22

我有同样的问题,我的代码是这样的(用于正常登录活动):

onView(withId(R.id.username)) 
      .perform(new TypeTextAction("test_user")); 
    onView(withId(R.id.password)) 
      .perform(new TypeTextAction("test123")); 
    onView(withId(R.id.login)).perform(click()); 

最后一行与抛出:SecurityException崩溃。在最后一次文字输入后发现,键盘保持打开状态,因此下一次单击被认为是在不同的应用程序上。

要解决这个问题,我只需在打字后关闭键盘。我还必须添加一些睡眠以确保键盘已关闭,否则测试会偶尔中断。所以最终代码看起来像这样:

onView(withId(R.id.username)) 
      .perform(new TypeTextAction("test_user")); 
    onView(withId(R.id.password)) 
      .perform(new TypeTextAction("test123")).perform(closeSoftKeyboard()); 
    Thread.sleep(250); 
    onView(withId(R.id.login)).perform(click()); 

这工作得很好。

+0

这对我有用,似乎有道理。我觉得奇怪的是,这个问题只发生在运行API 25的模拟器上。也想要注意的是,从API 23(Marshmallow)'INJECT_EVENTS'权限[**已被删除**](https://developer.android.com/sdk/api_diff/23/changes.html)。 –

+0

对我来说,问题是浮在我想点击的视图上方的Facebook聊天头。这也是一种FAB,因此乍一看看起来很相似。 :-) – ferini

3

对于有根的设备,this file帮了我很多。 它具有:

Injector.pressBackButton(); 
Injector.pressHomeButton(); 
Injector.pressPowerButton(); 
Injector.showNotificationCenter(); 
Injector.swipeLeftRight(); 
Injector.swipeRightLeft(); 
Injector.touch(x, y); 
14

我有同样的问题,并添加closeSoftKeyboard()方法解决了对我来说。

onView(withId(R.id.view)).perform(typeText(text_to_be_typed), closeSoftKeyboard()); 
0

运行espresso测试时,我遇到了完全相同的问题和错误消息。当运行整个软件包时,其中一个总是失败,但是当我单独运行它时总会失败。有趣的是,这个问题发生,因为我已经在AndroidManifest.xml中添加以下行到我的活动之一:

android:windowSoftInputMode="stateHidden" 

提到的测试驶过:

android:windowSoftInputMode="stateUnchanged|adjustResize" 

删除或上述行更改为后运行整个包时。

相关问题