SEBWIN-219: Implemented basic service operation.
This commit is contained in:
parent
7d5c6a1b0b
commit
ebc12934bf
22 changed files with 389 additions and 36 deletions
|
@ -15,6 +15,7 @@ namespace SafeExamBrowser.Configuration.Settings
|
|||
internal class Settings : ISettings
|
||||
{
|
||||
public ConfigurationMode ConfigurationMode { get; set; }
|
||||
public ServicePolicy ServicePolicy { get; set; }
|
||||
|
||||
public IBrowserSettings Browser { get; set; }
|
||||
public IKeyboardSettings Keyboard { get; set; }
|
||||
|
|
17
SafeExamBrowser.Contracts/Communication/IClientProxy.cs
Normal file
17
SafeExamBrowser.Contracts/Communication/IClientProxy.cs
Normal file
|
@ -0,0 +1,17 @@
|
|||
/*
|
||||
* Copyright (c) 2018 ETH Zürich, Educational Development and Technology (LET)
|
||||
*
|
||||
* 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 http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
using System;
|
||||
|
||||
namespace SafeExamBrowser.Contracts.Communication
|
||||
{
|
||||
public interface IClientProxy
|
||||
{
|
||||
bool Connect(Guid token);
|
||||
}
|
||||
}
|
|
@ -14,7 +14,7 @@ using SafeExamBrowser.Contracts.Communication.Responses;
|
|||
namespace SafeExamBrowser.Contracts.Communication
|
||||
{
|
||||
[ServiceContract(SessionMode = SessionMode.Required)]
|
||||
public interface ICommunicationHost
|
||||
public interface ICommunication
|
||||
{
|
||||
/// <summary>
|
||||
/// Initiates a connection to the host and must thus be called before any other opertion. To authenticate itself to the host, the
|
17
SafeExamBrowser.Contracts/Communication/IRuntimeProxy.cs
Normal file
17
SafeExamBrowser.Contracts/Communication/IRuntimeProxy.cs
Normal file
|
@ -0,0 +1,17 @@
|
|||
/*
|
||||
* Copyright (c) 2018 ETH Zürich, Educational Development and Technology (LET)
|
||||
*
|
||||
* 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 http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
using System;
|
||||
|
||||
namespace SafeExamBrowser.Contracts.Communication
|
||||
{
|
||||
public interface IRuntimeProxy
|
||||
{
|
||||
bool Connect(Guid token);
|
||||
}
|
||||
}
|
23
SafeExamBrowser.Contracts/Communication/IServiceProxy.cs
Normal file
23
SafeExamBrowser.Contracts/Communication/IServiceProxy.cs
Normal file
|
@ -0,0 +1,23 @@
|
|||
/*
|
||||
* Copyright (c) 2018 ETH Zürich, Educational Development and Technology (LET)
|
||||
*
|
||||
* 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 http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
namespace SafeExamBrowser.Contracts.Communication
|
||||
{
|
||||
public interface IServiceProxy
|
||||
{
|
||||
/// <summary>
|
||||
/// Tries to connect to the service host.
|
||||
/// </summary>
|
||||
bool Connect();
|
||||
|
||||
/// <summary>
|
||||
/// Disconnects from the service host.
|
||||
/// </summary>
|
||||
void Disconnect();
|
||||
}
|
||||
}
|
|
@ -7,11 +7,10 @@
|
|||
*/
|
||||
|
||||
using System;
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace SafeExamBrowser.Contracts.Communication.Messages
|
||||
{
|
||||
public interface IMessage : ISerializable
|
||||
public interface IMessage
|
||||
{
|
||||
/// <summary>
|
||||
/// The communication token needed for authentication with the host.
|
||||
|
|
|
@ -6,11 +6,9 @@
|
|||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
using System.Runtime.Serialization;
|
||||
|
||||
namespace SafeExamBrowser.Contracts.Communication.Responses
|
||||
{
|
||||
public interface IResponse : ISerializable
|
||||
public interface IResponse
|
||||
{
|
||||
}
|
||||
}
|
||||
|
|
|
@ -10,7 +10,16 @@ namespace SafeExamBrowser.Contracts.Configuration.Settings
|
|||
{
|
||||
public enum ConfigurationMode
|
||||
{
|
||||
/// <summary>
|
||||
/// In this mode, the application settings shall be used to configure the local client settings of a user. When running in this
|
||||
/// mode, the user has the possiblity to re-configure the application during runtime.
|
||||
/// </summary>
|
||||
ConfigureClient,
|
||||
|
||||
/// <summary>
|
||||
/// In this mode, the application settings shall only be used to start an exam. When running in this mode, the user cannot re-
|
||||
/// configure the application during runtime.
|
||||
/// </summary>
|
||||
Exam
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,6 +30,11 @@ namespace SafeExamBrowser.Contracts.Configuration.Settings
|
|||
/// </summary>
|
||||
IMouseSettings Mouse { get; }
|
||||
|
||||
/// <summary>
|
||||
/// The active service policy.
|
||||
/// </summary>
|
||||
ServicePolicy ServicePolicy { get; }
|
||||
|
||||
/// <summary>
|
||||
/// All taskbar-related settings.
|
||||
/// </summary>
|
||||
|
|
|
@ -0,0 +1,23 @@
|
|||
/*
|
||||
* Copyright (c) 2018 ETH Zürich, Educational Development and Technology (LET)
|
||||
*
|
||||
* 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 http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
namespace SafeExamBrowser.Contracts.Configuration.Settings
|
||||
{
|
||||
public enum ServicePolicy
|
||||
{
|
||||
/// <summary>
|
||||
/// The service component must be running. If it is not running, the user won't be able to start the application.
|
||||
/// </summary>
|
||||
Mandatory,
|
||||
|
||||
/// <summary>
|
||||
/// The service component is optional. If it is not running, all service-related actions are simply skipped.
|
||||
/// </summary>
|
||||
Optional
|
||||
}
|
||||
}
|
|
@ -25,10 +25,12 @@ namespace SafeExamBrowser.Contracts.I18n
|
|||
MessageBox_StartupErrorTitle,
|
||||
Notification_AboutTooltip,
|
||||
Notification_LogTooltip,
|
||||
SplashScreen_CloseServiceConnection,
|
||||
SplashScreen_EmptyClipboard,
|
||||
SplashScreen_InitializeBrowser,
|
||||
SplashScreen_InitializeConfiguration,
|
||||
SplashScreen_InitializeProcessMonitoring,
|
||||
SplashScreen_InitializeServiceConnection,
|
||||
SplashScreen_InitializeTaskbar,
|
||||
SplashScreen_InitializeWindowMonitoring,
|
||||
SplashScreen_InitializeWorkingArea,
|
||||
|
|
|
@ -55,7 +55,10 @@
|
|||
<ItemGroup>
|
||||
<Compile Include="Behaviour\IApplicationController.cs" />
|
||||
<Compile Include="Behaviour\IRuntimeController.cs" />
|
||||
<Compile Include="Communication\ICommunicationHost.cs" />
|
||||
<Compile Include="Communication\ICommunication.cs" />
|
||||
<Compile Include="Communication\IClientProxy.cs" />
|
||||
<Compile Include="Communication\IRuntimeProxy.cs" />
|
||||
<Compile Include="Communication\IServiceProxy.cs" />
|
||||
<Compile Include="Communication\Messages\IMessage.cs" />
|
||||
<Compile Include="Communication\Responses\IResponse.cs" />
|
||||
<Compile Include="Communication\Responses\IConnectResponse.cs" />
|
||||
|
@ -78,6 +81,7 @@
|
|||
<Compile Include="Behaviour\IStartupController.cs" />
|
||||
<Compile Include="Configuration\Settings\ISettingsRepository.cs" />
|
||||
<Compile Include="Configuration\Settings\ITaskbarSettings.cs" />
|
||||
<Compile Include="Configuration\Settings\ServicePolicy.cs" />
|
||||
<Compile Include="I18n\IText.cs" />
|
||||
<Compile Include="I18n\TextKey.cs" />
|
||||
<Compile Include="Logging\ILogContent.cs" />
|
||||
|
|
|
@ -15,30 +15,33 @@ using SafeExamBrowser.Contracts.Logging;
|
|||
|
||||
namespace SafeExamBrowser.Core.Communication
|
||||
{
|
||||
public class CommunicationHostProxy : ICommunicationHost
|
||||
public abstract class BaseProxy : ICommunication
|
||||
{
|
||||
private string address;
|
||||
private ILogger logger;
|
||||
private ICommunicationHost channel;
|
||||
private ICommunication channel;
|
||||
|
||||
public CommunicationHostProxy(ILogger logger, string address)
|
||||
protected Guid? CommunicationToken { get; private set; }
|
||||
protected ILogger Logger { get; private set; }
|
||||
|
||||
public BaseProxy(ILogger logger, string address)
|
||||
{
|
||||
this.address = address;
|
||||
this.logger = logger;
|
||||
this.Logger = logger;
|
||||
}
|
||||
|
||||
public IConnectResponse Connect(Guid? token = null)
|
||||
{
|
||||
var endpoint = new EndpointAddress(address);
|
||||
|
||||
channel = ChannelFactory<ICommunicationHost>.CreateChannel(new NetNamedPipeBinding(NetNamedPipeSecurityMode.Transport), endpoint);
|
||||
channel = ChannelFactory<ICommunication>.CreateChannel(new NetNamedPipeBinding(NetNamedPipeSecurityMode.Transport), endpoint);
|
||||
(channel as ICommunicationObject).Closed += CommunicationHostProxy_Closed;
|
||||
(channel as ICommunicationObject).Closing += CommunicationHostProxy_Closing;
|
||||
(channel as ICommunicationObject).Faulted += CommunicationHostProxy_Faulted;
|
||||
|
||||
var response = channel.Connect(token);
|
||||
|
||||
logger.Debug($"Tried to connect to {address}, connection was {(response.ConnectionEstablished ? "established" : "refused")}.");
|
||||
CommunicationToken = response.CommunicationToken;
|
||||
Logger.Debug($"Tried to connect to {address}, connection was {(response.ConnectionEstablished ? "established" : "refused")}.");
|
||||
|
||||
return response;
|
||||
}
|
||||
|
@ -48,7 +51,7 @@ namespace SafeExamBrowser.Core.Communication
|
|||
if (ChannelIsReady())
|
||||
{
|
||||
channel.Disconnect(message);
|
||||
logger.Debug($"Disconnected from {address}, transmitting {ToString(message)}.");
|
||||
Logger.Debug($"Disconnected from {address}, transmitting {ToString(message)}.");
|
||||
}
|
||||
|
||||
throw new CommunicationException($"Tried to disconnect from host, but channel was {GetChannelState()}!");
|
||||
|
@ -60,7 +63,7 @@ namespace SafeExamBrowser.Core.Communication
|
|||
{
|
||||
var response = channel.Send(message);
|
||||
|
||||
logger.Debug($"Sent {ToString(message)}, got {ToString(response)}.");
|
||||
Logger.Debug($"Sent {ToString(message)}, got {ToString(response)}.");
|
||||
|
||||
return response;
|
||||
}
|
||||
|
@ -68,6 +71,14 @@ namespace SafeExamBrowser.Core.Communication
|
|||
throw new CommunicationException($"Tried to send {ToString(message)}, but channel was {GetChannelState()}!");
|
||||
}
|
||||
|
||||
protected void FailIfNotConnected(string operationName)
|
||||
{
|
||||
if (!CommunicationToken.HasValue)
|
||||
{
|
||||
throw new InvalidOperationException($"Cannot perform '{operationName}' before being connected to endpoint!");
|
||||
}
|
||||
}
|
||||
|
||||
private bool ChannelIsReady()
|
||||
{
|
||||
return channel != null && (channel as ICommunicationObject).State == CommunicationState.Opened;
|
||||
|
@ -75,17 +86,17 @@ namespace SafeExamBrowser.Core.Communication
|
|||
|
||||
private void CommunicationHostProxy_Closed(object sender, EventArgs e)
|
||||
{
|
||||
logger.Debug("Communication channel has been closed.");
|
||||
Logger.Debug("Communication channel has been closed.");
|
||||
}
|
||||
|
||||
private void CommunicationHostProxy_Closing(object sender, EventArgs e)
|
||||
{
|
||||
logger.Debug("Communication channel is closing.");
|
||||
Logger.Debug("Communication channel is closing.");
|
||||
}
|
||||
|
||||
private void CommunicationHostProxy_Faulted(object sender, EventArgs e)
|
||||
{
|
||||
logger.Error("Communication channel has faulted!");
|
||||
Logger.Error("Communication channel has faulted!");
|
||||
}
|
||||
|
||||
private string GetChannelState()
|
19
SafeExamBrowser.Core/Communication/Messages/Message.cs
Normal file
19
SafeExamBrowser.Core/Communication/Messages/Message.cs
Normal file
|
@ -0,0 +1,19 @@
|
|||
/*
|
||||
* Copyright (c) 2018 ETH Zürich, Educational Development and Technology (LET)
|
||||
*
|
||||
* 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 http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using SafeExamBrowser.Contracts.Communication.Messages;
|
||||
|
||||
namespace SafeExamBrowser.Core.Communication.Messages
|
||||
{
|
||||
[Serializable]
|
||||
internal class Message : IMessage
|
||||
{
|
||||
public Guid CommunicationToken { get; set; }
|
||||
}
|
||||
}
|
34
SafeExamBrowser.Core/Communication/ServiceProxy.cs
Normal file
34
SafeExamBrowser.Core/Communication/ServiceProxy.cs
Normal file
|
@ -0,0 +1,34 @@
|
|||
/*
|
||||
* Copyright (c) 2018 ETH Zürich, Educational Development and Technology (LET)
|
||||
*
|
||||
* 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 http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using SafeExamBrowser.Contracts.Communication;
|
||||
using SafeExamBrowser.Contracts.Logging;
|
||||
using SafeExamBrowser.Core.Communication.Messages;
|
||||
|
||||
namespace SafeExamBrowser.Core.Communication
|
||||
{
|
||||
public class ServiceProxy : BaseProxy, IServiceProxy
|
||||
{
|
||||
public ServiceProxy(ILogger logger, string address) : base(logger, address)
|
||||
{
|
||||
}
|
||||
|
||||
public bool Connect()
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public void Disconnect()
|
||||
{
|
||||
FailIfNotConnected(nameof(Disconnect));
|
||||
|
||||
Disconnect(new Message { CommunicationToken = CommunicationToken.Value });
|
||||
}
|
||||
}
|
||||
}
|
|
@ -30,6 +30,9 @@
|
|||
<Entry key="Notification_LogTooltip">
|
||||
Application Log
|
||||
</Entry>
|
||||
<Entry key="SplashScreen_CloseServiceConnection">
|
||||
Closing service connection
|
||||
</Entry>
|
||||
<Entry key="SplashScreen_EmptyClipboard">
|
||||
Emptying clipboard
|
||||
</Entry>
|
||||
|
@ -42,6 +45,9 @@
|
|||
<Entry key="SplashScreen_InitializeProcessMonitoring">
|
||||
Initializing process monitoring
|
||||
</Entry>
|
||||
<Entry key="SplashScreen_InitializeServiceConnection">
|
||||
Initializing service connection
|
||||
</Entry>
|
||||
<Entry key="SplashScreen_InitializeTaskbar">
|
||||
Initializing taskbar
|
||||
</Entry>
|
||||
|
|
|
@ -58,7 +58,9 @@
|
|||
<Compile Include="Behaviour\Operations\I18nOperation.cs" />
|
||||
<Compile Include="Behaviour\ShutdownController.cs" />
|
||||
<Compile Include="Behaviour\StartupController.cs" />
|
||||
<Compile Include="Communication\CommunicationHostProxy.cs" />
|
||||
<Compile Include="Communication\BaseProxy.cs" />
|
||||
<Compile Include="Communication\Messages\Message.cs" />
|
||||
<Compile Include="Communication\ServiceProxy.cs" />
|
||||
<Compile Include="Logging\DefaultLogFormatter.cs" />
|
||||
<Compile Include="Logging\LogFileWriter.cs" />
|
||||
<Compile Include="Logging\LogMessage.cs" />
|
||||
|
@ -82,6 +84,8 @@
|
|||
<Name>SafeExamBrowser.Contracts</Name>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup />
|
||||
<ItemGroup>
|
||||
<Folder Include="Communication\Responses\" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
</Project>
|
|
@ -6,17 +6,151 @@
|
|||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||
using Moq;
|
||||
using SafeExamBrowser.Contracts.Communication;
|
||||
using SafeExamBrowser.Contracts.Configuration.Settings;
|
||||
using SafeExamBrowser.Contracts.I18n;
|
||||
using SafeExamBrowser.Contracts.Logging;
|
||||
using SafeExamBrowser.Contracts.UserInterface;
|
||||
using SafeExamBrowser.Runtime.Behaviour.Operations;
|
||||
|
||||
namespace SafeExamBrowser.Runtime.UnitTests.Behaviour.Operations
|
||||
{
|
||||
[TestClass]
|
||||
public class ServiceOperationTests
|
||||
{
|
||||
[TestMethod]
|
||||
public void Test()
|
||||
private Mock<ILogger> logger;
|
||||
private Mock<IServiceProxy> service;
|
||||
private Mock<ISettingsRepository> settings;
|
||||
private Mock<ISplashScreen> splashScreen;
|
||||
private Mock<IText> text;
|
||||
private ServiceOperation sut;
|
||||
|
||||
[TestInitialize]
|
||||
public void Initialize()
|
||||
{
|
||||
Assert.Fail();
|
||||
logger = new Mock<ILogger>();
|
||||
service = new Mock<IServiceProxy>();
|
||||
settings = new Mock<ISettingsRepository>();
|
||||
splashScreen = new Mock<ISplashScreen>();
|
||||
text = new Mock<IText>();
|
||||
|
||||
sut = new ServiceOperation(logger.Object, service.Object, settings.Object, text.Object)
|
||||
{
|
||||
SplashScreen = splashScreen.Object
|
||||
};
|
||||
}
|
||||
|
||||
[TestMethod]
|
||||
public void MustConnectToService()
|
||||
{
|
||||
service.Setup(s => s.Connect()).Returns(true);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Mandatory);
|
||||
|
||||
sut.Perform();
|
||||
|
||||
service.Setup(s => s.Connect()).Returns(true);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Optional);
|
||||
|
||||
sut.Perform();
|
||||
|
||||
service.Verify(s => s.Connect(), Times.Exactly(2));
|
||||
}
|
||||
|
||||
[TestMethod]
|
||||
public void MustNotFailIfServiceNotAvailable()
|
||||
{
|
||||
service.Setup(s => s.Connect()).Returns(false);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Mandatory);
|
||||
|
||||
sut.Perform();
|
||||
|
||||
service.Setup(s => s.Connect()).Returns(false);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Optional);
|
||||
|
||||
sut.Perform();
|
||||
|
||||
service.Setup(s => s.Connect()).Throws<Exception>();
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Mandatory);
|
||||
|
||||
sut.Perform();
|
||||
|
||||
service.Setup(s => s.Connect()).Throws<Exception>();
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Optional);
|
||||
|
||||
sut.Perform();
|
||||
}
|
||||
|
||||
[TestMethod]
|
||||
public void MustAbortIfServiceMandatoryAndNotAvailable()
|
||||
{
|
||||
service.Setup(s => s.Connect()).Returns(false);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Mandatory);
|
||||
|
||||
sut.Perform();
|
||||
|
||||
Assert.IsTrue(sut.AbortStartup);
|
||||
}
|
||||
|
||||
[TestMethod]
|
||||
public void MustNotAbortIfServiceOptionalAndNotAvailable()
|
||||
{
|
||||
service.Setup(s => s.Connect()).Returns(false);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Optional);
|
||||
|
||||
sut.Perform();
|
||||
|
||||
Assert.IsFalse(sut.AbortStartup);
|
||||
}
|
||||
|
||||
[TestMethod]
|
||||
public void MustDisconnectWhenReverting()
|
||||
{
|
||||
service.Setup(s => s.Connect()).Returns(true);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Mandatory);
|
||||
|
||||
sut.Perform();
|
||||
sut.Revert();
|
||||
|
||||
service.Setup(s => s.Connect()).Returns(true);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Optional);
|
||||
|
||||
sut.Perform();
|
||||
sut.Revert();
|
||||
|
||||
service.Verify(s => s.Disconnect(), Times.Exactly(2));
|
||||
}
|
||||
|
||||
[TestMethod]
|
||||
public void MustNotDisconnnectIfNotAvailable()
|
||||
{
|
||||
service.Setup(s => s.Connect()).Returns(false);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Mandatory);
|
||||
|
||||
sut.Perform();
|
||||
sut.Revert();
|
||||
|
||||
service.Setup(s => s.Connect()).Returns(false);
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Optional);
|
||||
|
||||
sut.Perform();
|
||||
sut.Revert();
|
||||
|
||||
service.Setup(s => s.Connect()).Throws<Exception>();
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Mandatory);
|
||||
|
||||
sut.Perform();
|
||||
sut.Revert();
|
||||
|
||||
service.Setup(s => s.Connect()).Throws<Exception>();
|
||||
settings.SetupGet(s => s.Current.ServicePolicy).Returns(ServicePolicy.Optional);
|
||||
|
||||
sut.Perform();
|
||||
sut.Revert();
|
||||
|
||||
service.Verify(s => s.Disconnect(), Times.Never);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -14,7 +14,7 @@ namespace SafeExamBrowser.Runtime.UnitTests.Behaviour
|
|||
public class RuntimeControllerTests
|
||||
{
|
||||
[TestMethod]
|
||||
public void Test()
|
||||
public void TODO()
|
||||
{
|
||||
Assert.Fail();
|
||||
}
|
||||
|
|
|
@ -6,9 +6,11 @@
|
|||
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using SafeExamBrowser.Contracts.Behaviour;
|
||||
using SafeExamBrowser.Contracts.Communication;
|
||||
using SafeExamBrowser.Contracts.Configuration.Settings;
|
||||
using SafeExamBrowser.Contracts.I18n;
|
||||
using SafeExamBrowser.Contracts.Logging;
|
||||
using SafeExamBrowser.Contracts.UserInterface;
|
||||
|
||||
|
@ -16,31 +18,76 @@ namespace SafeExamBrowser.Runtime.Behaviour.Operations
|
|||
{
|
||||
internal class ServiceOperation : IOperation
|
||||
{
|
||||
private ICommunicationHost serviceHost;
|
||||
private bool serviceAvailable;
|
||||
private bool serviceMandatory;
|
||||
private ILogger logger;
|
||||
private IServiceProxy service;
|
||||
private ISettingsRepository settingsRepository;
|
||||
private IText text;
|
||||
|
||||
public bool AbortStartup { get; private set; }
|
||||
public ISplashScreen SplashScreen { private get; set; }
|
||||
|
||||
public ServiceOperation(ICommunicationHost serviceHost, ILogger logger, ISettingsRepository settingsRepository)
|
||||
public ServiceOperation(ILogger logger, IServiceProxy service, ISettingsRepository settingsRepository, IText text)
|
||||
{
|
||||
this.serviceHost = serviceHost;
|
||||
this.service = service;
|
||||
this.logger = logger;
|
||||
this.settingsRepository = settingsRepository;
|
||||
this.text = text;
|
||||
}
|
||||
|
||||
public void Perform()
|
||||
{
|
||||
logger.Info("Initializing service connection...");
|
||||
// SplashScreen.UpdateText(...)
|
||||
logger.Info($"Initializing service connection...");
|
||||
SplashScreen.UpdateText(TextKey.SplashScreen_InitializeServiceConnection);
|
||||
|
||||
// TODO
|
||||
try
|
||||
{
|
||||
serviceMandatory = settingsRepository.Current.ServicePolicy == ServicePolicy.Mandatory;
|
||||
serviceAvailable = service.Connect();
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
var message = "Failed to connect to the service component!";
|
||||
|
||||
if (serviceMandatory)
|
||||
{
|
||||
logger.Error(message, e);
|
||||
}
|
||||
else
|
||||
{
|
||||
logger.Info($"{message} Reason: {e.Message}");
|
||||
}
|
||||
}
|
||||
|
||||
AbortStartup = serviceMandatory && !serviceAvailable;
|
||||
|
||||
if (AbortStartup)
|
||||
{
|
||||
logger.Info("Aborting startup because the service is mandatory but not available!");
|
||||
}
|
||||
else
|
||||
{
|
||||
logger.Info($"The service is {(serviceMandatory ? "mandatory" : "optional")} and {(!serviceAvailable ? "not" : "")} available.");
|
||||
}
|
||||
}
|
||||
|
||||
public void Revert()
|
||||
{
|
||||
// TODO
|
||||
logger.Info("Closing service connection...");
|
||||
SplashScreen.UpdateText(TextKey.SplashScreen_CloseServiceConnection);
|
||||
|
||||
if (serviceAvailable)
|
||||
{
|
||||
try
|
||||
{
|
||||
service.Disconnect();
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
logger.Error("Failed to disconnect from service component!", e);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,7 +17,7 @@ namespace SafeExamBrowser.Runtime.Behaviour
|
|||
{
|
||||
internal class RuntimeController : IRuntimeController
|
||||
{
|
||||
private ICommunicationHost serviceProxy;
|
||||
private ICommunication serviceProxy;
|
||||
private Queue<IOperation> operations;
|
||||
private ILogger logger;
|
||||
private ISettingsRepository settingsRepository;
|
||||
|
@ -27,7 +27,7 @@ namespace SafeExamBrowser.Runtime.Behaviour
|
|||
public ISettings Settings { private get; set; }
|
||||
|
||||
public RuntimeController(
|
||||
ICommunicationHost serviceProxy,
|
||||
ICommunication serviceProxy,
|
||||
ILogger logger,
|
||||
ISettingsRepository settingsRepository,
|
||||
IShutdownController shutdownController,
|
||||
|
|
|
@ -51,7 +51,7 @@ namespace SafeExamBrowser.Runtime
|
|||
InitializeLogging();
|
||||
|
||||
var text = new Text(logger);
|
||||
var serviceProxy = new CommunicationHostProxy(new ModuleLogger(logger, typeof(CommunicationHostProxy)), "net.pipe://localhost/safeexambrowser/service");
|
||||
var serviceProxy = new ServiceProxy(new ModuleLogger(logger, typeof(ServiceProxy)), "net.pipe://localhost/safeexambrowser/service");
|
||||
var shutdownController = new ShutdownController(logger, runtimeInfo, text, uiFactory);
|
||||
var startupController = new StartupController(logger, runtimeInfo, systemInfo, text, uiFactory);
|
||||
|
||||
|
@ -60,7 +60,7 @@ namespace SafeExamBrowser.Runtime
|
|||
StartupOperations = new Queue<IOperation>();
|
||||
StartupOperations.Enqueue(new I18nOperation(logger, text));
|
||||
StartupOperations.Enqueue(new ConfigurationOperation(logger, runtimeInfo, settingsRepository, text, uiFactory, args));
|
||||
StartupOperations.Enqueue(new ServiceOperation(serviceProxy, logger, settingsRepository));
|
||||
StartupOperations.Enqueue(new ServiceOperation(logger, serviceProxy, settingsRepository, text));
|
||||
//StartupOperations.Enqueue(new KioskModeOperation());
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue