jensenkd / plex-api

.NET Core SDK for Plex Media Server
MIT License
86 stars 27 forks source link

Automatically failover to LocalAddresses #101

Open Biztactix-Ryan opened 1 year ago

Biztactix-Ryan commented 1 year ago

Is your feature request related to a problem? Please describe. Can't connect to servers if it has a public IP Address as well as a local, Most Routers don't support Hairpin NAT correctly.

Describe the solution you'd like Upon failure, if there are LocalIPs listed, then create a URI for each of them and check if you can connect to it.

Describe alternatives you've considered I've tested it myself by overriding the Host on the AccountServer object, That works and I can continue from here... But obviously auto failover makes sense

Additional context It's Ugly, but it shows where I've gotten to with it, It just catches the error and then updates the host image

Tailslide commented 1 year ago

Ran into the exact same problem and used your code verbatim.. problem solved! Thanks, saved me so much time.

Still Ugly but maybe less ugly extension method:

MyServer = services.ConnectToPlexServer(key, servername);
Extension Method

```C# using Microsoft.Extensions.DependencyInjection; using Plex.Api.Factories; using Plex.Library.ApiModels.Servers; using Plex.ServerApi.Clients.Interfaces; using Plex.ServerApi.PlexModels.Account; namespace PlexMakePlaylist { public static class PlexExtensions { public static Server? ConnectToPlexServer(this IServiceProvider services, string token, string serverName = "", bool TryLocalFirst = true, bool OwnedOnly = true) { Server? myserver = null; var _plexFactory = services.GetService(); Plex.ServerApi.PlexModels.Server.PlexServer? server = null; if (_plexFactory != null) { var account = _plexFactory .GetPlexAccount(token); var serversum = account.ServerSummaries().Result; var server1 = serversum.Servers .Where(x => (x.Owned == 1 || OwnedOnly == false) && (x.Name == serverName || serverName == "") ) .First(); var serverClient = services.GetService(); if (serverClient == null) throw new MissingMemberException("Missing IPlexServerClient Service"); var libClient = services.GetService(); if (libClient == null) throw new MissingMemberException("Missing IPlexLibraryClient Service"); if (TryLocalFirst) { myserver = ConnectLocal(server1, serverClient, libClient); if (myserver == null) myserver=ConnectRemote(server1, serverClient, libClient); } else { myserver = ConnectRemote(server1, serverClient, libClient); if (myserver == null) myserver = ConnectLocal(server1, serverClient, libClient); } } return myserver; } private static Server? ConnectLocal(AccountServer server1, IPlexServerClient? serverClient, IPlexLibraryClient? libClient) { Server? myserver = null; try { List localIP = new List(); if (!server1.LocalAddresses.Contains(",")) localIP.Add(server1.LocalAddresses); else localIP.AddRange(server1.LocalAddresses.Split(",")); foreach (string ip in localIP) { server1.Host = ip; myserver = new Server(serverClient, libClient, server1); break; // assume if this went OK we are connected } } catch { // TODO: don't rely on exception for this somehow? } return myserver; } private static Server? ConnectRemote(AccountServer server1, IPlexServerClient serverClient, IPlexLibraryClient? libClient) { Server? myserver = null; try { myserver = new Server(serverClient, libClient, server1); } catch { // TODO: don't rely on exception for this somehow? } return myserver; } } } ```

jensenkd commented 1 year ago

I'll try to take a look at this this weekend.

Biztactix-Ryan commented 1 year ago

Ran into the exact same problem and used your code verbatim.. problem solved! Thanks, saved me so much time.

Still Ugly but maybe less ugly extension method:

MyServer = services.ConnectToPlexServer(key, servername);

Thanks... Your code is much nicer, I wasn't particularly in the mood for nice by that point, the plex bit was supposed to be the easy part ;) The old, I'll just write a quick bit of code to pull a list of all the shows I watch on Plex... and why isn't that working....