Я создал приложение (в соответствии с текущей архитектурой Android MVVM с использованием LiveData и Retrofit). Приложение служит в качестве пульта дистанционного управления для системы освещения и доступа.
Я создал класс Repository, который реализует сетевой бэкэнд с использованием Retrofit, который выполняет вызовы моего REST API. Когда я вручную запрашиваю (используя GET) обновление статуса, я могу получить статус своего ввода-вывода. Однако мне нужно использовать отправленные сервером события для тех же данных в другом URI для обновлений состояния ввода-вывода.
Кажется, Retrofit не поддерживает эту функцию. Я обнаружил другие API, которые, кажется, обрабатывают SSE, такие как EventSource, EventSource-Android, OkHttp-EventSource и Oksse. Это все разные реализации EventSource? Чем они функционально отличаются друг от друга?
Я учусь на чтении кода, написанного другими людьми; где я могу найти функциональные примеры того, как они реализованы? Результаты моего поиска не дают никаких полезных примеров. Есть ли рекомендуемые рекомендации по обработке событий, отправленных сервером?
Я действительно не хочу опрашивать мой сервер на предмет обновлений, и меня смущает, почему на Android мало поддержки SSE.
Для справки, вот некоторые из классов, которые я реализовал до сих пор.
Модель данных:
import org.simpleframework.xml.Element;
import org.simpleframework.xml.Root;
@Root(name = "onboardGpio", strict = false)
public class OnboardGPIO
{
@Element(name = "garageDoorFeedbackState")
private String garageDoorState;
@Element(name = "zoneOneState")
private String zoneOneState;
@Element(name = "zoneTwoState")
private String zoneTwoState;
@Element(name = "zoneThreeState")
private String zoneThreeState;
@Element(name = "systemArmedState")
private String systemArmed;
@Element(name = "panelTemperature")
private String panelTemperature;
@Element(name = "garageDoorRelayState")
private String garageDoorRelayState;
@Element(name = "zoneOneRelayState")
private String zoneOneRelayState;
@Element(name = "zoneTwoRelayState")
private String zoneTwoRelayState;
@Element(name = "zoneThreeRelayState")
private String zoneThreeRelayState;
...getters & setters...
}
Класс репозитория
import androidx.lifecycle.MutableLiveData;
import ca.thirdgear.homeautomation.http.HomeAutomationAPI;
import ca.thirdgear.homeautomation.http.HomeAutomationController;
import ca.thirdgear.homeautomation.model.OnboardGPIO;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
public class DataRepository
{
private static DataRepository dataRepository;
private HomeAutomationController homeAutomationController;
private HomeAutomationAPI homeAutomationAPIService;
private MutableLiveData<String> zoneOneState;
private MutableLiveData<String> zoneTwoState;
private MutableLiveData<String> garageDoorState;
public static DataRepository getInstance()
{
if(dataRepository == null)
{
dataRepository = new DataRepository();
}
return dataRepository;
}
private DataRepository()
{
homeAutomationController = HomeAutomationController.getInstance();
homeAutomationAPIService = homeAutomationController.createService(HomeAutomationAPI.class);
zoneOneState = new MutableLiveData<>();
zoneTwoState = new MutableLiveData<>();
garageDoorState = new MutableLiveData<>();
}
//get status of remote API I/O
public void getIoStatus()
{
Call<OnboardGPIO> call = homeAutomationAPIService.getIoStatus();
call.enqueue(new Callback<OnboardGPIO>() {
@Override
public void onResponse(Call<OnboardGPIO> call, Response<OnboardGPIO> response)
{
if(response.isSuccessful())
{
zoneOneState.setValue(response.body().getZoneOneState());
zoneTwoState.setValue(response.body().getZoneTwoState());
garageDoorState.setValue(response.body().getGarageDoorState());
}
}
@Override
public void onFailure(Call<OnboardGPIO> call, Throwable t)
{
//TODO
}
});
... other network calls ...
}
Сетевой класс
import okhttp3.Credentials;
import okhttp3.Interceptor;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import retrofit2.Retrofit;
import retrofit2.converter.simplexml.SimpleXmlConverterFactory;
import java.io.IOException;
import java.util.concurrent.TimeUnit;
@SuppressWarnings("deprecation")
public class HomeAutomationController
{
private static final String BASE_URL = "https://MY_URL/";
private static HomeAutomationController homeAutomationController;
private OkHttpClient okHttpClient;
private Retrofit retrofit;
public static HomeAutomationController getInstance()
{
if(homeAutomationController == null)
{
homeAutomationController = new HomeAutomationController();
}
return homeAutomationController;
}
private HomeAutomationController()
{
//create OkHttpClient
okHttpClient = new OkHttpClient().newBuilder().addInterceptor(new Interceptor() {
@Override
public okhttp3.Response intercept(Chain chain) throws IOException {
Request originalRequest = chain.request();
Request.Builder builder = originalRequest.newBuilder().header("Authorization",
Credentials.basic("USERNAME", "PASSWORD"));
Request newRequest = builder.build();
return chain.proceed(newRequest);
}
})
.readTimeout(0, TimeUnit.SECONDS)
.build();
//create retrofit object
retrofit = new Retrofit.Builder()
.baseUrl(BASE_URL)
.addConverterFactory(SimpleXmlConverterFactory.create())
.client(okHttpClient)
.build();
}
//create and return http service
public <S> S createService(Class <S> serviceClass)
{
return retrofit.create(serviceClass);
}
}