2012-07-05 43 views
8

我正在試圖構建一個應用程序,其中我的應用程序在後臺運行,並檢測用戶何時啓動另一個應用程序,以便可以控制其上的流程。 爲了說明我的查詢,我想指定一個例子。 我的應用程序在後臺運行(稱爲服務),並且用戶剛剛點擊應用程序'XYZ'。我的應用有可能檢測到應用「XYZ」已啓動? 不僅僅是檢測'XYZ的活動是否已經到達前臺,我想要檢測'XYZ'是否已經啓動。說有人推出'Whatsapp Messenger',我想知道我的應用程序是否可以知道'Whatsapp Messenger'已經啓動。如何檢測用戶何時啓動另一個應用程序? (Android)

編輯:很多人認爲我試圖構建惡意軟件,但我不是。我正在嘗試爲高中項目構建一個應用程序。我想要一個統計數據來看看我的相機多長時間用作心理項目的一部分。 :/

在此先感謝, Sumit。

+0

你爲什麼要這麼做實現的?引用「**,以便我可以控制其上的流量**」這聽起來可能。 – t0mm13b 2012-07-05 14:43:42

+0

我正在嘗試構建一個高中項目的應用程序。沒有惡意軟件。 :( – 2012-07-05 14:54:37

+0

http://stackoverflow.com/questions/3290936/android-detect-when-other-apps-are-launched – SMR 2014-05-17 05:14:39

回答

1

我想你應該看看Google Play中的「應用程序保護器」應用程序。他們發現用戶啓動了另一個應用程序這是通過讀取系統日誌完成的。嘗試在設備上啓動任何應用程序後打開LogCat並閱讀日誌。你會感到驚訝。

你應該去哪裏?我想你應該嘗試aLogCat的應用程序。它是綠色和開源的。這將幫助您實際讀取日誌。儘管如此,所有這些都被認爲是Android中的安全漏洞。

+0

可能的副本是否屬實Google會阻止API級別16以上的日誌讀取? – gonzobrains 2013-05-01 00:09:23

+1

@gonzobrains我已經猜到了,你可以閱讀只有你自己的pid發佈的日誌 – 2013-05-01 13:50:07

+0

@gonzobrains是的,我阻止了api 16以上。m也可以找到應用午餐的sorce代碼,你能幫我嗎 – 2013-06-27 12:54:12

3

是的,您可以通過跟蹤Logcat找到啓動的應用程序。正在追蹤ActivityManager標記與info -I日誌。

從adb shell命令是,

adb logcat ActivityManager:I *:S 

從應用程序代碼,

logcat ActivityManager:I *:S 

而且在logcat中,你可以找到一個線類似,

I/ActivityManager( 585): Starting activity: Intent { action=android.intent.action...} 

當任何應用程序將推出。

這是logcat的輸出,顯示該消息涉及到優先級「I」和標籤「ActivityManager」:

更新:

只是在你的應用程序的清單文件中添加權限,

android.permission.READ_LOGS 
+2

一般警告:這種方法(我在GS3上見證過的)中的一些更新的手機不再將包/活動放到這個日誌語句中,如果你對性能沒有興趣,你可以繼續輪詢ActivityManager.getRecentTasts()以知道何時 – FoamyGuy 2012-07-05 15:55:25

+0

將無法​​在JellyBean +中使用。READ_LOGS權限現僅保留給系統應用程序使用。 – 2016-08-04 08:56:00

-2

在我的書中,通過您提出問題的方式,這聽起來像是以某種方式讓您的服務以惡意軟件jinx爲邊界控制的應用程序。但它在Android中不起作用 - 由於每個應用程序的權限不同,它很簡單和簡單。從而,每個應用程序都相互隔離。因此,直接回答你的問題,其號碼

正如其他答案建議 - 你可以監視logcat,但..然後再...爲什麼?

+0

就這一部分而言的公共API,我沒有理由不這樣做。 – 2012-07-05 14:48:08

+0

@Mighter詢問OP爲什麼要控制服務中的應用程序?確定它是公共API的一部分,並且「你看不到沒有理由不這樣做」,對,如果我發現那個應用程序正在這樣做 - 一個字 - 卸載*。 – t0mm13b 2012-07-05 14:49:50

+0

當然,他想建立一個惡意軟件。 – 2012-07-05 14:50:34

8

不知道這是爲了做到這一點,最好的方式,但它的工作原理,你可以使用logcat,並期待在其輸出端,您可以使用此權限

android.permission.READ_LOGS 

,並使用下面的代碼:

try 
{ 
    Process mLogcatProc = null; 
    BufferedReader reader = null; 
    mLogcatProc = Runtime.getRuntime().exec(new String[]{"logcat", "-d"}); 

    reader = new BufferedReader(new InputStreamReader(mLogcatProc.getInputStream())); 

    String line; 
    final StringBuilder log = new StringBuilder(); 
    String separator = System.getProperty("line.separator"); 

    while ((line = reader.readLine()) != null) 
    { 
     log.append(line); 
     log.append(separator); 
    } 
    String w = log.toString(); 
    Toast.makeText(getApplicationContext(),w, Toast.LENGTH_LONG).show(); 
} 
catch (Exception e) 
{ 
    Toast.makeText(getApplicationContext(), e.getMessage(), Toast.LENGTH_LONG).show(); 
} 

,不要忘記它的Android清單許可,您可以將此代碼添加到一個線程,它的工作

+0

非常感謝您的幫助。我不太瞭解代碼,但我會弄清楚,但是最後一部分是什麼意思:「將此代碼添加到線程中」?你的意思是一個ASyncTask或類似的東西嗎?我希望我的應用程序能夠作爲服務工作,因此,在任何給定的時間,如果應用程序啓動,它都可以檢測到。 – 2012-07-05 15:05:54

+0

你可以使用一個普通的線程來做到這一點,如果你想讓你的應用程序作爲一個服務來運行,只需要將該線程放入服務中,然後將上面的代碼放入線程中...將線程添加到服務中的一個示例可以在這裏看到:http://stackoverflow.com/questions/4178682/how-to-start-a-new-thread-in-a-service – 2012-07-05 15:09:44

+0

謝謝一噸。我會盡力實施它並讓你知道結果。 – 2012-07-10 13:18:31

1

我已經可以檢測,如果服務其他應用程序啓動。我爲撥號程序製作了它。同樣可以被任何包名取代。

@Override 
public int onStartCommand(Intent intent, int flags, int startId){ 
    Toast.makeText(this,"Service Started", Toast.LENGTH_LONG).show(); 

    final String str = ""; 
    Timer timer = new Timer(); 
    timer.scheduleAtFixedRate(new TimerTask() { 
     int phonelaunched = 0,phoneclosed =0; 
     int phonelaunches = 1; 
     @Override 
     public void run() { 
      ActivityManager am = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE); 
      List<ActivityManager.RunningAppProcessInfo> runningAppProcessInfo = am.getRunningAppProcesses(); 

      for (ActivityManager.RunningAppProcessInfo appProcess: runningAppProcessInfo) { 
       Log.d(appProcess.processName.toString(),"is running"); 
       if (appProcess.processName.equals("com.android.dialer")) { 
        if (appProcess.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND /*isForeground(getApplicationContext(),runningAppProcessInfo.get(i).processName)*/){ 
         if (phonelaunched == 0){ 
          phonelaunched = 1; 
          Log.d(str,"dude phone has been launched"); 
         } 
         else if (phoneclosed == 1){ 
          phonelaunches++; 
          phoneclosed = 0; 
          Log.d(String.valueOf(phonelaunches),"dude that was counter"); 
         } 
        } 
        else { 
         phoneclosed = 1; 
         Log.d(str,"dude phone has been closed"); 

        } 
       } 
      } 
     } 
    },2000,3000); 

    return START_STICKY; 
} 

這裏我會經歷所有正在運行的任務,並檢查它是否是我們的預期應用程序。如果是這樣,我檢查應用程序是否爲前景,並且應用程序永遠不會使用'phonelaunched'變量啓動。當預期的應用程序在後臺並且相應地設置變量時使用phoneclosed。

這一切都是服務

+1

這段代碼不會在android L上運行了。改爲使用'android.app.usage'包。 https://developer.android.com/reference/android/app/usage/package-summary.html – 2015-09-06 13:33:21

+0

但我不得不把它寫在下面運行棒棒糖設備。我們可以在下面的棒棒糖設備中直接使用android.app.usage嗎? – 2015-09-06 16:54:41

相關問題