]> jfr.im git - z_archive/kelsier.git/commitdiff
Added bot class, misc other changes
authorJohn Runyon <redacted>
Fri, 12 Apr 2013 20:31:29 +0000 (15:31 -0500)
committerJohn Runyon <redacted>
Fri, 12 Apr 2013 20:31:29 +0000 (15:31 -0500)
Bot.cs [new file with mode: 0644]
Database.cs
Kelsier.csproj
Logger.cs
Program.cs
dbdump.sql [new file with mode: 0644]

diff --git a/Bot.cs b/Bot.cs
new file mode 100644 (file)
index 0000000..29f77e9
--- /dev/null
+++ b/Bot.cs
@@ -0,0 +1,111 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using MySql.Data.MySqlClient;
+using System.Net;
+using System.Net.Sockets;
+
+namespace Kelsier {
+    class Bot {
+        public int id { get; private set; }
+
+        public string nick { get; private set; }
+        public string ident { get; private set; }
+        public string realname { get; private set; }
+        public string localip { get; private set; }
+        public string server { get; private set; }
+        public int serverport { get; private set; }
+
+        private IPEndPoint local;
+
+        private Socket s;
+        public bool online { get; private set; }
+
+        private Logger log;
+
+
+        public Bot(int id) {
+            this.id = id;
+
+            this.log = new Logger(id.ToString("0000"), Root.log);
+
+            MySqlDataReader rdr = Root.db.queryReader("SELECT nick, ident, realname, bindip, server, serverport FROM bots WHERE id = @id", new object[] { "@id", id });
+            rdr.Read();
+
+            this.nick = rdr.GetString("nick");
+            this.ident = rdr.GetString("ident");
+            this.realname = rdr.GetString("realname");
+
+            if (rdr.IsDBNull(rdr.GetOrdinal("bindip"))) {
+                this.localip = null;
+                this.local = new IPEndPoint(IPAddress.Any, 0);
+            } else {
+                this.localip = rdr.GetString("bindip");
+                this.local = new IPEndPoint(IPAddress.Parse(this.localip), 0);
+            }
+
+            this.server = rdr.GetString("server");
+            this.serverport = rdr.GetInt32("serverport");
+        }
+
+        public string connect() {
+            if (online) throw new InvalidStateException();
+
+            s = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
+            s.Bind(local);
+            s.Connect(server, serverport);
+
+            Stator rcvstate = new Stator();
+            s.BeginReceive(rcvstate.buffer, 0, 1, SocketFlags.None, new AsyncCallback(dataIn), rcvstate);
+
+            return "TODO";
+        }
+
+        public void dataIn(IAsyncResult ar) {
+            Stator rcvstate = (Stator)ar.AsyncState;
+            s.EndReceive(ar);
+
+            if (rcvstate.buffer[0] == '\n') {
+                processData(rcvstate.buffersb.ToString());
+                rcvstate = new Stator();
+            } else {
+                rcvstate.buffersb.Append(Encoding.ASCII.GetString(rcvstate.buffer, 0, 1));
+            }
+            s.BeginReceive(rcvstate.buffer, 0, 1, SocketFlags.None, new AsyncCallback(dataIn), rcvstate);
+        }
+        private void send(string data, params object[] args) {
+            log.debug(">>> " + data);
+            s.Send(Encoding.ASCII.GetBytes(data + "\n"));
+        }
+
+        private void processData(string data) {
+            log.debug("<<< " + data);
+
+            if (!online) { register(); return; }
+
+            short numeric;
+            if (data.StartsWith(":") && Int16.TryParse(data.Substring(data.IndexOf(' ')+1, 3), out numeric)) {
+                if (numeric == 1) {
+                    send("JOIN #mustis");
+                    send("PRIVMSG #mustis :lolol!");
+                }
+            } else if (data.Substring(0, 4) == "PING") {
+                send("PONG" + data.Substring(4));
+            }
+        }
+
+        private void register() {
+            send(String.Format("NICK {0}", nick));
+            send(String.Format("USER {0} * * :{1}", ident, realname));
+            online = true;
+        }
+    }
+
+    class InvalidStateException : Exception { }
+
+    class Stator {
+        public byte[] buffer = new byte[1];
+        public StringBuilder buffersb = new StringBuilder();
+    }
+}
index 6497ca28f6d4e8956925bccd67dda68e8ff562c9..6f70a5ce3ea22abdd57ede17d1712bf5c4bae86f 100644 (file)
@@ -6,8 +6,9 @@
 
 namespace Kelsier {
     class Database {
-        protected MySqlConnection _dbh = null;
-        public MySqlConnection dbh { get { return _dbh; } }
+        public MySqlConnection dbh { get; private set; }
+
+        private string dbinfo;
 
 
         /// <summary>
@@ -15,25 +16,75 @@ class Database {
         /// </summary>
         /// <param name="dbinfo">Connector string</param>
         public Database(string dbinfo) {
-            _dbh = new MySqlConnection(dbinfo);
+            this.dbinfo = dbinfo;
+
+            dbh = new MySqlConnection(this.dbinfo);
+            dbh.Open();
+        }
+        public Database(Database copy) {
+            this.dbinfo = copy.dbinfo;
+
+            dbh = new MySqlConnection(this.dbinfo);
+            dbh.Open();
+        }
+
+        ~Database() {
+            dbh.Close();
         }
 
-        public void Connect() {
-            try {
-                dbh.Open();
-            } catch (MySqlException e) {
-                Root.log.error("Error: {0}", e.ToString());
+        public int execute(string query) {
+            MySqlCommand cmdo = new MySqlCommand(query, dbh);
+            return cmdo.ExecuteNonQuery();
+        }
+        public int execute(string query, object[] keys) {
+            MySqlCommand cmdo = new MySqlCommand();
+            cmdo.Connection = dbh;
+            cmdo.CommandText = query;
+            cmdo.Prepare();
+
+            for (int i = 0; i < keys.Length; i += 2) {
+                cmdo.Parameters.AddWithValue(keys[i].ToString(), keys[i + 1]);
             }
+
+            return cmdo.ExecuteNonQuery();
         }
 
         public object queryScalar(string query) {
             MySqlCommand cmdo = new MySqlCommand(query, dbh);
             return cmdo.ExecuteScalar();
         }
+        public object queryScalar(string query, object[] keys) {
+            MySqlCommand cmdo = new MySqlCommand();
+            cmdo.Connection = dbh;
+            cmdo.CommandText = query;
+            cmdo.Prepare();
+
+            for (int i = 0; i < keys.Length; i += 2) {
+                cmdo.Parameters.AddWithValue(keys[i].ToString(), keys[i + 1]);
+            }
+
+            return cmdo.ExecuteScalar();
+        }
 
         public MySqlDataReader queryReader(string query) {
             MySqlCommand cmdo = new MySqlCommand(query, dbh);
             return cmdo.ExecuteReader();
         }
+        public MySqlDataReader queryReader(string query, object[] keys) {
+            if (keys.Length % 2 != 0) {
+                throw new PlaceholdersException();
+            }
+            MySqlCommand cmdo = new MySqlCommand();
+            cmdo.Connection = dbh;
+            cmdo.CommandText = query;
+            cmdo.Prepare();
+
+            for (int i = 0; i < keys.Length; i += 2) {
+                cmdo.Parameters.AddWithValue(keys[i].ToString(), keys[i + 1]);
+            }
+            return cmdo.ExecuteReader();
+        }
     }
+
+    class PlaceholdersException : Exception { }
 }
index 40f73ef65331d655d70943e2648126aa813dde30..45ce524ce3f83cad0d38ccefdab62458b515e5dd 100644 (file)
     <TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
     <TargetFrameworkProfile>Client</TargetFrameworkProfile>
     <FileAlignment>512</FileAlignment>
+    <PublishUrl>publish\</PublishUrl>
+    <Install>true</Install>
+    <InstallFrom>Disk</InstallFrom>
+    <UpdateEnabled>false</UpdateEnabled>
+    <UpdateMode>Foreground</UpdateMode>
+    <UpdateInterval>7</UpdateInterval>
+    <UpdateIntervalUnits>Days</UpdateIntervalUnits>
+    <UpdatePeriodically>false</UpdatePeriodically>
+    <UpdateRequired>false</UpdateRequired>
+    <MapFileExtensions>true</MapFileExtensions>
+    <ApplicationRevision>0</ApplicationRevision>
+    <ApplicationVersion>1.0.0.%2a</ApplicationVersion>
+    <IsWebBootstrapper>false</IsWebBootstrapper>
+    <UseApplicationTrust>false</UseApplicationTrust>
+    <BootstrapperEnabled>true</BootstrapperEnabled>
   </PropertyGroup>
   <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|x86' ">
     <PlatformTarget>x86</PlatformTarget>
@@ -44,6 +59,7 @@
     <Reference Include="System.Xml" />
   </ItemGroup>
   <ItemGroup>
+    <Compile Include="Bot.cs" />
     <Compile Include="Database.cs" />
     <Compile Include="Logger.cs" />
     <Compile Include="Program.cs" />
       <LastGenOutput>Settings.Designer.cs</LastGenOutput>
     </None>
   </ItemGroup>
+  <ItemGroup>
+    <BootstrapperPackage Include=".NETFramework,Version=v4.0,Profile=Client">
+      <Visible>False</Visible>
+      <ProductName>Microsoft .NET Framework 4 Client Profile %28x86 and x64%29</ProductName>
+      <Install>true</Install>
+    </BootstrapperPackage>
+    <BootstrapperPackage Include="Microsoft.Net.Client.3.5">
+      <Visible>False</Visible>
+      <ProductName>.NET Framework 3.5 SP1 Client Profile</ProductName>
+      <Install>false</Install>
+    </BootstrapperPackage>
+    <BootstrapperPackage Include="Microsoft.Net.Framework.3.5.SP1">
+      <Visible>False</Visible>
+      <ProductName>.NET Framework 3.5 SP1</ProductName>
+      <Install>false</Install>
+    </BootstrapperPackage>
+    <BootstrapperPackage Include="Microsoft.Windows.Installer.3.1">
+      <Visible>False</Visible>
+      <ProductName>Windows Installer 3.1</ProductName>
+      <Install>true</Install>
+    </BootstrapperPackage>
+  </ItemGroup>
   <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
+  <PropertyGroup>
+    <PostBuildEvent>
+    </PostBuildEvent>
+  </PropertyGroup>
   <!-- To modify your build process, add your task inside one of the targets below and uncomment it. 
        Other similar extension points exist, see Microsoft.Common.targets.
   <Target Name="BeforeBuild">
index bbe14d183cf8b3b5908c54a0044ee2bf680a509f..230a5971e13a3673070ccfc26fad54e1f27439d6 100644 (file)
--- a/Logger.cs
+++ b/Logger.cs
@@ -6,7 +6,10 @@
 
 namespace Kelsier {
     class Logger {
-        protected TextWriter[] debugs, infos, errors;
+        public LogOutput[] debugs {get; private set; }
+        public LogOutput[] infos { get; private set; }
+        public LogOutput[] errors { get; private set; }
+        public string from { get; private set; }
 
         /// <summary>
         /// Construct a Logger, writing to the specified TextWriter objects. Use an empty array to disable an output.
@@ -14,25 +17,30 @@ class Logger {
         /// <param name="debugs">Array of TextWriter's to use for debug output</param>
         /// <param name="infos">...for info output</param>
         /// <param name="errors">...for error output</param>
-        public Logger(TextWriter[] debugs, TextWriter[] infos, TextWriter[] errors) {
+        public Logger(string from, LogOutput[] debugs, LogOutput[] infos, LogOutput[] errors) {
+            int fromid;
+            if (Int32.TryParse(from, out fromid)) {
+                this.from = fromid.ToString("0000");
+            } else {
+                this.from = from;
+            }
+
             this.debugs = debugs;
             this.infos = infos;
             this.errors = errors;
 
-            this.debug("Starting logging (debug) here at {0}", DateTime.Now.ToString("F"));
-            this.info("Starting logging (info) here at {0}", DateTime.Now.ToString("F"));
-            this.error("Starting logging (error) here at {0}", DateTime.Now.ToString("F"));
+            if (from == "Root") {
+                this.debug("Starting Root logging (debug) here at "+DateTime.Now.ToString("F"));
+                this.info("Starting Root logging (info) here at "+DateTime.Now.ToString("F"));
+                this.error("Starting Root logging (error) here at "+DateTime.Now.ToString("F"));
+            }
         }
+        public Logger(string from, Logger copy) {
+            this.from = from;
 
-        ~Logger() {
-            this.debug("Stopping logging (debug) here at {0}", DateTime.Now.ToString("F"));
-            this.info("Stopping logging (info) here at {0}", DateTime.Now.ToString("F"));
-            this.error("Stopping logging (error) here at {0}", DateTime.Now.ToString("F"));
-            foreach (TextWriter[] group in new TextWriter[][] { this.debugs, this.infos, this.errors }) {
-                foreach (TextWriter outw in group) {
-                    outw.Close();
-                }
-            }
+            this.debugs = copy.debugs;
+            this.infos = copy.infos;
+            this.errors = copy.infos;
         }
 
         /// <summary>
@@ -40,9 +48,10 @@ class Logger {
         /// </summary>
         /// <param name="msg">Log message (with formatting placeholders, if desired)</param>
         /// <param name="args">Formatting replacements.</param>
-        public void debug(string msg, params object[] args) {
-            foreach (TextWriter outw in this.debugs) {
-                outw.WriteLine("(D@" + DateTime.Now.ToString("HH:mm:ss") + ")[MAIN] " + msg, args);
+        public void debug(object msg) {
+            foreach (LogOutput outw in debugs) {
+                if (outw.open)
+                    outw.writer.WriteLine("(D@" + DateTime.Now.ToString("HH:mm:ss") + ")[" + from + "] " + msg.ToString());
             }
         }
 
@@ -51,9 +60,10 @@ class Logger {
         /// </summary>
         /// <param name="msg">Log message (with formatting placeholders, if desired)</param>
         /// <param name="args">Formatting replacements.</param>
-        public void info(string msg, params object[] args) {
-            foreach (TextWriter outw in this.infos) {
-                outw.WriteLine("(I@" + DateTime.Now.ToString("HH:mm:ss") + ")[MAIN] " + msg, args);
+        public void info(object msg) {
+            foreach (LogOutput outw in infos) {
+                if (outw.open)
+                    outw.writer.WriteLine("(I@" + DateTime.Now.ToString("HH:mm:ss") + ")[" + from + "] " + msg.ToString());
             }
         }
 
@@ -62,10 +72,20 @@ class Logger {
         /// </summary>
         /// <param name="msg">Log message (with formatting placeholders, if desired)</param>
         /// <param name="args">Formatting replacements.</param>
-        public void error(string msg, params object[] args) {
-            foreach (TextWriter outw in this.errors) {
-                outw.WriteLine("(E@" + DateTime.Now.ToString("HH:mm:ss") + ")[MAIN] " + msg, args);
+        public void error(object msg) {
+            foreach (LogOutput outw in errors) {
+                if (outw.open)
+                    outw.writer.WriteLine("(E@" + DateTime.Now.ToString("HH:mm:ss") + ")[" + from + "] " + msg.ToString());
             }
         }
     }
+
+    class LogOutput {
+        public TextWriter writer { get; private set; }
+        public bool open;
+        public LogOutput(TextWriter writer) {
+            this.writer = writer;
+            this.open = true;
+        }
+    }
 }
index b174ed9a2db5ee28ff0b496a52ebd25bb4d3cc0c..a8d9df9ca84499140e70e5f3848d8cbf05113dca 100644 (file)
@@ -3,37 +3,43 @@
 using System.Linq;
 using System.Text;
 using MySql.Data.MySqlClient;
+using System.IO;
 
 namespace Kelsier {
     class Root {
-        static protected Database _db = null;
-        static public Database db { get { return _db; } }
+        static public Database db { get; private set; }
+        static public Logger log { get; private set; }
 
-        static protected Logger _log;
-        static public Logger log { get { return _log; } }
+        static private Dictionary<int, Bot> bots; // accessed by this.bot(int id)
 
 
         static void Main(string[] args) {
-            System.IO.StreamWriter fileout = new System.IO.StreamWriter("kelsier.log", false);
+            StreamWriter fileout = new StreamWriter("kelsier.log", false);
             fileout.AutoFlush = true;
-            System.IO.TextWriter[] outputs = { Console.Out, fileout };
-            _log = new Logger(outputs, outputs, outputs);
-
-            _db = new Database(Properties.Settings.Default.dbstr);
-
-            db.Connect();
-            
-            log.debug("1 + 3 = {0}", db.queryScalar("SELECT 1+3").ToString());
-
-            _log = null;
-            GC.Collect();
-            GC.WaitForPendingFinalizers();
-
-#if DEBUG
-            Console.Write("Key to end...");
-            Console.ReadKey();
-#endif
+            LogOutput[] outputs = new LogOutput[] { new LogOutput(Console.Out), new LogOutput(fileout) };
+            log = new Logger("Root", new LogOutput[] { new LogOutput(Console.Out) }, outputs, outputs);
+
+            db = new Database(Properties.Settings.Default.dbstr);
+
+            List<int> botids = new List<int>();
+            MySqlDataReader rdr = db.queryReader("SELECT id FROM bots");
+            while (rdr.Read()) {
+                botids.Add(rdr.GetInt32("id"));
+            }
+            rdr.Close();
+
+            bots = new Dictionary<int, Bot>();
+            foreach (int key in botids) {
+                bots.Add(key, new Bot(key));
+                bots[key].connect();
+            }
+
+            while (true) {
+                System.Threading.Thread.Sleep(2000);
+            }
         }
+
+        static Bot bot(int id) { return bots[id]; }
     }
 
 
diff --git a/dbdump.sql b/dbdump.sql
new file mode 100644 (file)
index 0000000..e0b0c5c
--- /dev/null
@@ -0,0 +1,14 @@
+/*!40101 SET @saved_cs_client     = @@character_set_client */;
+/*!40101 SET character_set_client = utf8 */;
+CREATE TABLE `bots` (
+  `id` int(10) unsigned NOT NULL AUTO_INCREMENT,
+  `nick` varchar(40) NOT NULL,
+  `ident` varchar(10) NOT NULL DEFAULT 'kelsier',
+  `realname` varchar(100) NOT NULL DEFAULT 'Kelsier IRC Bot',
+  `bindip` varchar(15) DEFAULT NULL,
+  `server` varchar(100) NOT NULL DEFAULT 'irc.quakenet.org',
+  `serverport` smallint(5) unsigned NOT NULL DEFAULT '6667',
+  PRIMARY KEY (`id`)
+) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8;
+/*!40101 SET character_set_client = @saved_cs_client */;
+INSERT INTO `bots` VALUES (1,'Kelsier','kelsier','Kelsier IRC Bot',NULL,'irc.quakenet.org',6667);