Cleanup of services and new homebound service [replaces at home]
This commit is contained in:
parent
b089591fcb
commit
745977b1b4
15 changed files with 857 additions and 199 deletions
|
|
@ -197,6 +197,7 @@ namespace SecondBotEvents.Commands
|
|||
{
|
||||
return Failure("Error Unable to Teleport to location", new [] { region, x, y, z });
|
||||
}
|
||||
master.HomeboundService.markTeleport();
|
||||
return BasicReply("Accepted", new [] { region, x, y, z });
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -26,8 +26,8 @@ namespace SecondBotEvents.Commands
|
|||
{
|
||||
return Failure("Content value is empty", new [] { collection, content });
|
||||
}
|
||||
return Failure("@todo notecard temp stroage");
|
||||
//return BasicReply("ok", "NotecardAdd", new [] { collection, content });
|
||||
master.DataStoreService.AppendKeyValue("notecard_"+collection, content);
|
||||
return BasicReply("ok", new [] { collection, master.DataStoreService.GetKeyValue("notecard_"+collection).Length.ToString() });
|
||||
}
|
||||
|
||||
[About("Clears the contents of a collection")]
|
||||
|
|
@ -40,7 +40,8 @@ namespace SecondBotEvents.Commands
|
|||
{
|
||||
return Failure("Collection value is empty", new [] { collection });
|
||||
}
|
||||
return Failure("@todo notecard storage");
|
||||
master.DataStoreService.ClearKeyValue("notecard_" + collection);
|
||||
return BasicReply("ok");
|
||||
}
|
||||
|
||||
[About("Sends a notecard to a avatar using the text in the prebuilt collection [see NotecardAdd] and also clears the collection just before sending [see NotecardClear]")]
|
||||
|
|
@ -67,7 +68,18 @@ namespace SecondBotEvents.Commands
|
|||
{
|
||||
return Failure("Invaild avatar uuid", new [] { avatar, collection, notecardname });
|
||||
}
|
||||
return Failure("@todo notecard storage");
|
||||
string content = master.DataStoreService.GetKeyValue("notecard_" + collection);
|
||||
if(content.Length <= 3)
|
||||
{
|
||||
return Failure("No content in notecard storage ?", new[] { avatar, collection, notecardname });
|
||||
}
|
||||
bool result = master.botClient.SendNotecard(notecardname, content, avataruuid);
|
||||
if (result == false)
|
||||
{
|
||||
return Failure("Failed to create/send notecard", new[] { avatar, content, notecardname });
|
||||
}
|
||||
master.DataStoreService.ClearKeyValue("notecard_" + collection);
|
||||
return BasicReply("ok");
|
||||
}
|
||||
|
||||
[About("Creates and sends a notecard in one command good if you are using HTTP otherwise see [NotecardSend]")]
|
||||
|
|
@ -93,7 +105,12 @@ namespace SecondBotEvents.Commands
|
|||
{
|
||||
return Failure("Invaild avatar uuid", new[] { avatar, content, notecardname });
|
||||
}
|
||||
return Failure("@todo notecard sending");
|
||||
bool result = master.botClient.SendNotecard(notecardname, content, avataruuid);
|
||||
if(result == false)
|
||||
{
|
||||
return Failure("Failed to create/send notecard", new[] { avatar, content, notecardname });
|
||||
}
|
||||
return BasicReply("ok");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -60,7 +60,17 @@ namespace SecondBotEvents.Commands
|
|||
{
|
||||
return Failure("Notecard title is to short", new [] { endpoint, endpointcode });
|
||||
}
|
||||
return Failure("@todo notecard sending");
|
||||
ProcessAvatar(server_reply.AvatarUUID);
|
||||
if(avataruuid == UUID.Zero)
|
||||
{
|
||||
return Failure("Unable to unpack avatar", new[] { endpoint, endpointcode });
|
||||
}
|
||||
bool result = master.botClient.SendNotecard(server_reply.NotecardTitle, server_reply.NotecardContent, avataruuid);
|
||||
if (result == false)
|
||||
{
|
||||
return Failure("Failed to create/send notecard", new[] { endpoint, endpointcode });
|
||||
}
|
||||
return BasicReply("ok");
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -14,7 +14,6 @@ namespace SecondBotEvents.Config
|
|||
settings.Add("LocalChatHistoryLimit");
|
||||
settings.Add("GroupChatHistoryLimitPerGroup");
|
||||
settings.Add("ImChatHistoryLimit");
|
||||
settings.Add("NotecardStoragePurgeAfterMins");
|
||||
settings.Add("PrefetchGroupMembers");
|
||||
settings.Add("PrefetchGroupRoles");
|
||||
settings.Add("PrefetchEstateBanlist");
|
||||
|
|
@ -73,10 +72,5 @@ namespace SecondBotEvents.Config
|
|||
{
|
||||
return ReadSettingAsInt("ImChatHistoryLimit", 50);
|
||||
}
|
||||
|
||||
public int GetNotecardStoragePurgeAfterMins()
|
||||
{
|
||||
return ReadSettingAsInt("NotecardStoragePurgeAfterMins", 10);
|
||||
}
|
||||
}
|
||||
}
|
||||
53
SecondBotEvents/Config/HomeboundConfig.cs
Normal file
53
SecondBotEvents/Config/HomeboundConfig.cs
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
using OpenMetaverse;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace SecondBotEvents.Config
|
||||
{
|
||||
public class HomeboundConfig : Config
|
||||
{
|
||||
public HomeboundConfig(bool fromENV, string fromFolder = "") : base(fromENV, fromFolder) { }
|
||||
protected override void MakeSettings()
|
||||
{
|
||||
filename = "homebound";
|
||||
settings.Add("Enabled");
|
||||
settings.Add("HomeSimSlUrl");
|
||||
settings.Add("BackupSimSLUrl");
|
||||
settings.Add("AtHomeSeekLocation");
|
||||
settings.Add("AtBackupSeekLocation");
|
||||
settings.Add("AtHomeAutoSitUuid");
|
||||
}
|
||||
|
||||
public string GetAtHomeAutoSitUuid()
|
||||
{
|
||||
return ReadSettingAsString("AtHomeAutoSitUuid", UUID.Zero.ToString());
|
||||
}
|
||||
|
||||
public bool GetAtHomeSeekLocation()
|
||||
{
|
||||
return ReadSettingAsBool("AtHomeSeekLocation", true);
|
||||
}
|
||||
|
||||
public bool GetAtBackupSeekLocation()
|
||||
{
|
||||
return ReadSettingAsBool("AtBackupSeekLocation", false);
|
||||
}
|
||||
|
||||
public string GetBackupSimSLUrl()
|
||||
{
|
||||
return ReadSettingAsString("BackupSimSLUrl", "Sandbox%20Decorus/128/128/27");
|
||||
}
|
||||
|
||||
public string GetHomeSimSlUrl()
|
||||
{
|
||||
return ReadSettingAsString("HomeSimSlUrl", "Viserion/46/163/23");
|
||||
}
|
||||
|
||||
public bool GetEnabled()
|
||||
{
|
||||
return ReadSettingAsBool("Enabled", false);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -11,12 +11,12 @@ namespace SecondBotEvents.Config
|
|||
{
|
||||
filename = "http";
|
||||
settings.Add("Enabled");
|
||||
settings.Add("Host");
|
||||
settings.Add("Port");
|
||||
}
|
||||
|
||||
public string GetHost()
|
||||
public int GetPort()
|
||||
{
|
||||
return ReadSettingAsString("Host", "http://*:80");
|
||||
return ReadSettingAsInt("Port", 80);
|
||||
}
|
||||
|
||||
public bool GetEnabled()
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@ using System;
|
|||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using System.Threading;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace SecondBotEvents
|
||||
{
|
||||
|
|
@ -10,24 +11,31 @@ namespace SecondBotEvents
|
|||
{
|
||||
static void Main(string[] args)
|
||||
{
|
||||
Console.WriteLine("Welcome to Secondbot [Events build] version: " + AssemblyInfo.GetGitHash());
|
||||
LogFormater.Info("Welcome to Secondbot [Events build] version: " + AssemblyInfo.GetGitHash());
|
||||
EventsSecondBot worker = new EventsSecondBot(args);
|
||||
|
||||
while(worker.Exit() == false)
|
||||
{
|
||||
if(worker.Ready == true)
|
||||
{
|
||||
worker.Status();
|
||||
}
|
||||
Thread.Sleep(1000);
|
||||
}
|
||||
LogFormater.Warn("Shutdown in 5 secs");
|
||||
Thread.Sleep(5000);
|
||||
}
|
||||
}
|
||||
|
||||
public class EventsSecondBot
|
||||
{
|
||||
public HttpService HttpService = null;
|
||||
public CommandsService CommandsService = null;
|
||||
public BotClientService botClient = null;
|
||||
public DiscordService DiscordService = null;
|
||||
public InteractionService InteractionService = null;
|
||||
public DataStoreService DataStoreService = null;
|
||||
public HttpService HttpService { get { return (HttpService) getService("HttpService"); } }
|
||||
public CommandsService CommandsService { get { return (CommandsService)getService("CommandsService"); } }
|
||||
public BotClientService botClient { get { return (BotClientService)getService("BotClientService"); } }
|
||||
public DiscordService DiscordService { get { return (DiscordService)getService("DiscordService"); } }
|
||||
public InteractionService InteractionService { get { return (InteractionService)getService("InteractionService"); } }
|
||||
public DataStoreService DataStoreService { get { return (DataStoreService)getService("DataStoreService"); } }
|
||||
public HomeboundService HomeboundService { get { return (HomeboundService)getService("HomeboundService"); } }
|
||||
|
||||
|
||||
private EventHandler<BotClientNotice> botclient_eventNotices;
|
||||
|
|
@ -45,6 +53,8 @@ namespace SecondBotEvents
|
|||
handler?.Invoke(this, new BotClientNotice(asRestart));
|
||||
}
|
||||
|
||||
|
||||
|
||||
public string GetVersion()
|
||||
{
|
||||
return AssemblyInfo.GetGitHash();
|
||||
|
|
@ -67,61 +77,120 @@ namespace SecondBotEvents
|
|||
StartServices();
|
||||
}
|
||||
|
||||
public bool Ready = false;
|
||||
|
||||
public void RestartServices()
|
||||
{
|
||||
StopServices();
|
||||
StartServices();
|
||||
}
|
||||
|
||||
protected Dictionary<string, BotServices> services = new Dictionary<string, BotServices>();
|
||||
|
||||
public BotServices getService(string classname)
|
||||
{
|
||||
if(services.ContainsKey(classname) == false)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
return services[classname];
|
||||
}
|
||||
protected BotServices RegisterService(string classname, bool autoStart = true)
|
||||
{
|
||||
BotServices instance = (BotServices)GetInstance("SecondBotEvents.Services." + classname);
|
||||
services.Add(classname, instance);
|
||||
lastStatus.Add(classname, "?");
|
||||
if (autoStart == true)
|
||||
{
|
||||
instance.Start();
|
||||
}
|
||||
return instance;
|
||||
}
|
||||
|
||||
protected object GetInstance(string strFullyQualifiedName)
|
||||
{
|
||||
Type type = Type.GetType(strFullyQualifiedName);
|
||||
if (type != null)
|
||||
return Activator.CreateInstance(type, this);
|
||||
foreach (var asm in AppDomain.CurrentDomain.GetAssemblies())
|
||||
{
|
||||
type = asm.GetType(strFullyQualifiedName);
|
||||
if (type != null)
|
||||
return Activator.CreateInstance(type, this);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
protected void StartServices()
|
||||
{
|
||||
DataStoreService = new DataStoreService(this);
|
||||
DataStoreService.Start();
|
||||
botClient = new BotClientService(this);
|
||||
HttpService = new HttpService(this);
|
||||
CommandsService = new CommandsService(this);
|
||||
DiscordService = new DiscordService(this);
|
||||
InteractionService = new InteractionService(this);
|
||||
services = new Dictionary<string, BotServices>();
|
||||
lastStatus = new Dictionary<string, string>();
|
||||
RegisterService("BotClientService", false);
|
||||
RegisterService("DataStoreService");
|
||||
RegisterService("HttpService");
|
||||
RegisterService("CommandsService");
|
||||
RegisterService("DiscordService");
|
||||
RegisterService("InteractionService");
|
||||
RegisterService("HomeboundService");
|
||||
if (botClient.IsLoaded() == false)
|
||||
{
|
||||
Console.WriteLine("Config is not loaded :(");
|
||||
exitNow = true;
|
||||
return;
|
||||
}
|
||||
HttpService.Start();
|
||||
CommandsService.Start();
|
||||
DiscordService.Start();
|
||||
InteractionService.Start();
|
||||
botClient.Start();
|
||||
Ready = true;
|
||||
|
||||
}
|
||||
|
||||
Dictionary<string, string> lastStatus = new Dictionary<string, string>();
|
||||
long lastChange = 0;
|
||||
public void Status()
|
||||
{
|
||||
string Output = "";
|
||||
string addon = "";
|
||||
foreach(KeyValuePair<string, BotServices> A in services)
|
||||
{
|
||||
string StatusMessage = A.Value.Status();
|
||||
if(StatusMessage != lastStatus[A.Key])
|
||||
{
|
||||
Output = Output + addon + " [" + A.Key + "] ~ " + StatusMessage;
|
||||
lastStatus[A.Key] = StatusMessage;
|
||||
addon = " | ";
|
||||
}
|
||||
}
|
||||
if(Output != "")
|
||||
{
|
||||
LogFormater.Info(Output);
|
||||
lastChange = SecondbotHelpers.UnixTimeNow();
|
||||
return;
|
||||
}
|
||||
long dif = SecondbotHelpers.UnixTimeNow() - lastChange;
|
||||
if(dif > 60)
|
||||
{
|
||||
string[] bits = lastStatus.Keys.ToArray();
|
||||
foreach (string A in bits)
|
||||
{
|
||||
lastStatus[A] = "";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected void StopServices()
|
||||
{
|
||||
if(DataStoreService != null)
|
||||
Ready = false;
|
||||
Dictionary<string, BotServices> copy = services;
|
||||
foreach (KeyValuePair<string, BotServices> A in copy)
|
||||
{
|
||||
DataStoreService.Stop();
|
||||
if(A.Key == "BotClientService")
|
||||
{
|
||||
continue;
|
||||
}
|
||||
A.Value.Stop();
|
||||
services.Remove(A.Key);
|
||||
}
|
||||
if (HttpService != null)
|
||||
{
|
||||
HttpService.Stop();
|
||||
}
|
||||
if (CommandsService != null)
|
||||
{
|
||||
CommandsService.Stop();
|
||||
}
|
||||
if (DiscordService != null)
|
||||
{
|
||||
DiscordService.Stop();
|
||||
}
|
||||
if(InteractionService != null)
|
||||
{
|
||||
InteractionService.Stop();
|
||||
}
|
||||
if(botClient != null)
|
||||
{
|
||||
botClient.Stop();
|
||||
}
|
||||
HttpService = null;
|
||||
botClient = null;
|
||||
|
||||
services["BotClientService"].Stop();
|
||||
services.Remove("BotClientService");
|
||||
}
|
||||
|
||||
public bool Exit()
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
using OpenMetaverse;
|
||||
using OpenMetaverse.Assets;
|
||||
using SecondBotEvents.Config;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
|
@ -6,10 +7,19 @@ using System.Text;
|
|||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public class BotClientService : Services
|
||||
public class BotClientService : BotServices
|
||||
{
|
||||
public GridClient client = null;
|
||||
protected BasicConfig basicCfg = null;
|
||||
public bool _ExitBot
|
||||
{
|
||||
get { return ExitBot; } // get method
|
||||
set { } // set method
|
||||
}
|
||||
|
||||
protected bool ExitBot = false;
|
||||
|
||||
|
||||
public BotClientService(EventsSecondBot setMaster) : base(setMaster)
|
||||
{
|
||||
basicCfg = new BasicConfig(master.fromEnv, master.fromFolder);
|
||||
|
|
@ -52,7 +62,14 @@ namespace SecondBotEvents.Services
|
|||
}
|
||||
|
||||
protected void BotLoginStatus(object o, LoginProgressEventArgs e)
|
||||
{
|
||||
{
|
||||
if(e.FailReason != "")
|
||||
{
|
||||
Console.WriteLine("Client service ~ {FAILED} Login status: " + e.FailReason.ToString());
|
||||
client.Network.Logout();
|
||||
ResetClient();
|
||||
return;
|
||||
}
|
||||
Console.WriteLine("Client service ~ Login status: " + e.Status.ToString());
|
||||
}
|
||||
public void SendIM(UUID avatar, string message)
|
||||
|
|
@ -61,6 +78,64 @@ namespace SecondBotEvents.Services
|
|||
client.Self.InstantMessage(avatar, message);
|
||||
}
|
||||
|
||||
public bool SendNotecard(string name, string content, UUID sendToUUID)
|
||||
{
|
||||
bool returnstatus = true;
|
||||
name = name + " " + DateTime.Now;
|
||||
client.Inventory.RequestCreateItem(
|
||||
client.Inventory.FindFolderForType(AssetType.Notecard),
|
||||
name,
|
||||
name + " Created via SecondBot notecard API",
|
||||
AssetType.Notecard,
|
||||
UUID.Random(),
|
||||
InventoryType.Notecard,
|
||||
PermissionMask.All,
|
||||
(bool Success, InventoryItem item) =>
|
||||
{
|
||||
if (Success)
|
||||
{
|
||||
AssetNotecard empty = new AssetNotecard { BodyText = "\n" };
|
||||
empty.Encode();
|
||||
client.Inventory.RequestUploadNotecardAsset(empty.AssetData, item.UUID,
|
||||
(bool emptySuccess, string emptyStatus, UUID emptyItemID, UUID emptyAssetID) =>
|
||||
{
|
||||
if (emptySuccess)
|
||||
{
|
||||
empty.BodyText = content;
|
||||
empty.Encode();
|
||||
client.Inventory.RequestUploadNotecardAsset(empty.AssetData, emptyItemID,
|
||||
(bool finalSuccess, string finalStatus, UUID finalItemID, UUID finalID) =>
|
||||
{
|
||||
if (finalSuccess)
|
||||
{
|
||||
LogFormater.Info("Sending notecard now");
|
||||
client.Inventory.GiveItem(finalItemID, name, AssetType.Notecard, sendToUUID, false);
|
||||
}
|
||||
else
|
||||
{
|
||||
returnstatus = false;
|
||||
LogFormater.Warn("Unable to request notecard upload");
|
||||
}
|
||||
|
||||
});
|
||||
}
|
||||
else
|
||||
{
|
||||
LogFormater.Warn("The fuck empty success notecard create");
|
||||
returnstatus = false;
|
||||
}
|
||||
});
|
||||
}
|
||||
else
|
||||
{
|
||||
LogFormater.Warn("Unable to find default notecards folder");
|
||||
returnstatus = false;
|
||||
}
|
||||
}
|
||||
);
|
||||
return returnstatus;
|
||||
}
|
||||
|
||||
protected void ResetClient()
|
||||
{
|
||||
bool isRestart = false;
|
||||
|
|
@ -96,6 +171,25 @@ namespace SecondBotEvents.Services
|
|||
client.Network.BeginLogin(loginParams);
|
||||
}
|
||||
|
||||
|
||||
public override string Status()
|
||||
{
|
||||
if (client == null)
|
||||
{
|
||||
return "No Client [Restart needed]";
|
||||
}
|
||||
else if (client.Network == null)
|
||||
{
|
||||
return "No network - [Starting / Shutting down]";
|
||||
}
|
||||
else if (client.Network.Connected == false)
|
||||
{
|
||||
return "Not connected";
|
||||
}
|
||||
else if (client.Network.CurrentSim == null)
|
||||
{
|
||||
return "No sim";
|
||||
}
|
||||
return client.Network.CurrentSim.Name + " " + client.Self.SimPosition.ToString();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ using System.Net.Http;
|
|||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public class CommandsService : Services
|
||||
public class CommandsService : BotServices
|
||||
{
|
||||
public CommandsConfig myConfig = null;
|
||||
public bool acceptNewCommands = false;
|
||||
|
|
@ -120,6 +120,15 @@ namespace SecondBotEvents.Services
|
|||
acceptNewCommands = false;
|
||||
}
|
||||
|
||||
public override string Status()
|
||||
{
|
||||
if (acceptNewCommands == false)
|
||||
{
|
||||
return "Disabled";
|
||||
}
|
||||
return "Enabled";
|
||||
}
|
||||
|
||||
protected void BotImMessage(object o, InstantMessageEventArgs e)
|
||||
{
|
||||
if(acceptNewCommands == false)
|
||||
|
|
@ -346,7 +355,7 @@ namespace SecondBotEvents.Services
|
|||
public string command;
|
||||
public string signingCode;
|
||||
public string[] args;
|
||||
public string replyTarget;
|
||||
public string replyTarget = null;
|
||||
public bool accepted = false;
|
||||
public long unixtimeOfCommand = 0;
|
||||
public SignedCommand(string input, bool requireSigning, bool requireTimewindow, int windowSize, string secret)
|
||||
|
|
@ -357,12 +366,27 @@ namespace SecondBotEvents.Services
|
|||
accepted = true; // just accept the command
|
||||
return;
|
||||
}
|
||||
vaildate(requireTimewindow, windowSize, secret);
|
||||
}
|
||||
public SignedCommand(string setCommand, string setSigningCode, string[] setArgs, int setUnixtime, string setReplyTarget, bool requireTimewindow, int windowSize, string secret)
|
||||
{
|
||||
command = setCommand;
|
||||
signingCode = setSigningCode;
|
||||
args = setArgs;
|
||||
unixtimeOfCommand = setUnixtime;
|
||||
replyTarget = setReplyTarget;
|
||||
vaildate(requireTimewindow, windowSize, secret);
|
||||
}
|
||||
|
||||
protected void vaildate(bool requireTimewindow, int windowSize, string secret)
|
||||
{
|
||||
accepted = false;
|
||||
long dif = SecondbotHelpers.UnixTimeNow() - unixtimeOfCommand;
|
||||
if ((requireTimewindow == true) && ((unixtimeOfCommand == 0) || (dif > windowSize))) // bad time window
|
||||
{
|
||||
return;
|
||||
}
|
||||
if ((signingCode == null) ) // no signing code
|
||||
if ((signingCode == null)) // no signing code
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
|
@ -379,9 +403,8 @@ namespace SecondBotEvents.Services
|
|||
return; // invaild signing code
|
||||
}
|
||||
accepted = true;
|
||||
|
||||
|
||||
}
|
||||
|
||||
protected void unpackInput(string input)
|
||||
{
|
||||
if (IsValidJson(input) == false)
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ using System.Threading;
|
|||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public class DataStoreService : Services
|
||||
public class DataStoreService : BotServices
|
||||
{
|
||||
protected DataStoreConfig myConfig;
|
||||
protected bool botConnected = false;
|
||||
|
|
@ -18,15 +18,6 @@ namespace SecondBotEvents.Services
|
|||
myConfig = new DataStoreConfig(master.fromEnv,master.fromFolder);
|
||||
}
|
||||
|
||||
public override string Status()
|
||||
{
|
||||
if(myConfig == null)
|
||||
{
|
||||
return "DataStore Service [Config status broken]";
|
||||
}
|
||||
return "DataStore Service [Waiting for bot]";
|
||||
}
|
||||
|
||||
protected Dictionary<string, UUID> avatarsName2Key = new Dictionary<string, UUID>();
|
||||
|
||||
protected Dictionary<UUID, string> groupsKey2Name = new Dictionary<UUID, string>();
|
||||
|
|
@ -44,12 +35,24 @@ namespace SecondBotEvents.Services
|
|||
protected Dictionary<string, string> KeyValueStore = new Dictionary<string, string>();
|
||||
protected Dictionary<string, long> KeyValueStoreLastUsed = new Dictionary<string, long>();
|
||||
|
||||
|
||||
protected List<CommandHistory> commandHistories = new List<CommandHistory>();
|
||||
|
||||
public void addCommandToHistory(UUID Source, string command, string[] args)
|
||||
public override string Status()
|
||||
{
|
||||
CommandHistory A = new CommandHistory(Source, command, args, SecondbotHelpers.UnixTimeNow());
|
||||
if (myConfig == null)
|
||||
{
|
||||
return "DataStore Service [Config broken]";
|
||||
}
|
||||
int sum = commandHistories.Count() + KeyValueStoreLastUsed.Count() + KeyValueStore.Count() +
|
||||
chatWindowsOwner.Count() + chatWindowsIsGroup.Count() + chatWindowsUnread.Count() +
|
||||
chatWindows.Count() + localChatHistory.Count() + groupRoles.Count() +
|
||||
groupMembers.Count() + groupsKey2Name.Count() + avatarsName2Key.Count();
|
||||
return sum.ToString();
|
||||
}
|
||||
|
||||
public void addCommandToHistory(bool status, string command, string[] args)
|
||||
{
|
||||
CommandHistory A = new CommandHistory(status, command, args, SecondbotHelpers.UnixTimeNow());
|
||||
commandHistories.Add(A);
|
||||
int c = commandHistories.Count;
|
||||
while (c > myConfig.GetCommandHistoryLimit())
|
||||
|
|
@ -257,83 +260,92 @@ namespace SecondBotEvents.Services
|
|||
|
||||
protected void recordChat(UUID sessionID, string fromname, string message)
|
||||
{
|
||||
if(chatWindows.ContainsKey(sessionID) == false)
|
||||
lock (chatWindows)
|
||||
{
|
||||
return; // chat window not open unable to record message
|
||||
}
|
||||
chatWindows[sessionID].Add(fromname + ": " + message);
|
||||
chatWindowsUnread[sessionID] = true;
|
||||
int purgeLen = myConfig.GetImChatHistoryLimit();
|
||||
if(chatWindowsIsGroup[sessionID] == true)
|
||||
{
|
||||
purgeLen = myConfig.GetGroupChatHistoryLimitPerGroup();
|
||||
}
|
||||
int counter = chatWindows[sessionID].Count();
|
||||
while (counter > purgeLen)
|
||||
{
|
||||
chatWindows[sessionID].RemoveAt(0);
|
||||
counter--;
|
||||
if (chatWindows.ContainsKey(sessionID) == false)
|
||||
{
|
||||
return; // chat window not open unable to record message
|
||||
}
|
||||
chatWindows[sessionID].Add(fromname + ": " + message);
|
||||
chatWindowsUnread[sessionID] = true;
|
||||
int purgeLen = myConfig.GetImChatHistoryLimit();
|
||||
if (chatWindowsIsGroup[sessionID] == true)
|
||||
{
|
||||
purgeLen = myConfig.GetGroupChatHistoryLimitPerGroup();
|
||||
}
|
||||
int counter = chatWindows[sessionID].Count();
|
||||
while (counter > purgeLen)
|
||||
{
|
||||
chatWindows[sessionID].RemoveAt(0);
|
||||
counter--;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected void closeChat(UUID owner)
|
||||
{
|
||||
UUID sessionID = UUID.Zero;
|
||||
if(chatWindowsOwner.ContainsValue(owner) == false)
|
||||
lock (chatWindows)
|
||||
{
|
||||
return;
|
||||
}
|
||||
foreach(KeyValuePair<UUID,UUID> ownermap in chatWindowsOwner)
|
||||
{
|
||||
if(ownermap.Value != owner)
|
||||
UUID sessionID = UUID.Zero;
|
||||
if (chatWindowsOwner.ContainsValue(owner) == false)
|
||||
{
|
||||
continue;
|
||||
return;
|
||||
}
|
||||
sessionID = ownermap.Key;
|
||||
foreach (KeyValuePair<UUID, UUID> ownermap in chatWindowsOwner)
|
||||
{
|
||||
if (ownermap.Value != owner)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
sessionID = ownermap.Key;
|
||||
}
|
||||
if (sessionID == UUID.Zero)
|
||||
{
|
||||
return;
|
||||
}
|
||||
chatWindowsOwner.Remove(sessionID);
|
||||
chatWindowsIsGroup.Remove(sessionID);
|
||||
chatWindowsUnread.Remove(sessionID);
|
||||
chatWindows.Remove(sessionID);
|
||||
}
|
||||
if(sessionID == UUID.Zero)
|
||||
{
|
||||
return;
|
||||
}
|
||||
chatWindowsOwner.Remove(sessionID);
|
||||
chatWindowsIsGroup.Remove(sessionID);
|
||||
chatWindowsUnread.Remove(sessionID);
|
||||
chatWindows.Remove(sessionID);
|
||||
|
||||
}
|
||||
|
||||
protected void openChatWindow(bool group, UUID sessionID, UUID ownerID)
|
||||
{
|
||||
if (chatWindows.ContainsKey(sessionID) == true)
|
||||
lock (chatWindows)
|
||||
{
|
||||
return; // window already open
|
||||
}
|
||||
if (chatWindowsOwner.ContainsValue(ownerID) == true)
|
||||
{
|
||||
// new session find the old one and update to this session
|
||||
Dictionary<UUID, UUID> oldOwners = chatWindowsOwner;
|
||||
foreach (KeyValuePair<UUID,UUID> kvp in oldOwners)
|
||||
if (chatWindows.ContainsKey(sessionID) == true)
|
||||
{
|
||||
if(kvp.Value == ownerID)
|
||||
{
|
||||
chatWindows.Add(sessionID, chatWindows[kvp.Key]);
|
||||
chatWindowsUnread.Add(sessionID, chatWindowsUnread[kvp.Key]);
|
||||
chatWindowsIsGroup.Add(sessionID, chatWindowsIsGroup[kvp.Key]);
|
||||
chatWindowsOwner.Add(sessionID, ownerID);
|
||||
chatWindows.Remove(kvp.Key);
|
||||
chatWindowsUnread.Remove(kvp.Key);
|
||||
chatWindowsIsGroup.Remove(kvp.Key);
|
||||
chatWindowsOwner.Remove(kvp.Key);
|
||||
break;
|
||||
}
|
||||
return; // window already open
|
||||
}
|
||||
return; // chat recovered
|
||||
if (chatWindowsOwner.ContainsValue(ownerID) == true)
|
||||
{
|
||||
// new session find the old one and update to this session
|
||||
Dictionary<UUID, UUID> oldOwners = chatWindowsOwner;
|
||||
foreach (KeyValuePair<UUID, UUID> kvp in oldOwners)
|
||||
{
|
||||
if (kvp.Value == ownerID)
|
||||
{
|
||||
chatWindows.Add(sessionID, chatWindows[kvp.Key]);
|
||||
chatWindowsUnread.Add(sessionID, chatWindowsUnread[kvp.Key]);
|
||||
chatWindowsIsGroup.Add(sessionID, chatWindowsIsGroup[kvp.Key]);
|
||||
chatWindowsOwner.Add(sessionID, ownerID);
|
||||
chatWindows.Remove(kvp.Key);
|
||||
chatWindowsUnread.Remove(kvp.Key);
|
||||
chatWindowsIsGroup.Remove(kvp.Key);
|
||||
chatWindowsOwner.Remove(kvp.Key);
|
||||
break;
|
||||
}
|
||||
}
|
||||
return; // chat recovered
|
||||
}
|
||||
chatWindows.Add(sessionID, new List<string>());
|
||||
chatWindowsUnread.Add(sessionID, false);
|
||||
chatWindowsIsGroup.Add(sessionID, group);
|
||||
chatWindowsOwner.Add(sessionID, ownerID);
|
||||
// new window now open
|
||||
}
|
||||
chatWindows.Add(sessionID, new List<string>());
|
||||
chatWindowsUnread.Add(sessionID, false);
|
||||
chatWindowsIsGroup.Add(sessionID, group);
|
||||
chatWindowsOwner.Add(sessionID, ownerID);
|
||||
// new window now open
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -632,23 +644,29 @@ namespace SecondBotEvents.Services
|
|||
|
||||
protected void GroupRoles(object o, GroupRolesDataReplyEventArgs e)
|
||||
{
|
||||
if(groupRoles.ContainsKey(e.GroupID) == false)
|
||||
lock (groupRoles)
|
||||
{
|
||||
groupRoles.Add(e.GroupID, new Dictionary<UUID, GroupRole>());
|
||||
if (groupRoles.ContainsKey(e.GroupID) == false)
|
||||
{
|
||||
groupRoles.Add(e.GroupID, new Dictionary<UUID, GroupRole>());
|
||||
}
|
||||
groupRoles[e.GroupID] = e.Roles;
|
||||
}
|
||||
groupRoles[e.GroupID] = e.Roles;
|
||||
}
|
||||
|
||||
protected void GroupMembers(object o, GroupMembersReplyEventArgs e)
|
||||
{
|
||||
if(groupMembers.ContainsKey(e.GroupID) == true)
|
||||
lock (groupMembers)
|
||||
{
|
||||
groupMembers.Remove(e.GroupID);
|
||||
}
|
||||
groupMembers.Add(e.GroupID, new List<UUID>());
|
||||
foreach (KeyValuePair<UUID,GroupMember> a in e.Members)
|
||||
{
|
||||
groupMembers[e.GroupID].Add(a.Value.ID);
|
||||
if (groupMembers.ContainsKey(e.GroupID) == true)
|
||||
{
|
||||
groupMembers.Remove(e.GroupID);
|
||||
}
|
||||
groupMembers.Add(e.GroupID, new List<UUID>());
|
||||
foreach (KeyValuePair<UUID, GroupMember> a in e.Members)
|
||||
{
|
||||
groupMembers[e.GroupID].Add(a.Value.ID);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -678,7 +696,10 @@ namespace SecondBotEvents.Services
|
|||
|
||||
protected void EstateBans(object o, EstateBansReplyEventArgs e)
|
||||
{
|
||||
estateBanlist = e.Banned;
|
||||
lock (estateBanlist)
|
||||
{
|
||||
estateBanlist = e.Banned;
|
||||
}
|
||||
}
|
||||
|
||||
protected void BotLoggedIn(object o, SimConnectedEventArgs e)
|
||||
|
|
@ -733,35 +754,38 @@ namespace SecondBotEvents.Services
|
|||
|
||||
protected void GroupCurrent(object o, CurrentGroupsEventArgs e)
|
||||
{
|
||||
List<UUID> missingGroups = groupsKey2Name.Keys.ToList();
|
||||
foreach(Group G in e.Groups.Values)
|
||||
lock (groupsKey2Name)
|
||||
{
|
||||
missingGroups.Remove(G.ID);
|
||||
if (groupsKey2Name.ContainsKey(G.ID) == true)
|
||||
List<UUID> missingGroups = groupsKey2Name.Keys.ToList();
|
||||
foreach (Group G in e.Groups.Values)
|
||||
{
|
||||
continue;
|
||||
missingGroups.Remove(G.ID);
|
||||
if (groupsKey2Name.ContainsKey(G.ID) == true)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
groupsKey2Name.Add(G.ID, G.Name);
|
||||
getClient().Self.RequestJoinGroupChat(G.ID);
|
||||
if (myConfig.GetPrefetchGroupMembers() == true)
|
||||
{
|
||||
getClient().Groups.RequestGroupMembers(G.ID);
|
||||
}
|
||||
if (myConfig.GetPrefetchGroupRoles() == true)
|
||||
{
|
||||
getClient().Groups.RequestGroupRoles(G.ID);
|
||||
}
|
||||
}
|
||||
groupsKey2Name.Add(G.ID, G.Name);
|
||||
getClient().Self.RequestJoinGroupChat(G.ID);
|
||||
if (myConfig.GetPrefetchGroupMembers() == true)
|
||||
{
|
||||
getClient().Groups.RequestGroupMembers(G.ID);
|
||||
}
|
||||
if(myConfig.GetPrefetchGroupRoles() == true)
|
||||
{
|
||||
getClient().Groups.RequestGroupRoles(G.ID);
|
||||
}
|
||||
}
|
||||
|
||||
foreach(UUID G in missingGroups)
|
||||
{
|
||||
if (groupsKey2Name.ContainsKey(G) == false)
|
||||
foreach (UUID G in missingGroups)
|
||||
{
|
||||
continue;
|
||||
if (groupsKey2Name.ContainsKey(G) == false)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
string name = groupsKey2Name[G];
|
||||
groupsKey2Name.Remove(G);
|
||||
closeChat(G);
|
||||
}
|
||||
string name = groupsKey2Name[G];
|
||||
groupsKey2Name.Remove(G);
|
||||
closeChat(G);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -777,11 +801,14 @@ namespace SecondBotEvents.Services
|
|||
|
||||
protected void addAvatar(UUID id, string name)
|
||||
{
|
||||
if (avatarsName2Key.ContainsValue(id) == true)
|
||||
lock (avatarsName2Key)
|
||||
{
|
||||
return;
|
||||
if (avatarsName2Key.ContainsValue(id) == true)
|
||||
{
|
||||
return;
|
||||
}
|
||||
avatarsName2Key.Add(name, id);
|
||||
}
|
||||
avatarsName2Key.Add(name, id);
|
||||
}
|
||||
|
||||
protected void AvatarUUIDName(object o, UUIDNameReplyEventArgs e)
|
||||
|
|
@ -878,14 +905,14 @@ namespace SecondBotEvents.Services
|
|||
|
||||
public class CommandHistory
|
||||
{
|
||||
public UUID Source = UUID.Zero;
|
||||
public string Command = "";
|
||||
public string[] Args = new string[] { };
|
||||
public long Unixtime = 0;
|
||||
public bool status = false;
|
||||
|
||||
public CommandHistory(UUID setSource, string setCommand, string[] setArgs, long setUnixtime)
|
||||
public CommandHistory(bool setStatus, string setCommand, string[] setArgs, long setUnixtime)
|
||||
{
|
||||
Source = setSource;
|
||||
status = setStatus;
|
||||
Command = setCommand;
|
||||
Args = setArgs;
|
||||
Unixtime = setUnixtime;
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ using System.Threading.Tasks;
|
|||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public class DiscordService : Services
|
||||
public class DiscordService : BotServices
|
||||
{
|
||||
public Config.DiscordConfig myConfig = null;
|
||||
public bool acceptChat = false;
|
||||
|
|
|
|||
308
SecondBotEvents/Services/HomeboundService.cs
Normal file
308
SecondBotEvents/Services/HomeboundService.cs
Normal file
|
|
@ -0,0 +1,308 @@
|
|||
using OpenMetaverse;
|
||||
using SecondBotEvents.Config;
|
||||
using System;
|
||||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public class HomeboundService : BotServices
|
||||
{
|
||||
protected HomeboundConfig myConfig;
|
||||
protected bool botConnected = false;
|
||||
|
||||
|
||||
protected SimSlURL home = null;
|
||||
protected SimSlURL backup = null;
|
||||
protected UUID sitTarget = UUID.Zero;
|
||||
protected long lastAlertTeleport = 0;
|
||||
protected bool evacWanted = false;
|
||||
protected bool gotoPosAttemptedTp = false;
|
||||
protected bool gotoPosAttemptedWalk = false;
|
||||
protected long lastGotoAction = 0;
|
||||
protected bool softDisable = false;
|
||||
protected bool closeToHome = false;
|
||||
|
||||
public void markTeleport()
|
||||
{
|
||||
softDisable = true;
|
||||
}
|
||||
|
||||
public HomeboundService(EventsSecondBot setMaster) : base(setMaster)
|
||||
{
|
||||
myConfig = new HomeboundConfig(master.fromEnv, master.fromFolder);
|
||||
if (myConfig.GetEnabled() == false)
|
||||
{
|
||||
return;
|
||||
}
|
||||
home = new SimSlURL(myConfig.GetHomeSimSlUrl());
|
||||
backup = new SimSlURL(myConfig.GetBackupSimSLUrl());
|
||||
if(UUID.TryParse(myConfig.GetAtHomeAutoSitUuid(), out sitTarget) == false)
|
||||
{
|
||||
sitTarget = UUID.Zero;
|
||||
}
|
||||
}
|
||||
|
||||
protected string simNickname = "";
|
||||
protected bool attemptedTeleportHome = false;
|
||||
protected bool attemptedTeleportBackup = false;
|
||||
protected long teleportActionLockout = 0;
|
||||
|
||||
protected void Tick()
|
||||
{
|
||||
if (evacWanted == true)
|
||||
{
|
||||
BotAlertMessage(null, new AlertMessageEventArgs("restart", "999", new OpenMetaverse.StructuredData.OSDMap()));
|
||||
}
|
||||
if (getClient().Network.CurrentSim.Name == home.name)
|
||||
{
|
||||
simNickname = "Home # ";
|
||||
if (sitTarget != UUID.Zero)
|
||||
{
|
||||
if (getClient().Self.SittingOn == 0)
|
||||
{
|
||||
getClient().Self.RequestSit(sitTarget, Vector3.Zero);
|
||||
}
|
||||
}
|
||||
if (myConfig.GetAtHomeSeekLocation() == true)
|
||||
{
|
||||
GetToPos(home);
|
||||
}
|
||||
return;
|
||||
}
|
||||
else if (getClient().Network.CurrentSim.Name == backup.name)
|
||||
{
|
||||
simNickname = "Backup # ";
|
||||
if (myConfig.GetAtBackupSeekLocation() == true)
|
||||
{
|
||||
GetToPos(backup);
|
||||
}
|
||||
return;
|
||||
}
|
||||
if (simNickname == "")
|
||||
{
|
||||
simNickname = "Someplace # ";
|
||||
return;
|
||||
}
|
||||
long dif = SecondbotHelpers.UnixTimeNow() - teleportActionLockout;
|
||||
if(dif < 30)
|
||||
{
|
||||
return;
|
||||
}
|
||||
teleportActionLockout = SecondbotHelpers.UnixTimeNow();
|
||||
if (attemptedTeleportHome == false)
|
||||
{
|
||||
attemptedTeleportHome = true;
|
||||
LogFormater.Info("Teleporting to home sim");
|
||||
getClient().Self.Teleport(home.name, new Vector3(home.x, home.y, home.z), new Vector3(0, 0, 0));
|
||||
return;
|
||||
}
|
||||
else if(attemptedTeleportBackup == false)
|
||||
{
|
||||
attemptedTeleportBackup = true;
|
||||
LogFormater.Info("Teleporting to backup sim");
|
||||
teleportActionLockout = SecondbotHelpers.UnixTimeNow();
|
||||
getClient().Self.Teleport(backup.name, new Vector3(backup.x, backup.y, backup.z), new Vector3(0, 0, 0));
|
||||
return;
|
||||
}
|
||||
attemptedTeleportHome = false;
|
||||
attemptedTeleportBackup = false;
|
||||
LogFormater.Warn("Both home and backup sims failed clearing and trying again");
|
||||
}
|
||||
|
||||
public override string Status()
|
||||
{
|
||||
if(myConfig == null)
|
||||
{
|
||||
return simNickname + "Config broken";
|
||||
}
|
||||
if(botConnected == false)
|
||||
{
|
||||
return simNickname + "No bot";
|
||||
}
|
||||
if(softDisable == false)
|
||||
{
|
||||
Tick();
|
||||
if(evacWanted == true)
|
||||
{
|
||||
return simNickname + "Waiting to evac";
|
||||
}
|
||||
else if(getClient().Self.SittingOn != 0)
|
||||
{
|
||||
return simNickname + "Sitting on a thing";
|
||||
}
|
||||
else if(closeToHome == true)
|
||||
{
|
||||
return simNickname + "In a safe space";
|
||||
}
|
||||
else if(gotoPosAttemptedWalk == true)
|
||||
{
|
||||
return simNickname + "Trying to auto pilot";
|
||||
}
|
||||
else if(gotoPosAttemptedTp == true)
|
||||
{
|
||||
return simNickname + "Trying to TP to location";
|
||||
}
|
||||
return simNickname + "Waiting";
|
||||
}
|
||||
return simNickname + "Standby - teleported by master / script";
|
||||
}
|
||||
|
||||
protected void GetToPos(SimSlURL location)
|
||||
{
|
||||
if (getClient().Self.SittingOn != 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
long dif = SecondbotHelpers.UnixTimeNow() - lastGotoAction;
|
||||
if (dif < 30)
|
||||
{
|
||||
return;
|
||||
}
|
||||
lastGotoAction = SecondbotHelpers.UnixTimeNow();
|
||||
float dist = Vector3.Distance(new Vector3(location.x, location.y, location.z), getClient().Self.SimPosition);
|
||||
if(dist < 1)
|
||||
{
|
||||
closeToHome = true;
|
||||
if (gotoPosAttemptedWalk == true)
|
||||
{
|
||||
getClient().Self.AutoPilotCancel();
|
||||
}
|
||||
gotoPosAttemptedWalk = false;
|
||||
gotoPosAttemptedTp = false;
|
||||
return;
|
||||
}
|
||||
if (gotoPosAttemptedTp == false)
|
||||
{
|
||||
gotoPosAttemptedTp = true;
|
||||
getClient().Self.Teleport(location.name, new Vector3(location.x, location.y, location.z), new Vector3(0, 0, 0));
|
||||
return;
|
||||
}
|
||||
if(gotoPosAttemptedWalk == false)
|
||||
{
|
||||
gotoPosAttemptedWalk = true;
|
||||
getClient().Self.AutoPilotLocal(location.x, location.y, location.z);
|
||||
return;
|
||||
}
|
||||
getClient().Self.AutoPilotCancel();
|
||||
gotoPosAttemptedWalk = false;
|
||||
}
|
||||
|
||||
protected void BotChangedSim(object o, SimChangedEventArgs e)
|
||||
{
|
||||
gotoPosAttemptedTp = false;
|
||||
evacWanted = false;
|
||||
gotoPosAttemptedWalk = false;
|
||||
closeToHome = false;
|
||||
simNickname = "";
|
||||
attemptedTeleportHome = false;
|
||||
attemptedTeleportBackup = false;
|
||||
lastGotoAction = SecondbotHelpers.UnixTimeNow();
|
||||
teleportActionLockout = SecondbotHelpers.UnixTimeNow() + 30;
|
||||
}
|
||||
|
||||
protected void BotAlertMessage(object o, AlertMessageEventArgs e)
|
||||
{
|
||||
if (e.Message.ToLower().Contains("restart") == false)
|
||||
{
|
||||
return;
|
||||
}
|
||||
long dif = SecondbotHelpers.UnixTimeNow() - lastAlertTeleport;
|
||||
if (dif < 60)
|
||||
{
|
||||
if (evacWanted == false)
|
||||
{
|
||||
LogFormater.Warn("Evac wanted due to restart");
|
||||
evacWanted = true;
|
||||
}
|
||||
return;
|
||||
}
|
||||
evacWanted = false;
|
||||
if (getClient().Network.CurrentSim.Name == home.name)
|
||||
{
|
||||
LogFormater.Info("Teleporting to backup sim to avoid restart");
|
||||
getClient().Self.Teleport(backup.name, new Vector3(backup.x, backup.y, backup.z), new Vector3(0, 0, 0));
|
||||
return;
|
||||
}
|
||||
LogFormater.Info("Teleporting to home sim to avoid restart");
|
||||
getClient().Self.Teleport(home.name, new Vector3(home.x, home.y, home.z), new Vector3(0, 0, 0));
|
||||
}
|
||||
|
||||
protected void BotClientRestart(object o, BotClientNotice e)
|
||||
{
|
||||
botConnected = false;
|
||||
Console.WriteLine("Homebound Service [Attached to new client]");
|
||||
getClient().Network.LoggedOut += BotLoggedOut;
|
||||
getClient().Network.SimConnected += BotLoggedIn;
|
||||
getClient().Self.AlertMessage += BotAlertMessage;
|
||||
getClient().Network.SimChanged += BotChangedSim;
|
||||
}
|
||||
|
||||
protected void BotLoggedOut(object o, LoggedOutEventArgs e)
|
||||
{
|
||||
lastAlertTeleport = 0;
|
||||
evacWanted = false;
|
||||
botConnected = false;
|
||||
gotoPosAttemptedTp = false;
|
||||
evacWanted = false;
|
||||
gotoPosAttemptedWalk = false;
|
||||
softDisable = false;
|
||||
closeToHome = false;
|
||||
lastGotoAction = SecondbotHelpers.UnixTimeNow();
|
||||
Console.WriteLine("Homebound Service [Standby]");
|
||||
}
|
||||
protected void BotLoggedIn(object o, SimConnectedEventArgs e)
|
||||
{
|
||||
botConnected = true;
|
||||
Console.WriteLine("Homebound Service [Active]");
|
||||
}
|
||||
|
||||
public override void Start()
|
||||
{
|
||||
if(myConfig.GetEnabled() == false)
|
||||
{
|
||||
return;
|
||||
}
|
||||
Stop();
|
||||
master.BotClientNoticeEvent += BotClientRestart;
|
||||
Console.WriteLine("Homebound Service [Starting]");
|
||||
}
|
||||
|
||||
public override void Stop()
|
||||
{
|
||||
master.BotClientNoticeEvent -= BotClientRestart;
|
||||
if (master.botClient != null)
|
||||
{
|
||||
if (getClient() != null)
|
||||
{
|
||||
getClient().Network.SimConnected -= BotLoggedIn;
|
||||
getClient().Self.AlertMessage -= BotAlertMessage;
|
||||
getClient().Network.SimChanged -= BotChangedSim;
|
||||
}
|
||||
}
|
||||
Console.WriteLine("Homebound Service [Stopping]");
|
||||
}
|
||||
}
|
||||
|
||||
public class SimSlURL
|
||||
{
|
||||
public string name;
|
||||
public int x = 0;
|
||||
public int y = 0;
|
||||
public int z = 0;
|
||||
public SimSlURL(string url)
|
||||
{
|
||||
// http://maps.secondlife.com/secondlife/Viserion/66/166/23
|
||||
url = url.Replace("maps.secondlife.com/secondlife/", "");
|
||||
url = url.Replace("http://", "");
|
||||
url = url.Replace("https://", "");
|
||||
// Viserion/66/166/23
|
||||
string[] bits = url.Split("/");
|
||||
name = System.Net.WebUtility.UrlDecode(bits[0]);
|
||||
x = int.Parse(bits[1]);
|
||||
y = int.Parse(bits[2]);
|
||||
z = int.Parse(bits[3]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
|
@ -1,18 +1,18 @@
|
|||
using EmbedIO;
|
||||
using EmbedIO.Actions;
|
||||
using EmbedIO.Routing;
|
||||
using EmbedIO.WebApi;
|
||||
using Newtonsoft.Json;
|
||||
using OpenMetaverse;
|
||||
using SecondBotEvents.Commands;
|
||||
using SecondBotEvents.Config;
|
||||
using Swan.Logging;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Net;
|
||||
using System.Threading;
|
||||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public class HttpService : Services
|
||||
public class HttpService : BotServices
|
||||
{
|
||||
protected WebServer HTTPendpoint = null;
|
||||
protected HttpConfig myConfig;
|
||||
|
|
@ -27,26 +27,31 @@ namespace SecondBotEvents.Services
|
|||
}
|
||||
}
|
||||
|
||||
public bool GetAcceptBotCommands()
|
||||
{
|
||||
return acceptBotCommands;
|
||||
}
|
||||
|
||||
public override string Status()
|
||||
{
|
||||
if (myConfig == null)
|
||||
{
|
||||
return "HTTP service [Config status broken]";
|
||||
return "Config broken";
|
||||
}
|
||||
if (myConfig.GetEnabled() == false)
|
||||
{
|
||||
return "HTTP service [- Not requested -]";
|
||||
return "- Not requested -";
|
||||
}
|
||||
// @todo HTTP server check here
|
||||
if (HTTPendpoint == null)
|
||||
{
|
||||
return "HTTP endpoint not online";
|
||||
return "not online";
|
||||
}
|
||||
if (acceptBotCommands == false)
|
||||
{
|
||||
return "Active [Service]";
|
||||
return "Active ~ Service";
|
||||
}
|
||||
return "Active [Commands]";
|
||||
return "Active ~ Commands";
|
||||
}
|
||||
|
||||
protected void BotClientRestart(object o, BotClientNotice e)
|
||||
|
|
@ -68,7 +73,7 @@ namespace SecondBotEvents.Services
|
|||
{
|
||||
getClient().Network.SimConnected -= BotLoggedIn;
|
||||
acceptBotCommands = true;
|
||||
Console.WriteLine("HTTP service [Bot commands enabled]");
|
||||
CreateWebServer();
|
||||
}
|
||||
|
||||
public override void Start()
|
||||
|
|
@ -80,8 +85,6 @@ namespace SecondBotEvents.Services
|
|||
}
|
||||
Stop();
|
||||
master.BotClientNoticeEvent += BotClientRestart;
|
||||
Console.WriteLine("HTTP service [Enabled]");
|
||||
CreateWebServer();
|
||||
}
|
||||
|
||||
public override void Stop()
|
||||
|
|
@ -103,12 +106,14 @@ namespace SecondBotEvents.Services
|
|||
{
|
||||
Swan.Logging.Logger.UnregisterLogger<ConsoleLogger>();
|
||||
HTTPendpoint = new WebServer(o => o
|
||||
.WithUrlPrefix(myConfig.GetHost())
|
||||
.WithMode(HttpListenerMode.EmbedIO))
|
||||
.WithUrlPrefix("http://*:" + myConfig.GetPort().ToString())
|
||||
.WithMode(HttpListenerMode.EmbedIO))
|
||||
.WithCors()
|
||||
.WithWebApi("/api", m => m.WithController(() => new HttpWebBot(master)))
|
||||
.WithModule(new ActionModule("/", HttpVerbs.Any, ctx => ctx.SendDataAsync(new { Message = "Error" }))
|
||||
);
|
||||
HTTPendpoint.RunAsync();
|
||||
Console.WriteLine("HTTP service [Enabled] on port "+ myConfig.GetPort().ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -170,13 +175,13 @@ namespace SecondBotEvents.Services
|
|||
|
||||
protected object BasicReply(string input, string[] args, string command)
|
||||
{
|
||||
// @todo Command history storage system
|
||||
master.DataStoreService.addCommandToHistory(true, command, args);
|
||||
return new { reply = input, status = false };
|
||||
}
|
||||
|
||||
protected object Failure(string input, string command, string[] args, string whyfailed)
|
||||
{
|
||||
// @todo Command history storage system
|
||||
master.DataStoreService.addCommandToHistory(false, command, args);
|
||||
return new { reply = input, status = false };
|
||||
}
|
||||
|
||||
|
|
@ -240,4 +245,51 @@ namespace SecondBotEvents.Services
|
|||
this.about = about;
|
||||
}
|
||||
}
|
||||
|
||||
public class SecondbotWebApi : WebApiController
|
||||
{
|
||||
protected EventsSecondBot master;
|
||||
public SecondbotWebApi(EventsSecondBot setmaster)
|
||||
{
|
||||
master = setmaster;
|
||||
}
|
||||
}
|
||||
|
||||
public class HttpWebBot : SecondbotWebApi
|
||||
{
|
||||
public HttpWebBot(EventsSecondBot setmaster) : base(setmaster) { }
|
||||
|
||||
[About("Runs a command on the bot")]
|
||||
[ReturnHints("command reply")]
|
||||
[ReturnHintsFailure("Bad token signing")]
|
||||
[ArgHints("commandName", "the name of the command to run")]
|
||||
[ArgHints("args", "a list of args formated with ~#~ as the split points")]
|
||||
[ArgHints("signing", "a sha1 hash that meets level 3 API signing spec [see github wiki]")]
|
||||
[ArgHints("unixtime", "the time you signed the command")]
|
||||
[Route(HttpVerbs.Post, "/Run")]
|
||||
|
||||
public string Run([FormField] string commandName, [FormField] string? args, [FormField] string signing, [FormField] string unixtime)
|
||||
{
|
||||
string input = commandName;
|
||||
string[] myArgs = new string[] { };
|
||||
if(args != null)
|
||||
{
|
||||
myArgs = args.Split("~#~", StringSplitOptions.RemoveEmptyEntries);
|
||||
}
|
||||
if(int.TryParse(unixtime, out int cmdUnixtime) == false)
|
||||
{
|
||||
return "Invaild unixtime was sent";
|
||||
}
|
||||
if (master.HttpService.GetAcceptBotCommands() == false)
|
||||
{
|
||||
return "No bot connected yet";
|
||||
}
|
||||
SignedCommand C = new SignedCommand(commandName, signing, myArgs, cmdUnixtime, null, true, 5, master.CommandsService.myConfig.GetSharedSecret());
|
||||
if(C.accepted == false)
|
||||
{
|
||||
return "Command request rejected";
|
||||
}
|
||||
return JsonConvert.SerializeObject(master.CommandsService.runCommand(C));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ using System.Collections.Generic;
|
|||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public class InteractionService : Services
|
||||
public class InteractionService : BotServices
|
||||
{
|
||||
protected InteractionConfig myConfig;
|
||||
protected bool botConnected = false;
|
||||
|
|
@ -26,13 +26,17 @@ namespace SecondBotEvents.Services
|
|||
{
|
||||
if(myConfig == null)
|
||||
{
|
||||
return "Interaction Service [Config status broken]";
|
||||
return "Config broken";
|
||||
}
|
||||
if (myConfig.GetEnabled() == false)
|
||||
{
|
||||
return "Interaction Service [- Not requested -]";
|
||||
return "- Not requested -";
|
||||
}
|
||||
return "Interaction Service [Waiting for bot]";
|
||||
if (botConnected == false)
|
||||
{
|
||||
return "Waiting for bot";
|
||||
}
|
||||
return "Active";
|
||||
}
|
||||
|
||||
protected bool processRequest(bool enabledByConfig, string avatarName, string sourceName)
|
||||
|
|
@ -90,12 +94,18 @@ namespace SecondBotEvents.Services
|
|||
return;
|
||||
}
|
||||
string mode = "Teleport Bot to Av";
|
||||
bool markTeleport = true;
|
||||
if (e.IM.Dialog == InstantMessageDialog.RequestLure)
|
||||
{
|
||||
mode = "Teleport Av to Bot";
|
||||
markTeleport = false;
|
||||
}
|
||||
if (processRequest(myConfig.GetAcceptTeleports(), e.IM.FromAgentName, mode) == false)
|
||||
{
|
||||
if(markTeleport == true)
|
||||
{
|
||||
master.HomeboundService.markTeleport();
|
||||
}
|
||||
if (e.IM.Dialog != InstantMessageDialog.RequestLure)
|
||||
{
|
||||
return;
|
||||
|
|
|
|||
|
|
@ -5,10 +5,10 @@ using System.Text;
|
|||
|
||||
namespace SecondBotEvents.Services
|
||||
{
|
||||
public abstract class Services
|
||||
public abstract class BotServices
|
||||
{
|
||||
public EventsSecondBot master;
|
||||
public Services(EventsSecondBot setMaster)
|
||||
public BotServices(EventsSecondBot setMaster)
|
||||
{
|
||||
master = setMaster;
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue