Seems to be fully working
This commit is contained in:
@@ -18,7 +18,6 @@ using EmbedIO.Routing;
|
||||
using EmbedIO.WebApi;
|
||||
using RemoteControl.Message;
|
||||
using RemoteControl.Utils;
|
||||
using Swan;
|
||||
using GameDevice = Assets.Scripts.Objects.Pipes.Device;
|
||||
|
||||
|
||||
@@ -38,7 +37,8 @@ namespace RemoteControl
|
||||
|
||||
private readonly Harmony _harmony = new Harmony(pluginGuid);
|
||||
|
||||
public WebServer WebServer { get; private set; }
|
||||
public static WebServer WebServer { get; private set; }
|
||||
internal static SubscriptionModule Subscribers { get; private set; }
|
||||
|
||||
|
||||
private CancellationTokenSource _modLifecycle = new();
|
||||
@@ -70,6 +70,7 @@ namespace RemoteControl
|
||||
|
||||
|
||||
var subscriptionModule = new SubscriptionModule("/subscribe");
|
||||
Subscribers = subscriptionModule;
|
||||
WebServer = new WebServer(o =>
|
||||
o.WithUrlPrefix($"http://{(ListenOnAllInterfaces.Value ? "0.0.0.0" : "localhost")}:{Port.Value}/")
|
||||
.WithEmbedIOHttpListener()
|
||||
@@ -125,28 +126,83 @@ namespace RemoteControl
|
||||
private static readonly Dictionary<string, LogicType> LtByName = EnumCollections.LogicTypes.AsLookupDict(true);
|
||||
private static readonly Dictionary<string, LogicSlotType> StByName = EnumCollections.LogicSlotTypes.AsLookupDict(true);
|
||||
|
||||
private static Device GetDeviceJson(GameDevice device) =>
|
||||
new()
|
||||
{
|
||||
ReferenceId = device.ReferenceId,
|
||||
Name = device.DisplayName,
|
||||
NameHash = device.GetNameHash(),
|
||||
PrefabHash = device.PrefabHash,
|
||||
PrefabName = device.PrefabName,
|
||||
LogicValues = EnumCollections.LogicTypes.Values.Where(ty => device.CanLogicRead(ty))
|
||||
.ToDictionary(ty => ty, ty => device.GetLogicValue(ty)),
|
||||
Slots = Enumerable.Range(0, device.TotalSlots)
|
||||
.Select(slot => EnumCollections.LogicSlotTypes.Values.Where(sty => device.CanLogicRead(sty, slot))
|
||||
.ToDictionary(ty => ty, sty=> device.GetLogicValue(sty, slot)))
|
||||
.ToList()
|
||||
};
|
||||
private static Device GetDeviceJson(GameDevice device) => new(device);
|
||||
|
||||
|
||||
private static Device? GetDeviceJson(long referenceId)
|
||||
{
|
||||
var dev = Referencable.Find<GameDevice>(referenceId);
|
||||
return dev == null ? null : GetDeviceJson(dev);
|
||||
return dev == null ? null : new Device(dev);
|
||||
}
|
||||
|
||||
private static GameDevice? GetNetworkDevice(string probeName, long referenceId)
|
||||
{
|
||||
GameDevice? dev = null;
|
||||
|
||||
GameDevice.AllDevices.ForEach(anaDev =>
|
||||
{
|
||||
if (anaDev is CableAnalyser analyser)
|
||||
{
|
||||
if (analyser.DisplayName != probeName) return false;
|
||||
dev = analyser.CableNetwork.DeviceList.Find(netDev => netDev.ReferenceId == referenceId);
|
||||
return dev != null;
|
||||
}
|
||||
|
||||
return false;
|
||||
});
|
||||
|
||||
return dev;
|
||||
}
|
||||
|
||||
|
||||
private static List<GameDevice> GetNetworkDevice(string probeName, string deviceName)
|
||||
{
|
||||
List<GameDevice> result = new();
|
||||
|
||||
GameDevice.AllDevices.ForEach(anaDev =>
|
||||
{
|
||||
if (anaDev is not CableAnalyser analyser) return;
|
||||
if (analyser.DisplayName != probeName) return;
|
||||
var found = analyser.CableNetwork.DeviceList.Find(netDev => netDev.DisplayName == deviceName);
|
||||
if (found is not null)
|
||||
{
|
||||
result.Add(found);
|
||||
}
|
||||
});
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
private static T FindUniqueDeviceForHttp<T>(string networkName, string deviceName)
|
||||
{
|
||||
var result = default(T);
|
||||
bool isFound = false;
|
||||
|
||||
GameDevice.AllDevices.ForEach(anaDev =>
|
||||
{
|
||||
if (anaDev is not CableAnalyser analyser) return;
|
||||
if (analyser.DisplayName != networkName) return;
|
||||
var found = analyser.CableNetwork.DeviceList.Find(netDev =>
|
||||
netDev is T && (netDev.DisplayName == deviceName || netDev.ReferenceId.ToString() == deviceName));
|
||||
if (found is T item)
|
||||
{
|
||||
if (isFound)
|
||||
{
|
||||
throw HttpException.InternalServerError("More than one object matches");
|
||||
}
|
||||
|
||||
result = item;
|
||||
isFound = true;
|
||||
}
|
||||
});
|
||||
if (!isFound)
|
||||
{
|
||||
throw HttpException.NotFound();
|
||||
}
|
||||
|
||||
return result!;
|
||||
}
|
||||
|
||||
[Route(HttpVerbs.Get, "/networks")]
|
||||
public Task<IList<string>> ListNetworks() => Task.FromResult(SubscriptionManager.GetProbes());
|
||||
|
||||
@@ -159,11 +215,9 @@ namespace RemoteControl
|
||||
var networks = new HashSet<CableNetwork>();
|
||||
GameDevice.AllDevices.ForEach(dev =>
|
||||
{
|
||||
if (dev is CableAnalyser analyser)
|
||||
if (dev is CableAnalyser analyser && dev.DisplayName == networkId)
|
||||
{
|
||||
Debug.Log($"Found CA {analyser.DisplayName}: {analyser.ReferenceId}");
|
||||
networks.Add(analyser.CableNetwork);
|
||||
|
||||
}
|
||||
});
|
||||
|
||||
@@ -172,7 +226,6 @@ namespace RemoteControl
|
||||
{
|
||||
foreach (var device in network.DeviceList)
|
||||
{
|
||||
RemoteControl.Log($"Found {device.PrefabName}: {device.DisplayName}({device.ReferenceId})");
|
||||
if (devices.ContainsKey(device.ReferenceId)) continue;
|
||||
devices.Add(device.ReferenceId, GetDeviceJson(device));
|
||||
}
|
||||
@@ -191,12 +244,19 @@ namespace RemoteControl
|
||||
}
|
||||
|
||||
var value = await HttpContext.GetRequestDataAsync<double>();
|
||||
|
||||
SubscriptionManager.SetLogic(networkId, deviceId, ltype, value);
|
||||
var dev = GetNetworkDevice(networkId, deviceId) ?? throw HttpException.NotFound();
|
||||
if (dev.CanLogicWrite(ltype))
|
||||
{
|
||||
dev.SetLogicValue(ltype, value);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw HttpException.MethodNotAllowed();
|
||||
}
|
||||
}
|
||||
|
||||
[Route(HttpVerbs.Post, "/networks/{networkId}/device/{deviceId}/slot/{slotId}/{varId}")]
|
||||
public async Task SetSlot(string networkId, long deviceId, int slotId, string varId)
|
||||
public async Task SetSlot(string networkId, string deviceId, int slotId, string varId)
|
||||
{
|
||||
LogicSlotType ltype;
|
||||
if (!StByName.TryGetValue(varId.ToLowerInvariant(), out ltype))
|
||||
@@ -205,11 +265,19 @@ namespace RemoteControl
|
||||
}
|
||||
|
||||
var value = await HttpContext.GetRequestDataAsync<double>();
|
||||
SubscriptionManager.SetSlot(networkId, deviceId, slotId, ltype, value);
|
||||
var dev = FindUniqueDeviceForHttp<GameDevice>(networkId, deviceId);
|
||||
if (dev.CanLogicWrite(ltype, slotId))
|
||||
{
|
||||
dev.SetLogicValue(ltype, slotId, value);
|
||||
}
|
||||
else
|
||||
{
|
||||
throw HttpException.MethodNotAllowed();
|
||||
};
|
||||
}
|
||||
|
||||
[Route(HttpVerbs.Patch, "/networks/{networkId}/device/{deviceId}")]
|
||||
public async Task PatchDevice(string networkId, long deviceId)
|
||||
public async Task PatchDevice(string networkId, string deviceId)
|
||||
{
|
||||
var values = await HttpContext.GetRequestDataAsync<Dictionary<string, double>>();
|
||||
if (values.Keys.Any(key => !LtByName.ContainsKey(key.ToLowerInvariant())))
|
||||
@@ -217,30 +285,29 @@ namespace RemoteControl
|
||||
throw HttpException.BadRequest();
|
||||
}
|
||||
|
||||
var dev = FindUniqueDeviceForHttp<GameDevice>(networkId, deviceId);
|
||||
foreach (var keyValuePair in values)
|
||||
{
|
||||
SubscriptionManager.SetLogic(networkId, deviceId, LtByName[keyValuePair.Key.ToLowerInvariant()], keyValuePair.Value);
|
||||
var logicType = LtByName[keyValuePair.Key.ToLowerInvariant()];
|
||||
if (dev.CanLogicWrite(logicType))
|
||||
{
|
||||
dev.SetLogicValue(logicType, keyValuePair.Value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
[Route(HttpVerbs.Get, "/networks/{networkId}/device/{deviceId}/code")]
|
||||
public async UniTask<string> GetCode(string networkId, long deviceId)
|
||||
public UniTask<string> GetCode(string networkId, string deviceId)
|
||||
{
|
||||
await UniTask.SwitchToMainThread(HttpContext.CancellationToken);
|
||||
var dev = FindUniqueDeviceForHttp<ICircuitHolder>(networkId, deviceId);
|
||||
return UniTask.FromResult(dev.GetSourceCode());
|
||||
}
|
||||
|
||||
string source;
|
||||
// lock (SubscriptionManager.Lock)
|
||||
{
|
||||
var device = SubscriptionManager.GetDevice(networkId, deviceId) ?? throw HttpException.NotFound();
|
||||
if (device is not ICircuitHolder)
|
||||
{
|
||||
throw HttpException.NotFound();
|
||||
}
|
||||
|
||||
source = ((ICircuitHolder)device).GetSourceCode();
|
||||
}
|
||||
|
||||
return source;
|
||||
[Route(HttpVerbs.Post, "/networks/{networkId}/device/{deviceId}/code")]
|
||||
public UniTask<string> SetCode(string networkId, string deviceId, string code)
|
||||
{
|
||||
var dev = FindUniqueDeviceForHttp<ICircuitHolder>(networkId, deviceId);
|
||||
return UniTask.FromResult(dev.GetSourceCode());
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user