示例#1
0
        public async Task JoinRoom_DoNothing_HasSceneStack()
        {
            // arrange
            await Mediator.Send(new OpenConferenceRequest(ConferenceId));

            // act
            await JoinParticipant(TestData.Sven);

            // assert
            var scenes = SynchronizedObjectListener.GetSynchronizedObject <SynchronizedScene>(TestData.Sven.Participant,
                                                                                              SynchronizedScene.SyncObjId(DefaultRoomId));

            Assert.Equal(SynchronizedSceneProvider.GetDefaultScene(), scenes.SelectedScene);
            Assert.Equal(DefaultSceneStack, scenes.SceneStack);
            Assert.Null(scenes.OverwrittenContent);
            Assert.NotNull(scenes.AvailableScenes);
        }
示例#2
0
        private async Task ApplyScene(string conferenceId, string roomId, ActiveScene scene, SceneState currentState)
        {
            var sceneState = await CreateNewSceneState(conferenceId, roomId, scene, currentState);

            await _sceneRepository.SetSceneState(conferenceId, roomId, sceneState);

            // optimistic concurrency

            // very important, we need to know the current state AFTER we saved the new state in repository
            await _mediator.Send(new ClearCacheRequest());

            var availableScenes =
                await _mediator.Send(new FetchAvailableScenesRequest(conferenceId, roomId, sceneState.SceneStack));

            if (!VerifySceneState(sceneState, availableScenes))
            {
                // something wrong with the applied scenes, we have to adjust here
                if (scene.OverwrittenContent != null && !availableScenes.Contains(scene.OverwrittenContent))
                {
                    scene = scene with {
                        OverwrittenContent = null
                    };
                }

                if (!availableScenes.Contains(scene.SelectedScene))
                {
                    scene = scene with
                    {
                        SelectedScene      = scene.OverwrittenContent ?? SynchronizedSceneProvider.GetDefaultScene(),
                        OverwrittenContent = null,
                    };
                }

                if (_recursionCounter++ > 10)
                {
                    var safeSceneStack = sceneState.SceneStack.TakeWhile(availableScenes.Contains).ToList();
                    await _sceneRepository.SetSceneState(conferenceId, roomId,
                                                         sceneState with {
                        SceneStack = safeSceneStack
                    });
示例#3
0
        public async Task <Unit> Handle(UpdateScenesRequest request, CancellationToken cancellationToken)
        {
            var(conferenceId, roomId) = request;

            await using (await _sceneRepository.LockScene(conferenceId, roomId))
            {
                var scene = await _sceneRepository.GetScene(conferenceId, roomId);

                scene ??= SynchronizedSceneProvider.GetDefaultActiveScene();

                var state = await _sceneRepository.GetSceneState(conferenceId, roomId);

                state ??= SynchronizedSceneProvider.GetEmptySceneState();

                await ApplyScene(conferenceId, roomId, scene, state);
            }

            await _mediator.Send(
                new UpdateSynchronizedObjectRequest(conferenceId, SynchronizedScene.SyncObjId(roomId)));

            return(Unit.Value);
        }
示例#4
0
        public async ValueTask Handle(string conferenceId, string roomId, Func <ActiveScene, ActiveScene> patchFunc)
        {
            await using (await _sceneRepository.LockScene(conferenceId, roomId))
            {
                var previousScene = await _sceneRepository.GetScene(conferenceId, roomId);

                previousScene ??= SynchronizedSceneProvider.GetDefaultActiveScene();

                await _sceneRepository.SetScene(conferenceId, roomId, patchFunc(previousScene));
            }

            // for optimistic concurrency
            await _mediator.Send(new ClearCacheRequest());

            if (!await IsRoomExisting(conferenceId, roomId))
            {
                await _sceneRepository.RemoveScene(conferenceId, roomId);

                throw SceneError.RoomNotFound.ToException();
            }

            await _mediator.Send(new UpdateScenesRequest(conferenceId, roomId));
        }