2022-06-20 20:10:25 +00:00
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence.
// See the LICENCE file in the repository root for full licence text.
2023-02-03 17:38:42 +00:00
using System.IO ;
2022-06-20 20:10:25 +00:00
using System.Linq ;
using NUnit.Framework ;
using osu.Framework ;
using osu.Framework.Allocation ;
using osu.Framework.Extensions ;
using osu.Framework.Graphics.Containers ;
using osu.Framework.Platform ;
using osu.Framework.Testing ;
using osu.Game.IPC ;
using osu.Game.Online.API ;
using osu.Game.Online.API.Requests ;
using osu.Game.Online.API.Requests.Responses ;
using osu.Game.Overlays ;
2023-02-03 17:38:42 +00:00
using osu.Game.Overlays.Notifications ;
using osu.Game.Tests.Resources ;
2022-06-20 20:10:25 +00:00
namespace osu.Game.Tests.Visual.Navigation
{
[TestFixture]
[Ignore("This test cannot be run headless, as it requires the game host running the nested game to have IPC bound.")]
public partial class TestSceneInterProcessCommunication : OsuGameTestScene
{
private HeadlessGameHost ipcSenderHost = null ! ;
private OsuSchemeLinkIPCChannel osuSchemeLinkIPCSender = null ! ;
2023-02-03 17:38:42 +00:00
private ArchiveImportIPCChannel archiveImportIPCSender = null ! ;
2022-06-20 20:10:25 +00:00
private const int requested_beatmap_set_id = 1 ;
2023-02-03 17:22:51 +00:00
protected override TestOsuGame CreateTestGame ( ) = > new IpcGame ( LocalStorage , API ) ;
2022-06-20 20:10:25 +00:00
[Resolved]
private GameHost gameHost { get ; set ; } = null ! ;
public override void SetUpSteps ( )
{
base . SetUpSteps ( ) ;
AddStep ( "set up request handling" , ( ) = >
{
( ( DummyAPIAccess ) API ) . HandleRequest = request = >
{
switch ( request )
{
case GetBeatmapSetRequest gbr :
var apiBeatmapSet = CreateAPIBeatmapSet ( ) ;
apiBeatmapSet . OnlineID = requested_beatmap_set_id ;
apiBeatmapSet . Beatmaps = apiBeatmapSet . Beatmaps . Append ( new APIBeatmap
{
DifficultyName = "Target difficulty" ,
OnlineID = 75 ,
} ) . ToArray ( ) ;
gbr . TriggerSuccess ( apiBeatmapSet ) ;
return true ;
}
return false ;
} ;
} ) ;
2023-02-03 17:38:42 +00:00
AddStep ( "create IPC sender channels" , ( ) = >
2022-06-20 20:10:25 +00:00
{
2024-01-18 10:45:35 +00:00
ipcSenderHost = new HeadlessGameHost ( gameHost . Name , new HostOptions { IPCPort = OsuGame . IPC_PORT } ) ;
2022-06-20 20:10:25 +00:00
osuSchemeLinkIPCSender = new OsuSchemeLinkIPCChannel ( ipcSenderHost ) ;
2023-02-03 17:38:42 +00:00
archiveImportIPCSender = new ArchiveImportIPCChannel ( ipcSenderHost ) ;
2022-06-20 20:10:25 +00:00
} ) ;
}
[Test]
public void TestOsuSchemeLinkIPCChannel ( )
{
AddStep ( "open beatmap via IPC" , ( ) = > osuSchemeLinkIPCSender . HandleLinkAsync ( $@"osu://s/{requested_beatmap_set_id}" ) . WaitSafely ( ) ) ;
AddUntilStep ( "beatmap overlay displayed" , ( ) = > Game . ChildrenOfType < BeatmapSetOverlay > ( ) . FirstOrDefault ( ) ? . State . Value = = Visibility . Visible ) ;
AddUntilStep ( "beatmap overlay showing content" , ( ) = > Game . ChildrenOfType < BeatmapSetOverlay > ( ) . FirstOrDefault ( ) ? . Header . BeatmapSet . Value . OnlineID = = requested_beatmap_set_id ) ;
}
2023-02-03 17:38:42 +00:00
[Test]
public void TestArchiveImportLinkIPCChannel ( )
{
string? beatmapFilepath = null ;
AddStep ( "import beatmap via IPC" , ( ) = > archiveImportIPCSender . ImportAsync ( beatmapFilepath = TestResources . GetQuickTestBeatmapForImport ( ) ) . WaitSafely ( ) ) ;
AddUntilStep ( "import complete notification was presented" , ( ) = > Game . Notifications . ChildrenOfType < ProgressCompletionNotification > ( ) . Count ( ) , ( ) = > Is . EqualTo ( 1 ) ) ;
AddAssert ( "original file deleted" , ( ) = > File . Exists ( beatmapFilepath ) , ( ) = > Is . False ) ;
}
2022-06-20 20:10:25 +00:00
public override void TearDownSteps ( )
{
2023-02-03 17:38:42 +00:00
AddStep ( "dispose IPC senders" , ( ) = >
2022-06-20 20:10:25 +00:00
{
2022-06-21 05:08:30 +00:00
osuSchemeLinkIPCSender . Dispose ( ) ;
2023-02-03 17:38:42 +00:00
archiveImportIPCSender . Dispose ( ) ;
2022-06-20 20:10:25 +00:00
ipcSenderHost . Dispose ( ) ;
} ) ;
base . TearDownSteps ( ) ;
}
2023-02-03 17:22:51 +00:00
private partial class IpcGame : TestOsuGame
{
private OsuSchemeLinkIPCChannel ? osuSchemeLinkIPCChannel ;
2023-02-03 17:38:42 +00:00
private ArchiveImportIPCChannel ? archiveImportIPCChannel ;
2023-02-03 17:22:51 +00:00
public IpcGame ( Storage storage , IAPIProvider api , string [ ] ? args = null )
: base ( storage , api , args )
{
}
protected override void LoadComplete ( )
{
base . LoadComplete ( ) ;
osuSchemeLinkIPCChannel = new OsuSchemeLinkIPCChannel ( Host , this ) ;
2023-02-03 17:38:42 +00:00
archiveImportIPCChannel = new ArchiveImportIPCChannel ( Host , this ) ;
2023-02-03 17:22:51 +00:00
}
protected override void Dispose ( bool isDisposing )
{
base . Dispose ( isDisposing ) ;
osuSchemeLinkIPCChannel ? . Dispose ( ) ;
2023-02-03 17:38:42 +00:00
archiveImportIPCChannel ? . Dispose ( ) ;
2023-02-03 17:22:51 +00:00
}
}
2022-06-20 20:10:25 +00:00
}
}