Форум программистов, компьютерный форум, киберфорум
Наши страницы
Программирование Android
Войти
Регистрация
Восстановить пароль
 
 
S4nchez
4 / 4 / 1
Регистрация: 25.08.2015
Сообщений: 56
#1

Как приложение Вконтакте узнаёт о новом сообщении? - Программирование Android

27.09.2016, 16:40. Просмотров 1036. Ответов 37
Метки нет (Все метки)

Как реализовать подобную вещь:
как, например, приложение Вконтакте узнаёт о новом сообщение? Оно циклично посылает запрос на сервер с этой целью? Или для этого используется какое-то средство Андроида?
http://www.cyberforum.ru/android-dev/thread1451581.html
Как возможно это реализовать? Если я хочу в своём приложении встроить что-то типа "оповещения о новых событиях", а информацию о них выкладывать на своём сервере.

Просто, если циклично посылать запрос, то это и на батарею плохо влияет и на расход трафика.
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
Similar
Эксперт
41792 / 34177 / 6122
Регистрация: 12.04.2006
Сообщений: 57,940
27.09.2016, 16:40
Я подобрал для вас темы с готовыми решениями и ответами на вопрос Как приложение Вконтакте узнаёт о новом сообщении? (Программирование Android):

Приложение не может пройти авторизацию вконтакте
Такая вот проблема , приложение с авторизаций вконтакте на некоторых...

Одно приложение вконтакте работает, а второе нет
Создал одно приложение работает с контактом нормально. Создаю другое...

Как вызвать БД в новом activity
Нужно в новом классе вызвать БД. Нашел в интернете пример, но почему-то, при...

Как сделать оповещение о новом сообщении.
Здравствуйте подскажите пожалуйста как можно реализовать оповещение о новом...

Как отправить на e-mail сообщение о новом сообщении
Здравствуйте, Мне нужна помощь, я новичок в php, и ещё многого не знаю, но...

37
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
28.10.2016, 11:49 #21
А вот то-то и оно! Вы не пробовали делать запрос из сервиса к базе Firebase. А я -то думаю откуда такая бойкая уверенность. Мой сервис прекрасно работает в фоне, я как-бы тоже постиг дзен в этом плане. И запускать приложение при получении сообщения я тоже умею. Не работают запросы
нужно лишь послать запрос "окай, Firebase, на этом устройстве есть приложение которое хочет получать для пользователя *** с паролем *** уведомления при изменении данных ***
вот это действие не работает внутри сервиса.
Ладно, придется мне слать письма на email, чтобы хоть как-то уведомить что пора открывать приложение.
0
Pablito
2645 / 2127 / 726
Регистрация: 12.05.2014
Сообщений: 7,434
Завершенные тесты: 1
28.10.2016, 11:55 #22
я весь текст не осилил
можно очень коротко что надо сделать?

пока я понял следующее - есть телефон, надо что-то сделать что бы появилось уведомление, по клику на которое должна стартовать программа?
0
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
28.10.2016, 12:10 #23
Коротко задача такая. Юзер №1 создает список и выкладывает его в базу данных Firebase. Юзер №2 видит этот список и при желании добавляет себя в него. После этого выключает приложение, а еще лучше перезагружает устройство.
По прошествии какого-то времени Юзер №1 - создатель списка, видит, что его список пополнился участниками. Теперь он помечает галкой тех кому остаться в этом списке, а кому сказать "пока". Остается реализовать механизм оповещения всех участников списка, что же решил Юзер №1 в отношении конкретно его. То есть как Юзеру №2 получить уведомление при отключенном приложении?
0
korshun84
86 / 86 / 22
Регистрация: 08.07.2014
Сообщений: 502
28.10.2016, 12:13 #24
Цитата Сообщение от Bi-do-mi Посмотреть сообщение
Вы не пробовали делать запрос из сервиса к базе Firebase.
Немного упустил суть разговора, но если речь идет о приеме пуша на мобильном устройстве, то из вашего сервиса никакие запросы к "базе Firebase" делать не надо, надо в нем наследоваться от FirebaseMessagingService и он все будет делать сам.
Другой вопрос, что на некоторых реальных устройствах 5-6 версии андроида оно перестает работать, когда телефон спит, но это уже к теме не относится.
0
Pablito
2645 / 2127 / 726
Регистрация: 12.05.2014
Сообщений: 7,434
Завершенные тесты: 1
28.10.2016, 12:19 #25
мне кажется тут вообще можно обойтись без FCM, только подписаться на определенные "ветки" в firebase базе
0
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
28.10.2016, 12:22 #26
Нет, дело не в приеме пуша. Пуш принимать мы умеем. Вопрос в каком месте создать этот самый пуш автоматически при обновлении конкретных данных хранящихся в Firebase Database. Или как его запросить из фонового сервиса. Из консоли FCM писать уведомления вручную тоже умеем. Это не нужно.

Добавлено через 2 минуты
Подписка на ветки Firebase хорошо работает когда приложение запущено или в не на главном экране, но где-то живет. Будут ли работать подписки если вырубить приложение полностью? Мой практический опыт настойчиво утверждает, что нет.
0
Pablito
2645 / 2127 / 726
Регистрация: 12.05.2014
Сообщений: 7,434
Завершенные тесты: 1
28.10.2016, 12:25 #27
я такие выверты люблю, это тренирует
то есть задача такая - я должен в сервисе получить оповещение о том, что в базе изменилась информация, для простоты пусть это будет одна запись

чуть позже отпишусь как проверю
0
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
28.10.2016, 12:51 #28
Как решение, возникла еще одна идея. Раз уж сервис без запуска основного приложения не может получить данные из базы, нужно просто периодически запускать (если оно не запущено) с помощью сервиса само приложение в фоне. Хотя я не знаю есть ли такая возможность. Ну а приложение уже само сделает запрос в базу.
0
Pablito
2645 / 2127 / 726
Регистрация: 12.05.2014
Сообщений: 7,434
Завершенные тесты: 1
28.10.2016, 13:54 #29
у меня в одном небольшом приложении есть привязка к firebase databse, там при старте делается
Java
1
2
DatabaseReference reference = FirebaseDatabase.getInstance().getReference("Ololo_db_branch");
        reference.addValueEventListener(this);
так я просто создал сервис и вынес эти строки туда интерфейс реализовал в самом сервисе
так все работает нормально, я даже из recent apps смахиваю приложение и все равно работает сервис

то есть я в базе добавляю запись и тут же в логах вижу что срабатотал onDataChange

проверять с перезагрузкой не вижу смысла - там все тоже самое, главное стартануть сервис через бут ресивер

ps: щас пойду на обед и выключу экран телефона, посмотрим сработает ли onDataChange минут через 30

Добавлено через 35 минут
все по-прежнему работает, то есть листенер в сервисе сработал
0
shavuz
114 / 120 / 25
Регистрация: 29.01.2014
Сообщений: 596
28.10.2016, 14:37 #30
сервис может получать данные когда приложение не запущено, на то он и сервис. достаточно один раз запустить приложение. если этого не происходит то значит не правельно сделан сервис.
0
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
28.10.2016, 14:39 #31
У меня пока не получается. Может быть мой сервис умирает слишком быстро? Его надо создавать с флагом START_STICKY?
0
Pablito
2645 / 2127 / 726
Регистрация: 12.05.2014
Сообщений: 7,434
Завершенные тесты: 1
28.10.2016, 14:43 #32
может быть пришла пора показать код?
0
shavuz
114 / 120 / 25
Регистрация: 29.01.2014
Сообщений: 596
28.10.2016, 14:46 #33
конечно стики. и ресивер ему на бут тоже нужен.
0
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
28.10.2016, 14:49 #34
Вот
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
public class PollService extends IntentService {
    private static final String TAG = "PollService";
    private static final String EXTRA_MEETING = "meeting";
    private Meeting mMeeting;
 
 
    public static Intent newIntent(Context context) {
        return new Intent(context, PollService.class);
    }
 
    public PollService() {
        super(TAG);
    }
 
    @Override
    public void onCreate() {
        super.onCreate();
       
 
        DatabaseReference reference = FirebaseDatabase.getInstance().getReference("meetings");
        reference.addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                Log.d(TAG,"data updates");
                Uri defaultSoundUri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
                Notification notification = new NotificationCompat.Builder(PollService.this)
                        .setTicker("Бегущая строка")
                        .setSmallIcon(android.R.drawable.ic_menu_report_image)
                        .setContentTitle("OnCreate!")
                        .setContentText("FirebaseUser = null")
                        .setAutoCancel(true)
                        .setSound(defaultSoundUri)
                        .build();
                NotificationManagerCompat notificationManager =
                        NotificationManagerCompat.from(PollService.this);
                notificationManager.notify(0, notification);
            }
 
            @Override
            public void onCancelled(DatabaseError databaseError) {
 
            }
        });
    }
 
    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        Log.d(TAG,"onStartCommand");
        return super.onStartCommand(intent, flags, startId);
 
    }
 
    @Override
    public void onDestroy() {
        Log.d(TAG,"onDestroy");
        super.onDestroy();
    }
 
    @Override
    protected void onHandleIntent(Intent intent) {
        if (!isNetworkAvailableAndConnected()) {
            return;
        }
        Log.d(TAG, "onHandle");        
        mMeeting=intent.getParcelableExtra(EXTRA_MEETING);
        if (mMeeting.getEndDate()-System.currentTimeMillis()<0){
            MyPreferences.setStoredMeeting(getApplicationContext(),null);
            DatabaseReference databaseReference =
                    FirebaseDatabase.getInstance()
                            .getReference("meetings/" + mMeeting.getId());
            databaseReference.removeValue();
        }
    }
 
    private boolean isNetworkAvailableAndConnected() {
        ConnectivityManager cm =
                (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE);
        boolean isNetworkAvailable = cm.getActiveNetworkInfo() != null;
        boolean isNetworkConnected = isNetworkAvailable &&
                cm.getActiveNetworkInfo().isConnected();
        return isNetworkConnected;
    }
 
 
    public static void setCheckAlarm(Context context, boolean shouldDelete, Meeting meeting) {
        Intent i = PollService.newIntent(context);
        i.putExtra(EXTRA_MEETING, meeting);
        PendingIntent pi = PendingIntent.getService(context, 0, i, PendingIntent.FLAG_UPDATE_CURRENT);
        AlarmManager alarmManager = (AlarmManager) context.getSystemService(ALARM_SERVICE);
        if (!shouldDelete) {
            alarmManager.set(AlarmManager.ELAPSED_REALTIME_WAKEUP,
                    SystemClock.elapsedRealtime()+meeting.getEndDate()-System.currentTimeMillis(), pi);
        } else {
            alarmManager.cancel(pi);
            pi.cancel();
        }
    }
 
    public static boolean isServiceAlarmOn(Context context) {
        Intent i = PollService.newIntent(context);
        PendingIntent pi = PendingIntent
                .getService(context, 0, i, PendingIntent.FLAG_NO_CREATE);
        return pi == null;
    }
}
вызываю сервис так:
Java
1
2
Intent i=PollService.newIntent(getApplicationContext());
                        startService(i);
0
Pablito
2645 / 2127 / 726
Регистрация: 12.05.2014
Сообщений: 7,434
Завершенные тесты: 1
28.10.2016, 14:59 #35
а почему IntentService а не просто Service?
слушатель хотя бы раз отрабатывает?

при изменении данных должен вызываться onDataChange, а не onHandleIntent
0
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
28.10.2016, 16:14 #36
Я немного подредактировал код сервиса и его вызов
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
public class PollService extends IntentService {
    private static final String TAG = "PollService";
    public static final String EXTRA_MEETING = "meeting";
    private Meeting mMeeting;
 
 
    public static Intent newIntent(Context context) {
        return new Intent(context, PollService.class);
    }
 
    public PollService() {
        super(TAG);
    }
 
    @Override
    public void onCreate() {
        super.onCreate();
        Log.d(TAG,"onCreate");
 
    }
 
    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        Log.d(TAG,"onStartCommand");
        return super.onStartCommand(intent, flags, startId);
 
    }
 
    @Override
    public void onDestroy() {
        Log.d(TAG,"onDestroy");
        Uri defaultSoundUri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
        Notification notification = new NotificationCompat.Builder(PollService.this)
                .setTicker("Бегущая строка")
                .setSmallIcon(android.R.drawable.ic_menu_report_image)
                .setContentTitle("OnDestroy!")
                .setContentText("service destroyd")
                .setAutoCancel(true)
                .setSound(defaultSoundUri)
                .build();
        NotificationManagerCompat notificationManager =
                NotificationManagerCompat.from(PollService.this);
        notificationManager.notify(0, notification);
        super.onDestroy();
    }
 
    @Override
    protected void onHandleIntent(Intent intent) {
        if (!isNetworkAvailableAndConnected()) {
            return;
        }
        Log.d(TAG, "onHandle");
        mMeeting=intent.getParcelableExtra(EXTRA_MEETING);
        DatabaseReference reference = FirebaseDatabase.getInstance()
                .getReference("meetings/" + mMeeting.getId());
        reference.addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(DataSnapshot dataSnapshot) {
                Log.d(TAG,"data updates");
                Uri defaultSoundUri= RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
                Notification notification = new NotificationCompat.Builder(PollService.this)
                        .setTicker("Бегущая строка")
                        .setSmallIcon(android.R.drawable.ic_menu_report_image)
                        .setContentTitle("OnCreate!")
                        .setContentText("data updates message")
                        .setAutoCancel(true)
                        .setSound(defaultSoundUri)
                        .build();
                NotificationManagerCompat notificationManager =
                        NotificationManagerCompat.from(PollService.this);
                notificationManager.notify(0, notification);
            }
 
            @Override
            public void onCancelled(DatabaseError databaseError) {
 
            }
        });
        
    }
 
    private boolean isNetworkAvailableAndConnected() {
        ConnectivityManager cm =
                (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE);
        boolean isNetworkAvailable = cm.getActiveNetworkInfo() != null;
        boolean isNetworkConnected = isNetworkAvailable &&
                cm.getActiveNetworkInfo().isConnected();
        return isNetworkConnected;
    }
 
 
    public static void setCheckAlarm(Context context, boolean shouldDelete, Meeting meeting) {
        Intent i = PollService.newIntent(context);
        i.putExtra(EXTRA_MEETING, meeting);
        PendingIntent pi = PendingIntent.getService(context, 0, i, PendingIntent.FLAG_UPDATE_CURRENT);
        AlarmManager alarmManager = (AlarmManager) context.getSystemService(ALARM_SERVICE);
        if (!shouldDelete) {
            alarmManager.set(AlarmManager.ELAPSED_REALTIME_WAKEUP,
                    SystemClock.elapsedRealtime()+meeting.getEndDate()-System.currentTimeMillis(), pi);
        } else {
            alarmManager.cancel(pi);
            pi.cancel();
        }
    }
 
    public static boolean isServiceAlarmOn(Context context) {
        Intent i = PollService.newIntent(context);
        PendingIntent pi = PendingIntent
                .getService(context, 0, i, PendingIntent.FLAG_NO_CREATE);
        return pi == null;
    }
}
Вызов
Java
1
2
3
Intent i=PollService.newIntent(getApplicationContext());
                        i.putExtra(PollService.EXTRA_MEETING, mMeeting);
                        startService(i);
В логах видно, что сервис создается в следующем порядке (смотри ниже) и тут же уничтожается.
При этом на изменения в базе есть реакция (логи data updates). Это все при живом приложении. Если приложение уничтожить - реакция на изменения в базе пропадают.

10-28 13:02:33.441 30061-30061/com.android.teambuilder D/PollService: onCreate
10-28 13:02:33.468 30061-30061/com.android.teambuilder D/PollService: onStartCommand
10-28 13:02:33.479 30061-32253/com.android.teambuilder D/PollService: onHandle
10-28 13:02:49.693 30061-30061/com.android.teambuilder D/PollService: onDestroy
10-28 13:02:51.361 30061-30061/com.android.teambuilder D/PollService: data updates
10-28 13:04:06.590 30061-30061/com.android.teambuilder D/PollService: data updates

Добавлено через 1 минуту
IntentService рекомендуют использовать в книжке, тем боле, что он наследуется от Service.
0
Pablito
2645 / 2127 / 726
Регистрация: 12.05.2014
Сообщений: 7,434
Завершенные тесты: 1
28.10.2016, 16:17 #37
ну раз в книжке рекомендуют и раз он все равно наследуется от Service - ну ок
0
Bi-do-mi
3 / 3 / 0
Регистрация: 19.07.2016
Сообщений: 15
19.11.2016, 12:18 #38
В общем, решилось все путем возврата в onStartCommand старт стики. Сервис начинает жить и слушать базу данных. Но когда сервис умирает обязательно нужно отключать и слушатель, а то он у меня своей жизнью жил независимо от сервиса.
0
19.11.2016, 12:18
MoreAnswers
Эксперт
37091 / 29110 / 5898
Регистрация: 17.06.2006
Сообщений: 43,301
19.11.2016, 12:18
Привет! Вот еще темы с решениями:

Социальные сети: как на MVC 3 можно организовать быстрое уведмомление о новом сообщении
Мне в голову пришло несколько вариантов: 1) организовать запросы со страницы...

Оповещение о новом сообщении
Пытаюсь сделать систему оповещения о новых сообщениях. Пока сделано с помощью...

Уведомление о новом сообщении
Всем доброго времени суток! Никак не могу найти варианта где я бы мог видеть...

Событие о новом сообщении
Доброго времени суток. Разрабатываю сайт ms sql, linq c#, iis, ms. Общение с...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
38
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin® Version 3.8.9
Copyright ©2000 - 2018, vBulletin Solutions, Inc.
Рейтинг@Mail.ru