diff options
10 files changed, 81 insertions, 59 deletions
diff --git a/.ci/azure-pipelines-api-client.yml b/.ci/azure-pipelines-api-client.yml index 7f428aec1..d120593ea 100644 --- a/.ci/azure-pipelines-api-client.yml +++ b/.ci/azure-pipelines-api-client.yml @@ -34,7 +34,7 @@ jobs: displayName: 'Build unstable typescript axios client' condition: startsWith(variables['Build.SourceBranch'], 'refs/heads/master') inputs: - script: 'bash ./apiclient/templates/typescript/axios/unstable.sh' + script: "bash ./apiclient/templates/typescript/axios/generate.sh $(System.ArtifactsDirectory) $(Build.BuildNumber)" - task: Npm@1 displayName: 'Publish unstable typescript axios client' @@ -50,7 +50,7 @@ jobs: displayName: 'Build stable typescript axios client' condition: startsWith(variables['Build.SourceBranch'], 'refs/tags/v') inputs: - script: 'bash ./apiclient/templates/typescript/axios/stable.sh' + script: "bash ./apiclient/templates/typescript/axios/generate.sh $(System.ArtifactsDirectory)" - task: Npm@1 displayName: 'Publish stable typescript axios client' diff --git a/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteTranscodeFileTask.cs b/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteTranscodeFileTask.cs index 691408167..26ef19354 100644 --- a/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteTranscodeFileTask.cs +++ b/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteTranscodeFileTask.cs @@ -148,7 +148,7 @@ namespace Emby.Server.Implementations.ScheduledTasks.Tasks public bool IsHidden => false; /// <inheritdoc /> - public bool IsEnabled => false; + public bool IsEnabled => true; /// <inheritdoc /> public bool IsLogged => true; diff --git a/Emby.Server.Implementations/SyncPlay/SyncPlayController.cs b/Emby.Server.Implementations/SyncPlay/SyncPlayController.cs index 80b977731..538479512 100644 --- a/Emby.Server.Implementations/SyncPlay/SyncPlayController.cs +++ b/Emby.Server.Implementations/SyncPlay/SyncPlayController.cs @@ -301,8 +301,7 @@ namespace Emby.Server.Implementations.SyncPlay if (_group.IsPaused) { // Pick a suitable time that accounts for latency - var delay = _group.GetHighestPing() * 2; - delay = delay < _group.DefaultPing ? _group.DefaultPing : delay; + var delay = Math.Max(_group.GetHighestPing() * 2, GroupInfo.DefaultPing); // Unpause group and set starting point in future // Clients will start playback at LastActivity (datetime) from PositionTicks (playback position) @@ -452,8 +451,7 @@ namespace Emby.Server.Implementations.SyncPlay else { // Client, that was buffering, resumed playback but did not update others in time - delay = _group.GetHighestPing() * 2; - delay = delay < _group.DefaultPing ? _group.DefaultPing : delay; + delay = Math.Max(_group.GetHighestPing() * 2, GroupInfo.DefaultPing); _group.LastActivity = currentTime.AddMilliseconds( delay); @@ -497,7 +495,7 @@ namespace Emby.Server.Implementations.SyncPlay private void HandlePingUpdateRequest(SessionInfo session, PlaybackRequest request) { // Collected pings are used to account for network latency when unpausing playback - _group.UpdatePing(session, request.Ping ?? _group.DefaultPing); + _group.UpdatePing(session, request.Ping ?? GroupInfo.DefaultPing); } /// <inheritdoc /> diff --git a/Jellyfin.Server.Implementations/Migrations/20201004171403_AddMaxActiveSessions.cs b/Jellyfin.Server.Implementations/Migrations/20201004171403_AddMaxActiveSessions.cs index 8fded7d0a..10acb4def 100644 --- a/Jellyfin.Server.Implementations/Migrations/20201004171403_AddMaxActiveSessions.cs +++ b/Jellyfin.Server.Implementations/Migrations/20201004171403_AddMaxActiveSessions.cs @@ -13,7 +13,8 @@ namespace Jellyfin.Server.Implementations.Migrations name: "MaxActiveSessions", schema: "jellyfin", table: "Users", - nullable: true); + nullable: false, + defaultValue: 0); } protected override void Down(MigrationBuilder migrationBuilder) diff --git a/Jellyfin.Server.Implementations/Migrations/JellyfinDbModelSnapshot.cs b/Jellyfin.Server.Implementations/Migrations/JellyfinDbModelSnapshot.cs index 3c9e1aee4..16d62f482 100644 --- a/Jellyfin.Server.Implementations/Migrations/JellyfinDbModelSnapshot.cs +++ b/Jellyfin.Server.Implementations/Migrations/JellyfinDbModelSnapshot.cs @@ -344,7 +344,7 @@ namespace Jellyfin.Server.Implementations.Migrations b.Property<int?>("LoginAttemptsBeforeLockout") .HasColumnType("INTEGER"); - b.Property<int?>("MaxActiveSessions") + b.Property<int>("MaxActiveSessions") .HasColumnType("INTEGER"); b.Property<int?>("MaxParentalAgeRating") diff --git a/MediaBrowser.Controller/SyncPlay/GroupInfo.cs b/MediaBrowser.Controller/SyncPlay/GroupInfo.cs index e742df517..a1cada25c 100644 --- a/MediaBrowser.Controller/SyncPlay/GroupInfo.cs +++ b/MediaBrowser.Controller/SyncPlay/GroupInfo.cs @@ -14,12 +14,12 @@ namespace MediaBrowser.Controller.SyncPlay public class GroupInfo { /// <summary> - /// Gets the default ping value used for sessions. + /// The default ping value used for sessions. /// </summary> - public long DefaultPing { get; } = 500; + public const long DefaultPing = 500; /// <summary> - /// Gets or sets the group identifier. + /// Gets the group identifier. /// </summary> /// <value>The group identifier.</value> public Guid GroupId { get; } = Guid.NewGuid(); @@ -58,7 +58,8 @@ namespace MediaBrowser.Controller.SyncPlay /// <summary> /// Checks if a session is in this group. /// </summary> - /// <value><c>true</c> if the session is in this group; <c>false</c> otherwise.</value> + /// <param name="sessionId">The session id to check.</param> + /// <returns><c>true</c> if the session is in this group; <c>false</c> otherwise.</returns> public bool ContainsSession(string sessionId) { return Participants.ContainsKey(sessionId); @@ -70,16 +71,14 @@ namespace MediaBrowser.Controller.SyncPlay /// <param name="session">The session.</param> public void AddSession(SessionInfo session) { - if (ContainsSession(session.Id)) - { - return; - } - - var member = new GroupMember(); - member.Session = session; - member.Ping = DefaultPing; - member.IsBuffering = false; - Participants[session.Id] = member; + Participants.TryAdd( + session.Id, + new GroupMember + { + Session = session, + Ping = DefaultPing, + IsBuffering = false + }); } /// <summary> @@ -88,12 +87,7 @@ namespace MediaBrowser.Controller.SyncPlay /// <param name="session">The session.</param> public void RemoveSession(SessionInfo session) { - if (!ContainsSession(session.Id)) - { - return; - } - - Participants.Remove(session.Id, out _); + Participants.Remove(session.Id); } /// <summary> @@ -103,18 +97,16 @@ namespace MediaBrowser.Controller.SyncPlay /// <param name="ping">The ping.</param> public void UpdatePing(SessionInfo session, long ping) { - if (!ContainsSession(session.Id)) + if (Participants.TryGetValue(session.Id, out GroupMember value)) { - return; + value.Ping = ping; } - - Participants[session.Id].Ping = ping; } /// <summary> /// Gets the highest ping in the group. /// </summary> - /// <value name="session">The highest ping in the group.</value> + /// <returns>The highest ping in the group.</returns> public long GetHighestPing() { long max = long.MinValue; @@ -133,18 +125,16 @@ namespace MediaBrowser.Controller.SyncPlay /// <param name="isBuffering">The state.</param> public void SetBuffering(SessionInfo session, bool isBuffering) { - if (!ContainsSession(session.Id)) + if (Participants.TryGetValue(session.Id, out GroupMember value)) { - return; + value.IsBuffering = isBuffering; } - - Participants[session.Id].IsBuffering = isBuffering; } /// <summary> /// Gets the group buffering state. /// </summary> - /// <value><c>true</c> if there is a session buffering in the group; <c>false</c> otherwise.</value> + /// <returns><c>true</c> if there is a session buffering in the group; <c>false</c> otherwise.</returns> public bool IsBuffering() { foreach (var session in Participants.Values) @@ -161,7 +151,7 @@ namespace MediaBrowser.Controller.SyncPlay /// <summary> /// Checks if the group is empty. /// </summary> - /// <value><c>true</c> if the group is empty; <c>false</c> otherwise.</value> + /// <returns><c>true</c> if the group is empty; <c>false</c> otherwise.</returns> public bool IsEmpty() { return Participants.Count == 0; diff --git a/apiclient/templates/typescript/axios/generate.sh b/apiclient/templates/typescript/axios/generate.sh new file mode 100644 index 000000000..111b71b82 --- /dev/null +++ b/apiclient/templates/typescript/axios/generate.sh @@ -0,0 +1,19 @@ +#!/bin/bash + +artifactsDirectory="${1}" +buildNumber="${2}" +if [[ -n ${buildNumber} ]]; then + # Unstable build + additionalProperties=",snapshotVersion=\"-SNAPSHOT.${buildNumber}\",npmRepository=\"https://pkgs.dev.azure.com/jellyfin-project/jellyfin/_packaging/unstable/npm/registry/\"" +else + # Stable build + additionalProperties="" +fi + +java -jar openapi-generator-cli.jar generate \ + --input-spec ${artifactsDirectory}/openapispec/openapi.json \ + --generator-name typescript-axios \ + --output ./apiclient/generated/typescript/axios \ + --template-dir ./apiclient/templates/typescript/axios \ + --ignore-file-override ./apiclient/.openapi-generator-ignore \ + --additional-properties=useSingleRequestParameter="true",withSeparateModelsAndApi="true",modelPackage="models",apiPackage="api",npmName="axios"${additionalProperties} diff --git a/apiclient/templates/typescript/axios/stable.sh b/apiclient/templates/typescript/axios/stable.sh deleted file mode 100644 index 118ef219f..000000000 --- a/apiclient/templates/typescript/axios/stable.sh +++ /dev/null @@ -1,9 +0,0 @@ -#!/bin/bash - -java -jar openapi-generator-cli.jar generate \ - --input-spec $(System.ArtifactsDirectory)/openapispec/openapi.json \ - --generator-name typescript-axios \ - --output ./apiclient/generated/typescript/axios \ - --template-dir ./apiclient/templates/typescript/axios \ - --ignore-file-override ./apiclient/.openapi-generator-ignore \ - --additional-properties=useSingleRequestParameter="true",withSeparateModelsAndApi="true",npmName="axios" diff --git a/apiclient/templates/typescript/axios/unstable.sh b/apiclient/templates/typescript/axios/unstable.sh deleted file mode 100644 index be9f9be43..000000000 --- a/apiclient/templates/typescript/axios/unstable.sh +++ /dev/null @@ -1,9 +0,0 @@ -#!/bin/bash - -java -jar openapi-generator-cli.jar generate \ - --input-spec $(System.ArtifactsDirectory)/openapispec/openapi.json \ - --generator-name typescript-axios \ - --output ./apiclient/generated/typescript/axios \ - --template-dir ./apiclient/templates/typescript/axios \ - --ignore-file-override ./apiclient/.openapi-generator-ignore \ - --additional-properties=useSingleRequestParameter="true",withSeparateModelsAndApi="true",npmName="axios",snapshotVersion="-SNAPSHOT.$(Build.BuildNumber)",npmRepository="https://pkgs.dev.azure.com/jellyfin-project/jellyfin/_packaging/unstable/npm/registry/" diff --git a/tests/Jellyfin.Common.Tests/Json/JsonGuidConverterTests.cs b/tests/Jellyfin.Common.Tests/Json/JsonGuidConverterTests.cs new file mode 100644 index 000000000..d9e66d677 --- /dev/null +++ b/tests/Jellyfin.Common.Tests/Json/JsonGuidConverterTests.cs @@ -0,0 +1,32 @@ +using System; +using System.Text.Json; +using MediaBrowser.Common.Json.Converters; +using Xunit; + +namespace Jellyfin.Common.Tests.Extensions +{ + public static class JsonGuidConverterTests + { + [Fact] + public static void Deserialize_Valid_Success() + { + var options = new JsonSerializerOptions(); + options.Converters.Add(new JsonGuidConverter()); + Guid value = JsonSerializer.Deserialize<Guid>(@"""a852a27afe324084ae66db579ee3ee18""", options); + Assert.Equal(new Guid("a852a27afe324084ae66db579ee3ee18"), value); + + value = JsonSerializer.Deserialize<Guid>(@"""e9b2dcaa-529c-426e-9433-5e9981f27f2e""", options); + Assert.Equal(new Guid("e9b2dcaa-529c-426e-9433-5e9981f27f2e"), value); + } + + [Fact] + public static void Roundtrip_Valid_Success() + { + var options = new JsonSerializerOptions(); + options.Converters.Add(new JsonGuidConverter()); + Guid guid = new Guid("a852a27afe324084ae66db579ee3ee18"); + string value = JsonSerializer.Serialize(guid, options); + Assert.Equal(guid, JsonSerializer.Deserialize<Guid>(value, options)); + } + } +} |
