Skip to content
This repository has been archived by the owner on Apr 12, 2023. It is now read-only.

Commit

Permalink
Merge pull request #1165 from cocoa-mhlw/feature/survey-submit
Browse files Browse the repository at this point in the history
調査内容の送信を実装
  • Loading branch information
cocoa-dev004 authored Oct 5, 2022
2 parents 8ebfe84 + b4c4d1f commit 8c66897
Show file tree
Hide file tree
Showing 17 changed files with 509 additions and 17 deletions.
3 changes: 3 additions & 0 deletions Covid19Radar/Covid19Radar/App.xaml.cs
Original file line number Diff line number Diff line change
Expand Up @@ -251,6 +251,9 @@ private static void RegisterCommonTypes(IContainer container)
// Utilities
container.Register<IDateTimeUtility, DateTimeUtility>(Reuse.Singleton);
container.Register<IDeviceInfoUtility, DeviceInfoUtility>(Reuse.Singleton);

// End of service
container.Register<ISurveyService, SurveyService>(Reuse.Singleton);
}

protected override void OnStart()
Expand Down
25 changes: 25 additions & 0 deletions Covid19Radar/Covid19Radar/Model/SurveyContent.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at https://mozilla.org/MPL/2.0/.
using System;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;

namespace Covid19Radar.Model
{
public class SurveyContent
{
[JsonProperty("q1")]
public int Q1 { get; set; }

[JsonProperty("q2")]
public int Q2 { get; set; }

[JsonProperty("q3")]
public long Q3 { get; set; }

[JsonProperty("exposure_data")]
public SurveyExposureData ExposureData { get; set; }
}
}

23 changes: 23 additions & 0 deletions Covid19Radar/Covid19Radar/Model/SurveyExposureData.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at https://mozilla.org/MPL/2.0/.
using System;
using Chino;
using Newtonsoft.Json;
using System.Collections.Generic;

namespace Covid19Radar.Model
{
public class SurveyExposureData
{
[JsonProperty("en_version")]
public string EnVersion { get; set; }

[JsonProperty("daily_summaries")]
public List<DailySummary> DailySummaryList { get; set; }

[JsonProperty("exposure_windows")]
public List<ExposureWindow> ExposureWindowList { get; set; }
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ public enum SendEventLogState
public class EventType
{
public static readonly EventType ExposureNotified = new EventType("ExposureNotification", "ExposureNotified");
public static readonly EventType Survey = new EventType("survey", "survey");

public static readonly EventType[] All = new EventType[] {
ExposureNotified
Expand Down
8 changes: 8 additions & 0 deletions Covid19Radar/Covid19Radar/Services/DialogService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,14 @@ await AlertAsync(
AppResources.ButtonOk);
}

public async Task ShowNetworkConnectionErrorAsync()
{
await UserDialogs.Instance.AlertAsync(
Resources.AppResources.DialogNetworkConnectionError,
Resources.AppResources.DialogNetworkConnectionErrorTitle,
Resources.AppResources.ButtonOk);
}

public async Task<bool> ConfirmAsync(string message, string title = null, string okText = null, string cancelText = null) =>
await UserDialogs.Instance.ConfirmAsync(message, title, okText, cancelText);

Expand Down
9 changes: 8 additions & 1 deletion Covid19Radar/Covid19Radar/Services/EventLogService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,8 @@ namespace Covid19Radar.Services
{
public interface IEventLogService
{
public Task SendAllAsync(long maxSize, int maxRetry);
Task SendAllAsync(long maxSize, int maxRetry);
Task<bool> SendAsync(EventLog eventLog);
}

public class EventLogService : IEventLogService
Expand Down Expand Up @@ -184,5 +185,11 @@ private async Task<bool> SendAsync(string idempotencyKey, List<EventLog> eventLo
_loggerService.Error("Send event log failure");
return false;
}

public async Task<bool> SendAsync(EventLog eventLog)
{
string idempotencyKey = Guid.NewGuid().ToString();
return await SendAsync(idempotencyKey, new List<EventLog> { eventLog });
}
}
}
5 changes: 5 additions & 0 deletions Covid19Radar/Covid19Radar/Services/EventLogServiceNop.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,5 +15,10 @@ public Task SendAllAsync(long maxSize, int maxRetry)
// do nothing
return Task.FromResult(new List<EventLog>());
}

public Task<bool> SendAsync(EventLog eventLog)
{
return Task.FromResult(true);
}
}
}
1 change: 1 addition & 0 deletions Covid19Radar/Covid19Radar/Services/IDialogService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,5 +17,6 @@ public interface IDialogService
Task<bool> ShowLocalNotificationOffWarningAsync();
Task ShowUserProfileNotSupportAsync();
Task ShowEventLogSaveCompletedAsync();
Task ShowNetworkConnectionErrorAsync();
}
}
87 changes: 87 additions & 0 deletions Covid19Radar/Covid19Radar/Services/SurveyService.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at https://mozilla.org/MPL/2.0/.
using System;
using Chino;
using Covid19Radar.Model;
using System.Collections.Generic;
using System.Threading.Tasks;
using Covid19Radar.Repository;
using Newtonsoft.Json.Linq;

namespace Covid19Radar.Services
{
public interface ISurveyService
{
Task<SurveyContent> BuildSurveyContent(int q1, int q2, DateTime q3, bool isExposureDataProvision);
Task<bool> SubmitSurvey(SurveyContent surveyContent);
}

public class SurveyService : ISurveyService
{
private readonly IEventLogService _eventLogService;
private readonly IExposureDataRepository _exposureDataRepository;
private readonly AbsExposureNotificationApiService _exposureNotificationApiService;

public SurveyService(
IEventLogService eventLogService,
IExposureDataRepository exposureDataRepository,
AbsExposureNotificationApiService exposureNotificationApiService
)
{
_eventLogService = eventLogService;
_exposureDataRepository = exposureDataRepository;
_exposureNotificationApiService = exposureNotificationApiService;
}

public async Task<SurveyContent> BuildSurveyContent(int q1, int q2, DateTime q3, bool isExposureDataProvision)
{
var surveyContent = new SurveyContent
{
Q1 = q1,
Q2 = q2,
Q3 = q3.ToUnixEpoch(),
ExposureData = isExposureDataProvision ? await GetExopsureData() : null
};
return surveyContent;
}

private async Task<SurveyExposureData> GetExopsureData()
{
try
{
long enVersion = await _exposureNotificationApiService.GetVersionAsync();
List<DailySummary> dailySummaryList = await _exposureDataRepository.GetDailySummariesAsync();
List<ExposureWindow> exposureWindowList = await _exposureDataRepository.GetExposureWindowsAsync();

var exposureData = new SurveyExposureData
{
EnVersion = enVersion.ToString(),
DailySummaryList = dailySummaryList,
ExposureWindowList = exposureWindowList
};

return exposureData;
}
catch
{
return null;
}
}

public async Task<bool> SubmitSurvey(SurveyContent surveyContent)
{
var eventLog = new EventLog
{
HasConsent = true,
Epoch = DateTime.UtcNow.ToUnixEpoch(),
Type = EventType.Survey.Type,
Subtype = EventType.Survey.SubType,
Content = JObject.FromObject(surveyContent),
};

return await _eventLogService.SendAsync(eventLog);
}
}
}

Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,9 @@
using System.ComponentModel;
using System.Runtime.CompilerServices;
using Covid19Radar.Common;
using Covid19Radar.Model;
using Covid19Radar.Repository;
using Covid19Radar.Services;
using Covid19Radar.Services.Logs;
using Covid19Radar.Views.EndOfService;
using Prism.Navigation;
Expand Down Expand Up @@ -47,6 +49,20 @@ public int SelectedIndexQ2
}
}

private SurveyAnswerPickerItem _selectedItemQ1;
public SurveyAnswerPickerItem SelectedItemQ1
{
get => _selectedItemQ1;
set => SetProperty(ref _selectedItemQ1, value);
}

private SurveyAnswerPickerItem _selectedItemQ2;
public SurveyAnswerPickerItem SelectedItemQ2
{
get => _selectedItemQ2;
set => SetProperty(ref _selectedItemQ2, value);
}

private DateTime _q3Answer;
public DateTime Q3Answer
{
Expand All @@ -60,16 +76,26 @@ public DateTime Q3Answer
}
}

private bool _isExposureDataProvision;
public bool IsExposureDataProvision
{
get => _isExposureDataProvision;
set => SetProperty(ref _isExposureDataProvision, value);
}

public bool IsTerminationOfUsePageButtonEnabled
=> _selectedIndexQ1 > 0 && _selectedIndexQ2 > 0 && _q3Answer != null;

private readonly IUserDataRepository _userDataRepository;
private readonly ISurveyService _surveyService;

public SurveyPageViewModel(
INavigationService navigationService,
ISurveyService surveyService,
IUserDataRepository userDataRepository
) : base(navigationService)
{
_surveyService = surveyService;
_userDataRepository = userDataRepository;
}

Expand All @@ -83,11 +109,19 @@ public override void Initialize(INavigationParameters parameters)

DateTime startDate = _userDataRepository.GetStartDate();
Q3Answer = startDate.ToLocalTime();

IsExposureDataProvision = false;
}

public IAsyncCommand OnToTerminationOfUsePageButton => new AsyncCommand(async () =>
{
var navigationParameters = new NavigationParameters();
SurveyContent surveyContent = await _surveyService.BuildSurveyContent(
SelectedItemQ1.Value,
SelectedItemQ2.Value,
Q3Answer,
IsExposureDataProvision);
var navigationParameters = TerminationOfUsePage.BuildNavigationParams(surveyContent);
await NavigationService.NavigateAsync(nameof(TerminationOfUsePage), navigationParameters);
});
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
using System.Threading.Tasks;
using Acr.UserDialogs;
using Chino;
using Covid19Radar.Model;
using Covid19Radar.Repository;
using Covid19Radar.Resources;
using Covid19Radar.Services;
Expand All @@ -19,6 +20,9 @@ public class TerminationOfUsePageViewModel : ViewModelBase
{
private readonly ILoggerService _loggerService;
private readonly ILogFileService _logFileService;
private readonly ISurveyService _surveyService;
private readonly IDialogService _dialogService;

private readonly IUserDataRepository _userDataRepository;
private readonly IEventLogRepository _eventLogRepository;
private readonly ISendEventLogStateRepository _sendEventLogStateRepository;
Expand All @@ -29,10 +33,14 @@ public class TerminationOfUsePageViewModel : ViewModelBase
private readonly AbsExposureDetectionBackgroundService _absExposureDetectionBackgroundService;
private readonly AbsDataMaintainanceBackgroundService _absDataMaintainanceBackgroundService;

private SurveyContent _surveyContent = null;

public TerminationOfUsePageViewModel(
INavigationService navigationService,
ILoggerService loggerService,
ILogFileService logFileService,
ISurveyService surveyService,
IDialogService dialogService,
IUserDataRepository userDataRepository,
IEventLogRepository eventLogRepository,
ISendEventLogStateRepository sendEventLogStateRepository,
Expand All @@ -45,6 +53,9 @@ AbsDataMaintainanceBackgroundService absDataMaintainanceBackgroundService
{
_loggerService = loggerService;
_logFileService = logFileService;
_surveyService = surveyService;
_dialogService = dialogService;

_userDataRepository = userDataRepository;
_eventLogRepository = eventLogRepository;
_sendEventLogStateRepository = sendEventLogStateRepository;
Expand All @@ -56,11 +67,29 @@ AbsDataMaintainanceBackgroundService absDataMaintainanceBackgroundService
_absDataMaintainanceBackgroundService = absDataMaintainanceBackgroundService;
}

public override void Initialize(INavigationParameters parameters)
{
base.Initialize(parameters);

if (parameters.ContainsKey(TerminationOfUsePage.NavigationParameterNameSurveyContent))
{
_surveyContent = parameters.GetValue<SurveyContent>(TerminationOfUsePage.NavigationParameterNameSurveyContent);
}
}

public IAsyncCommand OnTerminationButton => new AsyncCommand(async () =>
{
UserDialogs.Instance.ShowLoading(AppResources.LoadingTextDeleting);
try
{
UserDialogs.Instance.ShowLoading(AppResources.LoadingTextDeleting);
// Submit survey content if needed
if (_surveyContent != null && !await _surveyService.SubmitSurvey(_surveyContent))
{
await _dialogService.ShowNetworkConnectionErrorAsync();
_loggerService.Error("Failed submit survey");
return;
}
// Stop exposure notifications
await StopExposureNotificationAsync();
Expand All @@ -84,16 +113,18 @@ AbsDataMaintainanceBackgroundService absDataMaintainanceBackgroundService
await _eventLogRepository.RemoveAllAsync();
_ = _logFileService.DeleteLogsDir();
UserDialogs.Instance.HideLoading();
// Navigate to complete page
await NavigationService.NavigateAsync($"/{nameof(TerminationOfUseCompletePage)}");
}
catch (Exception ex)
{
_loggerService.Exception("Failed termination of use", ex);
}
finally
{
UserDialogs.Instance.HideLoading();
}
// Navigate to complete page
await NavigationService.NavigateAsync($"/{nameof(TerminationOfUseCompletePage)}");
});

private async Task StopExposureNotificationAsync()
Expand Down
Loading

0 comments on commit 8c66897

Please sign in to comment.