2012-05-02 28 views
24

Tôi đang làm việc trên một ứng dụng sẽ chuyển tiếp thông tin về vị trí của nó đến một máy chủ từ xa. Tôi có ý định làm điều đó bằng cách thực hiện một bài đăng HTTP đơn giản tới máy chủ web và tất cả đều đơn giản và tốt.Android - Dịch vụ nền định kỳ - Lời khuyên

Nhưng theo thông số kỹ thuật, ứng dụng cần phải tự thực thi theo thời gian, cho phép nói một lần trong mỗi 30 phút. Hãy độc lập với giao diện, có nghĩa là nó cần chạy ngay cả khi ứng dụng bị đóng.

Tôi đã xem xét và phát hiện ra rằng Dịch vụ Android là những gì cần được sử dụng. Tôi có thể sử dụng những gì để thực hiện một hệ thống như vậy. Dịch vụ (hoặc cơ chế khác) có khởi động lại khi điện thoại khởi động lại không?

Xin cảm ơn trước.

Trả lời

28

Tạo Service để gửi thông tin của bạn đến máy chủ. Có lẽ, bạn đã có quyền kiểm soát.

Service của bạn phải được bắt đầu bằng báo thức được kích hoạt bởi AlarmManager, nơi bạn có thể chỉ định khoảng thời gian. Trừ khi bạn phải báo cáo dữ liệu của mình chính xác cứ 30 phút một lần, bạn có thể muốn báo động không chính xác để có thể tiết kiệm pin.

Cuối cùng, bạn có thể đăng ký ứng dụng của bạn để có được phát sóng khởi động bằng cách thiết lập một BroadcastReceiver như vậy:

public class BootReceiver extends BroadcastReceiver { 
    @Override 
    public void onReceive(Context context, Intent intent) { 
     if (intent.getAction().equals(Intent.ACTION_BOOT_COMPLETED)) { 
      // Register your reporting alarms here.    
     } 
    } 
} 

Bạn sẽ cần thêm quyền sau đây để AndroidManifest.xml của bạn cho rằng để làm việc. Đừng quên đăng ký báo thức của bạn khi bạn chạy ứng dụng bình thường, hoặc chúng sẽ chỉ được đăng ký khi thiết bị khởi động.

<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/> 
0

Bạn có thể sử dụng Alarm Manager để khởi động Dịch vụ tại thời gian được chỉ định và sau đó lặp lại báo thức trong khoảng thời gian được chỉ định. Khi báo thức diễn ra, bạn có thể bắt đầu dịch vụ và kết nối với máy chủ và thực hiện những gì bạn muốn

6

Bạn nên sắp xếp dịch vụ của bạn với người quản lý báo động, đầu tiên tạo ra các ý định chờ giải quyết của dịch vụ:

Intent ii = new Intent(getApplicationContext(), MyService.class); 
PendingIntent pii = PendingIntent.getService(getApplicationContext(), 2222, ii, 
PendingIntent.FLAG_CANCEL_CURRENT); 

Sau đó sắp xếp nó sử dụng quản lý báo động:

//getting current time and add 5 seconds to it 
Calendar cal = Calendar.getInstance(); 
cal.add(Calendar.SECOND, 5); 
//registering our pending intent with alarmmanager 
AlarmManager am = (AlarmManager) getSystemService(ALARM_SERVICE); 
am.set(AlarmManager.RTC_WAKEUP,cal.getTimeInMillis(), pi); 

này sẽ khởi chạy dịch vụ của bạn sau 5 giây của thời gian hiện tại. Bạn có thể lặp lại báo thức của mình.

+0

lẽ dễ dàng hơn để làm điều gì đó như 'hệ thống .currentTimeMillis() + TIMEOUT_MS' hơn so với 'Lịch', để có được độ trễ ban đầu của bạn. –

+4

Các bạn biết rằng bạn có các giá trị tĩnh trong AlarmManager trong 1 ngày, 12 giờ, 1 giờ, nửa na giờ và 15 phút? 'public static thức INTERVAL_DAY' dài ' public static thức INTERVAL_FIFTEEN_MINUTES' dài 'public static thức dài INTERVAL_HALF_DAY' ' public static thức INTERVAL_HALF_HOUR' dài 'public static thức dài INTERVAL_HOUR' – DaMachk

11

Đây là cách bán khác nhau để giữ cho dịch vụ luôn hoạt động. Có cách để giết nó trong mã nếu bạn muốn muốn

Dịch vụ Bối cảnh:

package com.ex.ample; 

import android.app.Service; 
import android.content.*; 
import android.os.*; 
import android.widget.Toast; 

public class BackgroundService extends Service { 

    public Context context = this; 
    public Handler handler = null; 
    public static Runnable runnable = null; 

    @Override 
    public IBinder onBind(Intent intent) { 
     return null; 
    } 

    @Override 
    public void onCreate() { 
     Toast.makeText(this, "Service created!", Toast.LENGTH_LONG).show(); 

     handler = new Handler(); 
     runnable = new Runnable() { 
      public void run() { 
       Toast.makeText(context, "Service is still running", Toast.LENGTH_LONG).show(); 
       handler.postDelayed(runnable, 10000); 
      } 
     }; 

     handler.postDelayed(runnable, 15000); 
    } 

    @Override 
    public void onDestroy() { 
     /* IF YOU WANT THIS SERVICE KILLED WITH THE APP THEN UNCOMMENT THE FOLLOWING LINE */ 
     //handler.removeCallbacks(runnable); 
     Toast.makeText(this, "Service stopped", Toast.LENGTH_LONG).show(); 
    } 

    @Override 
    public void onStart(Intent intent, int startid) { 
     Toast.makeText(this, "Service started by user.", Toast.LENGTH_LONG).show(); 
    } 
} 

Đây là cách bạn bắt đầu nó từ hoạt động chính của bạn hoặc bất cứ nơi nào bạn muốn:

startService(new Intent(this, BackgroundService.class)); 

onDestroy() sẽ được gọi khi ứng dụng bị đóng hoặc bị giết nhưng runnable chỉ khởi động nó ngay lập tức.

Tôi hy vọng điều này sẽ giúp ai đó ra ngoài.

Lý do tại sao một số người làm điều này là bởi vì các ứng dụng doanh nghiệp mà trong một số trường hợp người sử dụng/người lao động không phải có khả năng ngăn chặn những điều nào đó :)

http://i.imgur.com/1vCnYJW.png

+1

đẹp khắc phục, nhưng điều này sẽ tiếp tục khởi động xử lý sau một thời gian, vì dịch vụ sẽ bắt đầu lại sau một thời gian. – Dev

+1

Để ngăn việc khởi động lại, hãy chuyển mã từ onCreate() sang @Override int công khai trênStartCommand (Intent intent, int flags, int startId) { // mã cho runnable return START_NOT_STICKY; } trả lại START_NOT_STICKY sẽ đảm bảo rằng dịch vụ sẽ không khởi động lại và trình xử lý của bạn sẽ vẫn bị dừng sau khi onDestroyed(). – Dev

+1

Đừng quên thêm dịch vụ vào 'AndroidManifest.xml': ''. –

Các vấn đề liên quan