Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- <?php
- /**
- * dAmn Class
- *
- *@todo add a global records variable to record joins/parts and other stats. Maybe record the times too?
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@author electicnet
- *@copyright SubjectX52873M 2006
- *@origin Tarbot 0.2e
- *@version 0.5
- *@modlevel medium
- *@package Dante
- *@license http://www.opensource.org/licenses/gpl-license.php GNU General Public License
- */
- /**
- * dAmn related functions
- * contains alot of functions and variables related to dAmn function.
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@author electicnet
- *@copyright SubjectX52873M 2006
- *@origin Tarbot 0.2e
- *@modlevel medium
- *@version 0.6
- */
- class dAmn {
- /**
- * Stores whether or not the bot is connected.
- *@var bool $connected
- */
- var $connected;
- /**
- * Stores whether or not the bot is logged in.
- *@var bool $loggedIn
- */
- var $loggedIn;
- /**
- * Tracks if there was a socket error
- *
- * Used to prevent the bot from going into an infinite loop, this has been a problem.
- *@origin Dante 0.4
- *@var bool $SocketAbort
- */
- var $SocketAbort;
- /**
- * Use the stored token for login.
- *
- *This is to track the use of a token and whether a new one is required
- *@var bool $UseToken
- */
- var $UseToken;
- /**
- *Last access time for the socket
- *@var integer $lastAccess
- */
- var $lastAccess;
- /**
- * Bot Startup
- *
- * Runs dAmn::getAuthToken() and sets $config['bot']['token']
- *@author electricnet
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Tarbot 0.2e
- *@version 0.6
- */
- function init(){
- global $config, $seperator, $debug;
- $this->connected = false;
- $this->loggedIn = false;
- $this->SocketAbort=false;
- //Grab login info.
- if(!$debug){
- internalHeader("STARTING DANTE!", "=");
- } else {
- internalHeader("STARTING DANTE -- DEBUG MODE!", "=");
- }
- internalMessage("Running ".BotType." version ".BotVersion." ".BotState);
- internalMessage("Written by: SubjectX52873M.");
- internalMessage("With code \"stolen\" from: Tarbot 0.2e, xBot 0.9, and Noodlebot 3.0");
- internalHeader("AUTHTOKEN");
- //New to version 0.3, now get the AuthToken
- if ($this->UseToken) {
- internalMessage("Trying Stored token first.");
- } else {
- $config['bot']['token'] = $this->getAuthToken();
- save_config('bot');
- }
- }
- /**
- * If the bot fails to load properly you need to reconnect the socket.
- *
- *This is only called if the stored Token fails to work.
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Dante 0.3
- *@version 0.5
- */
- function reconSocket() {
- global $config, $socket;
- socket_close($socket);
- $socket =null;
- $socket = socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
- if(!@socket_connect($socket, gethostbyname(BotServer), BotPort)) {intMsg('Can\'t connect socket!!!!');return;}
- if ($this->UseToken==false) { //IF NOT!! messed this up in 0.3
- //Okay, function called to reconnect from a failure with a stored token.
- internalMessage("Failed to login using stored token. Grabbing a new one and trying again.");
- $config['bot']['token'] = $this->getAuthToken();
- save_config('bot');
- global $packetping;
- $packetping=microtime(true);
- //Connect
- $this->startup();
- //Join rooms.
- $this->autoJoin();
- $this->pingpong();
- $loop = 0;
- $onceconnected = false;
- }
- }
- /**
- *Reconnect on disconnect
- *
- *Makes the code in the main file cleaner to use this here.
- *@origin Dante 0.3
- *@version 0.5
- */
- function reconnect() {
- global $socket, $loops;
- $this->SocketAbort=false;
- internalMessage("Closing socket.");
- @socket_shutdown($socket);
- @socket_close($socket); //Supress Errors.
- internalMessage("Waiting 15 secs for reconnect");
- sleep(15);
- echo "\n";
- internalMessage("Connecting...");
- $socket = null; // Remove previous references
- $socket = @socket_create(AF_INET, SOCK_STREAM, SOL_TCP);
- //Connect the socket
- if(@socket_connect($socket, gethostbyname(BotServer), BotPort)) {
- internalmessage("Connecting...");
- $this->startup();
- $this->autoJoin();
- $loops = 0;
- global $packetping;
- $packetping=microtime(true);
- } else {
- sleep(15); //Prevent inifinite loops
- $loops++;
- if ($loops==100) { internalmessage("Can't connect after 100 tries, dying."); die();}
- internalmessage("Can't connect socket!!!!, waiting 15 seconds. Try: $loops");
- sleep(15); //Prevent inifinite loops
- }
- }
- /**
- * Bot Startup
- *
- * Runs dAmn:connect() and dAmn::login()
- *
- * electricnet: Includes everything needed to startup in ONE function
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel no modified
- *@see dAmn:login()
- *@see dAmn:connect()
- *@version 0.1
- */
- function startup(){
- global $seperator;
- internalHeader("CONNECT");
- $this->connect();
- $this->login();
- }
- /**
- * Connect to server and send the useragent
- *
- *User Agent is currently just "agent=Dante"
- *
- *Raw dAmnClient 0.2\nagent=Dante\n\0
- *@author electricnet
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Tarbot 0.2e
- *@modlevel light
- *@todo Store Useragent elsewhere?
- *@version 0.1
- */
- function connect(){
- global $running;
- $this->send("dAmnClient 0.2\nagent=Dante\n".chr(0), true);
- $this->connected = true;
- $running = true;
- }
- /*
- 16:54:29 <ManjyomeThunder> i got a wii
- 16:55:02 <SubjectX52873M> Great, I have a penis too :)
- 16:55:09 <bentomlin> :rofl:
- 16:55:15 <ManjyomeThunder> wtf
- 16:55:29 <SubjectX52873M> Are you going to go play with your wii now?
- */
- //Wii is pronouced "Wee" :)
- //All three in the above are guys too so it was funny.
- /**
- * Login to server and send the username and token
- *@author electricnet
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.1
- */
- function login(){
- global $config;
- if($this->connected){
- $this->send(
- "login " . $config['bot']['username'] .
- "\npk=" . $config['bot']['token'] .
- "\n" . chr(0), true);
- $this->loggedIn = true;
- }
- }
- /**
- * Send stuff to the server.
- *
- * It's sent raw, you need to add chr(0) to the end of any data you send using this function.
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel not modified
- *@version 0.4
- */
- function send($data, $boic = false){
- global $socket, $debug;
- $this->checkQueues();
- if($debug){
- echo "** OUTGOING -> " . time() . " **\n";
- var_dump($data); //electricnet: DEBUG
- }
- if (!$this->SocketAbort) {
- if ($debug) {
- socket_send($socket, $data, strlen($data), 0x0);
- } else {
- @socket_send($socket, $data, strlen($data), 0x0);
- }
- if (socket_last_error($socket)){
- /*intmsg("Error");
- $this->SocketAbort=True;
- $this->connected=false;*/
- socket_clear_error($socket);
- }
- }
- $this->checkQueues($boic);
- }
- /**
- *Autojoin Rooms.
- *@origin Dante 0.4
- *@version 0.4
- */
- function autoJoin() {
- global $config;
- foreach($config['bot']['rooms'] as $room){
- $this->joinRoom($room);
- }
- }
- /**
- * Gets data from the socket and returns it
- *@author electricnet
- *@return string
- *@origin Tarbot 0.2e
- *@modlevel not modified
- *@version 0.4
- */
- function listen(){
- global $socket;
- $response = "";
- if ($debug) {
- //Don't supress errors.
- if(0 === socket_recv($socket, $response, 8192, 0)){ $this->connected = false; }
- } elseif (!$this->SocketAbort) {
- //Supress errors from the socket.
- if(0 === @socket_recv($socket, $response, 8192, 0)){ $this->connected = false; }
- }
- return $response;
- }
- /**
- * PONG!
- *
- * Sends data out to check if the bot is still connected
- *
- * Modified in Version 0.4 to allow the main loop to use with out halting the bot.
- *
- * Used to repond to a ping from the dAmnserver
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.6
- */
- function pingpong(){
- $this->send("pong\n" . chr(0));
- }
- /**
- *Sends an invalid msg main packet to the server to check for a connection
- *
- *This should not be called too often. :)
- *
- *Defaults to not block on incoming.
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Dante 0.4
- *@version 0.4
- */
- function pingpong2(){
- $this->send("send chat:!err_plz!\n\nmsg main\n\nBAD FOO" . chr(0));
- }
- /**
- * Send a message to a the chatroom
- *
- * Now accpets /np for nonparsed messages
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.5
- */
- function say($message, $chatroom){
- $chatroom = generateChatName($chatroom);
- if(substr($message, 0, 4) == "/me "){
- $this->me(substr($message, 4), $chatroom);
- } elseif(substr($message, 0, 4) == "/np "){
- $this->npmsg(substr($message, 4), $chatroom);
- } else {
- $this->send("send " . $chatroom . "\n\nmsg main\n\n" . $message . chr(0), true);
- }
- }
- /**
- * Send a nonparsed message to a chatroom
- *
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Dante 0.3
- *@version 0.3
- */
- function npmsg($message, $chatroom){
- $chatroom = generateChatName($chatroom);
- $this->send("send " . $chatroom . "\n\nnpmsg main\n\n" . $message . chr(0), true);
- }
- /**
- * Send an action to a the chatroom
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel not modified
- *@version 0.1
- */
- function me($message, $chatroom){
- $chatroom = generateChatName($chatroom);
- $this->send("send " . $chatroom . "\n\naction main\n\n" . $message . chr(0), true);
- }
- /**
- * Join a chatroom
- *@author electricnet
- *@return bool True for success in joining, False for failure.
- *@origin Tarbot 0.2e
- *@modlevel not modified
- *@version 0.1
- */
- function joinRoom($chatroom){
- if(!empty($chatroom)){
- $chatroom = generateChatName($chatroom);
- $this->send("join " . $chatroom . "\n" . chr(0), true);
- return true;
- } else {
- return false;
- }
- }
- /**
- * Leave a chatroom
- *@author electricnet
- *@return bool True for success in leave, False for failure.
- *@origin Tarbot 0.2e
- *@modlevel not modified
- *@version 0.1
- */
- function partRoom($chatroom){
- if(!empty($chatroom)){
- $chatroom = generateChatName($chatroom);
- $this->send("part " . $chatroom . "\n" . chr(0), true);
- return true;
- } else {
- return false;
- }
- }
- /**
- * Get a property
- *
- * This does not return a value. It sends a request for data to the server and dAmn:process catches it later.
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel not modified
- *@version 0.1
- */
- function get($property, $chatroom){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- $this->send("get " . $chatroom . "\np=" . $property . "\n" . chr(0));
- }
- /**
- * /whois a user
- *
- * This does not return a value. It sends a request for data to the server and dAmn:process catches it later.
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function getUserInfo($username){
- if (!empty($username)) {
- $this->send("get login:" . $username . "\np=info\n" . chr(0));
- }
- }
- /**
- * Kick a user from a chatroom
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function kick($username, $chatroom, $reason = ""){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- $this->send("kick " . $chatroom . "\nu=" . $username . "\n\n" . $reason . chr(0));
- }
- /**
- * Promote a user.
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function promote($username, $privclass, $chatroom){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- $this->send("send " . $chatroom . "\n\npromote " . $username . "\n\n" . $privclass . chr(0));
- }
- /**
- * Demote a user.
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function demote($username, $privclass, $chatroom){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- $this->send("send " . $chatroom . "\n\ndemote " . $username . "\n\n" . $privclass . chr(0));
- }
- /**
- * Ban a user.
- *
- * Equiv to !demote (user) banned
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function ban($username, $chatroom){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- $this->send("send " . $chatroom . "\n\nban " . $username . "\n\n" . chr(0));
- }
- /**
- * Unban a user.
- *
- *This promotes/demotes a user to the default guest level
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function unban($username, $chatroom){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- $this->send("send " . $chatroom . "\n\nunban " . $username . "\n\n" . chr(0));
- }
- /**
- * Set a property
- *
- * Only Topic/Title works right now.
- *@author electricnet
- *@return bool True for success in leave, False for failure.
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function set($property, $value, $chatroom){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- if($property == "title" || $property == "topic"){
- $this->send("set " . $chatroom . "\np=" . $property . "\n\n" . $value . chr(0));
- return true;
- } else {
- return false;
- }
- }
- /**
- * Admin
- *
- *See the dAmn FAQ for /admin uage
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.4
- */
- function admin($command, $chatroom){
- $chatroom = generateChatName($chatroom);
- if ($chatroom ==false) { return; }
- $this->send("send " . $chatroom . "\n\nadmin\n\n" . $command . chr(0));
- }
- /**
- *Check Socket for Data
- *
- *Checks for data from the socket and sends the info where it needs to go.
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel light
- *@version 0.5
- */
- function checkQueues($boic = false){
- global $socket, $debug, $data;
- if(socket_select($r = array($socket), $w = NULL, $e = NULL, 0) > 0){
- if (in_array($socket, $r)) {
- $data .= $this->listen();
- if ($this->SocketAbort==True) {
- $this->connected=false;
- return;
- } else {
- $datas = explode(chr(0), $data);
- $data = $datas[count($datas) - 1];
- unset($datas[count($datas) - 1]);
- if($debug){
- echo "** INCOMING <- " . time() . "**\n";
- var_dump($datas);
- }
- foreach($datas as $recievedData){
- if($debug){ echo "(" . strlen($recievedData) . ")\n"; }
- $this->process($recievedData);
- }
- $this->lastAccess = microtime(true);
- }
- } else {
- if (microtime(true)-$this->lastAccess < 100) {
- $this->connected=false;
- $lastAccess->lastAccess = microtime(true);
- echo "\nSOCKET TIMEOUT\n";
- }
- }//*/
- }
- }
- /**
- *Checks bot.ini for proper settings
- *
- *Builds a copy if one is not found.
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Dante 0.4b
- *@version 0.5
- */
- function checkINI() {
- global $config;
- include f("config.php");
- $die=false;
- if (empty($login['username'])) {
- intmsg('FATAL: No username in Config.php');
- $die=true;
- }
- if (empty($login['owner'])) {
- intmsg('FATAL: No owner in Config.php');
- $die=true;
- }
- if (empty($login['password'])) {
- intmsg('FATAL: No password in Config.php');
- $die=true;
- }
- if (empty($login['trigger'])) {
- intmsg('FATAL: No trigger in Config.php');
- $die=true;
- }
- if ($die) {die();}
- if ($config['bot']['EraseConfigNextRun']!=='no') {
- //Build the config.
- intmsg('Config does not exist, building.');
- $config['bot']=array(
- 'username'=>$login['username'],
- 'trigger'=>$login['trigger'],
- 'owner'=>$login['owner'],
- 'token' => '',
- 'about' => ':mechabug:Dante {version} owned by: {owner} and running on: {os} <br />'.
- 'Link: <a href="http://botdom.24bps.com/wiki/Dante">Project Page</a> | See {trig}credits for credits.',
- 'AutoRejoinWhenKicked' => true,
- 'timestamp' => 'H:i:s',
- 'timestamp_log' => 'M jS, Y / H:i:s',
- 'BadCommandMsg' => '',
- 'RestrictedCommandMsg' => '',
- 'thumbMode'=>false,
- 'logChats'=>true,
- 'rooms' => array('#Botdom','#LabX52'),
- 'EraseConfigNextRun'=>'no',
- );
- $config['ignore']=array();
- $config['users']=array();
- $config['access']=array(
- 'priv'=>array(),
- 'default'=>array(
- 'guests'=>0,
- 'commands'=>0,
- 'errors'=>0,
- 'trigcheck'=>0,
- ),
- ); //Clear out access
- save_config(false,true); //Save all ini files and force it to save.
- intmsg('Config has been created.');
- intmsg('Your bot can be found in #Botdom when it finishes loading.');
- sleep(5);
- } else {
- //Check config.
- $error=false;
- if ($config['bot']['username']!==$login['username']) {
- intmsg('Notice: Username in config.php does not match name in bot.ini Fixing');
- $config['bot']['username']=$login['username'];
- //If there is a new user you need a new token
- $config['bot']['token']='';
- $error=true;
- }
- if ($config['bot']['owner']!==$login['owner']) {
- $config['bot']['owner']=$login['owner'];
- intmsg('Notice: Owner in config.php does not match name in bot.ini Leaving Alone');
- $error=false;
- }
- if ($config['bot']['trigger']!==$login['trigger']) {
- intmsg('Notice: Trigger in config.php does not match name in bot.ini Leaving Alone');
- $error=false;
- }
- if (!isset($config['access']['default']['guests'])) {
- $config['access']['default']['guests']=0;
- intmsg('Notice: Missing guest priv default... Setting to 0');
- $error=true;
- }
- if (!isset($config['access']['default']['errors'])){
- $config['access']['default']['errors']=0;
- intmsg('Notice: Missing error priv default... Setting to 0');
- $error=true;
- }
- if (!isset($config['access']['default']['commands'])){
- $config['access']['default']['commands']=0;
- intmsg('Notice: Missing commands priv default... Setting to 0');
- $error=true;
- }
- if ($error) {
- save_config('bot');
- save_config('access');
- }
- }
- }
- /**
- *Get Token
- *
- *This function logs the bot into it's account and steals the cookie from the server. The cookie contains an Md5 hash, called an AuthToken. The dAmn server (chat.deviantart.com:3900) uses the AuthTokens for login not passwords. So the bot needs to grab the Authtoken before logging into the chat server.
- *
- *This function now sets up the bot's config file for the first time.
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@author electricnet
- *@origin Tarbot 0.2e
- *@modlevel Light
- *@version 0.4
- */
- function getAuthToken(){
- internalMessage("Getting authtoken...");
- global $event,$config;
- include f("config.php"); //This loads the $login
- $query = "username=" . $login['username'] . "&password=" . $login['password'] . "&reusetoken=1" . chr(0);
- $data = "POST /users/login HTTP/1.1\n" .
- "Host: www.deviantart.com\n" .
- "User-Agent: " . BotUserAgent . "\n" .
- "Accept: text/html\n" .
- "Cookie: skipintro=1\n" .
- "Content-Type: application/x-www-form-urlencoded\n" .
- "Content-Length: " . strlen($query) . "\n\n" . $query;
- $a = socket_create(AF_INET, SOCK_STREAM, getprotobyname("tcp"));
- @socket_connect($a, "www.deviantart.com", 80);
- @socket_send($a, $data, strlen($data), 0x0);
- $response = @socket_read($a, 8192);
- if (socket_last_error($a)){
- internalMessage("WARNING Can't open socket for login. Check your internet connection.");
- die();
- return;
- }
- @socket_clear_error($a);
- @socket_close($a);
- if(!empty($response)){
- $response = urldecode($response);
- if(stristr($response, "Set-Cookie: ") && stristr($response, "authtoken")){
- $bits = explode("userinfo=", $response);
- $cookie = substr($bits[1], 0, strpos($bits[1],"; expir"));
- $cookie = unserialize($cookie);
- if(!empty($cookie['authtoken'])){
- internalMessage("Got it!");
- unset($login); //Remove $login to prevent modules from grabbing the password.
- internalMessage("Authtoken: " . $cookie['authtoken']);
- //Need a authtoken event
- $event="authtoken";
- include f("system/callables/event.php");
- return $cookie['authtoken'];
- } else {
- internalMessage("Oops, couldn't get the authtoken. You may need to find it yourself.");
- $event="authtoken-fail";
- include f("system/callables/event.php");
- return false;
- }
- } else {
- internalMessage("Oops, couldn't get the authtoken. You may need to find it yourself.");
- $event="authtoken-fail";
- include f("system/callables/event.php");
- return false;
- }
- } else {
- unset($login);
- internalMessage("Oops, couldn't get the authtoken. You may need to find it yourself.");
- $event="authtoken-fail";
- include f("system/callables/event.php");
- return false;
- }
- }
- /*
- *Timeout
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Dante 0.2
- *@version 0.5
- */
- function timeout(){
- global $packetping;
- if (!isset($packetping)) {$packetping=microtime(true);}
- $ping=microtime(true)-$packetping;
- if ($ping > 100) {
- intmsg("Timeout detected\n");
- $this->connected=false;
- }
- }
- /**
- *Parse Tablumps
- *
- *Html tags and emoticons are incased in tab characters. This function makes messages more human readable and easier to program for.
- *
- *Swapped out the tarbot version of this for the noodlbot version. This one prints out prettier.
- *@author doofsmack?
- *@origin Noodlebot 3.0
- *@modlevel not modified
- *@version 0.1
- */
- function parseTablumps($text)
- {
- $search[]="/&emote\t([^\t])\t([0-9]+)\t([0-9]+)\t(.+)\t(.+)\t/U";
- $replace[]=":\\1:";
- $search[]="/&emote\t(.+)\t([0-9]+)\t([0-9]+)\t(.+)\t(.+)\t/U";
- $replace[]="\\1";
- $search[]="/&br\t/";
- $replace[]="\n\t";
- $search[]="/&(b|i|s|u|sub|sup|code|ul|ol|li|p|bcode)\t/";
- $replace[]="<\\1>";
- $search[]="/&\\/(b|i|s|u|sub|sup|code|ul|ol|li|p|bcode)\t/";
- $replace[]="</\\1>";
- $search[]="/&acro\t(.*)\t(.*)&\\/acro\t/U";
- $replace[]="<acronym title=\"\\1\">\\2</acronym>";
- $search[]="/&abbr\t(.*)\t(.*)&\\/abbr\t/U";
- $replace[]="<abbr title=\"\\1\">\\2</abbr>";
- $search[]="/&link\t([^\t]*)\t([^\t]*)\t&\t/U"; //noodleman: this one must be first.. otherwise the next one gets greedy and grabs the tab and name as part of the url.
- $replace[]="\\1 (\\2)";
- $search[]="/&link\t([^\t]*)\t&\t/U";
- $replace[]="\\1";
- $search[]="/&a\t(.*)\t(.*)\t(.*)&\\/a\t/U";
- $replace[]="<a href=\"\\1\" title=\"\\2\">\\3</a>";
- $search[]="/&(iframe|embed)\t(.*)\t([0-9]*)\t([0-9]*)\t&\\/(iframe|embed)\t/U";
- $replace[]="<\\1 src=\"\\2\" width=\"\\3\" height=\"\\4\" />";
- $search[]="/&img\t(.*)\t([0-9]*)\t([0-9]*)\t/U";
- $replace[]="<img src=\"\\1\" width=\"\\2\" height=\"\\3\" />";
- $search[]="/&thumb\t([0-9]*)\t(.*)\t(.*)\t(.*)\t(.*)\t(.*)\t(.*)\t/U";
- $replace[]=":thumb\\1:";
- $search[]="/&dev\t([^\t])\t([^\t]+)\t/U";
- $replace[]=":dev\\2:";
- $search[]="/&avatar\t([^\t]+)\t[01]\t/U";
- $replace[]=":icon\\1:";
- $search[]="/ width=\"\"/";
- $replace[]="";
- $search[]="/ height=\"\"/";
- $replace[]="";
- $oldtext='';
- while($text!=$oldtext)
- {
- $oldtext=$text;
- $text=preg_replace($search, $replace, $text);
- }
- return($text);
- }
- function getdays_month($month){
- if(!is_numeric($month)) $month=getnum_month($month);
- if(date("L")) $feb=29;
- else $feb=28;
- $days=array(
- '1'=>31,
- '2'=>$feb,
- '3'=>31,
- '4'=>30,
- '5'=>31,
- '6'=>30,
- '7'=>31,
- '8'=>31,
- '9'=>30,
- '10'=>31,
- '11'=>30,
- '12'=>31
- );
- return $days[$month];
- }
- /**
- *parseWhoisTS
- *@author Noodleman?
- *@origin Noodlebot 3.0
- *@modlevel not modified
- *@version 0.5
- */
- function parseWhoisTS($d, $words=true){
- $o=array();
- $o['year']=floor($d/31536000);
- $d-=$o['year']*31536000;
- $o['month']=0;
- for($m=0; $m<12; $m++)
- {
- $days=$this->getdays_month($m+1)*86400;
- if($d>=$days && $d>0)
- {
- $d-=$days;
- $o['month']++;
- } else break;
- }
- $o['week']=floor($d/604800);
- $d-=$o['week']*604800;
- $o['day']=floor($d/86400);
- $d-=$o['day']*86400;
- $o['hour']=floor($d/3600);
- $d-=$o['hour']*3600;
- $o['minute']=floor($d/60);
- $d-=$o['minute']*60;
- $o['second']=$d;
- $s="";
- foreach($o as $t => $v)
- if($v)
- {
- $s.=$v;
- if($words)
- {
- $s.=' '.$t;
- if($v!==1 && $v!=='1') $s.='s';
- }
- $s.=' ';
- }
- if($s=="") $s="<1 second";
- return $s;
- }
- /*X52 Well this is the best place to put it.
- Room info is stored like this
- $rooms = array(
- $chatroom=> array(
- joined (boolean),
- topic,title => array (
- value,
- by,
- time (Figure this out)
- )
- //NOTICE the members array does not store all users because the members packet is larger than 8kb the socket cuts it off before it finishes. See php.net docs for socket recv, read user comments and find a way to make this work.//
- members => member array (
- status = joined:parted:kicked:notset //notset is data from the prop-members event
- name = Nick //Crytopolonium
- pc = Privclass //Not reliable //Bots
- ico = 0:1 //1
- sym // ~
- symname (Need to make) // nonsubbed account
- realname ???? // w/ Chip
- typename ???? // dAmn addict
- ), // Need to add stuff.
- privclasses => pv,
- )
- */
- /**
- * Process Symbol
- *
- * This accepts the symbol that sit in front of a deviant's name and returns the type as a string.
- *
- * Example: dAmn::symproc('~') returns "Member" and dAmn::symproc('*') returns "Subscriber"
- *
- * Example: dAmn::symproc('~SubjectX52873M') returns 'Unknown Type (~SubjectX52873M)'
- * @author SubjectX52873M <SubjectX52873M@gmail.com>
- * @return string
- * @version 0.6
- */
- function symproc($symbol='='){
- if(empty($symbol)){ $symbol='=';}
- $symbols=array(
- '~' => 'Member',
- '*' => 'Subscriber',
- '=' => 'Official Beta Tester',
- '`' => 'Former Staff or Senior Member',
- '°' => 'Alumni Staff',
- '#' => 'Art Group Member',
- '@' => 'Shoutbox/dAmn Staff',
- ':' => 'Premium Content Staff',
- '©' => 'Policy Enforcement Staff',
- '%' => 'deviantART Prints Staff',
- '+' => 'General Staff',
- '¢' => 'Creative Staff',
- '^' => 'Gallery Director',
- '$' => 'Core Administrator',
- '!' => 'Banned User'
- );
- if(array_key_exists($symbol,$symbols)) {
- return $symbols[$symbol];
- } else {
- return 'Unknown Type ('.$symbol.')';
- }
- }
- /**
- *Parse Order
- *
- *Parses the order of a privclass update or creation.
- *
- *This pulls out the order=## from a privclass event
- *
- *Used in dAmn::process()
- *@return mixed On success a string is returned, on failure false is returned.
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@version 0.1
- */
- function parseOrder($data) {
- $da=explode("\n",$data);
- $db=explode("=",$da);
- if ($db[0]="order") {
- return $db[1];
- } else {
- return false;
- }
- }
- /**
- *Room parser
- *
- *Alias for downSortPChat
- *@version 0.4
- *@return string
- */
- function parseRoom($room) {
- return downSortPChat($room);
- }
- /**
- *propRoom
- *@version 0.5
- *@return String
- */
- function propRoom($p) {
- if(isset($p['property chat'])){
- return $this->parseRoom($p['property chat']);
- } elseif (isset($p['property pchat'])) {
- return $this->parseRoom($p['property pchat']);
- }else {
- return "(Unknown)";
- }
- }
- /**
- *Parse Datas
- *@return array
- *@version 0.2
- */
- function parseUserDatas($og) {
- $return=array();
- $o = explode("\n",$og);
- foreach($o as $i) {
- $stuffs = explode("=",$i);
- $return[$stuffs[0]]=$stuffs[1];
- }
- return $return;
- }
- /**
- *Process
- *
- *This breaks up the packets from the socket at routs the commands and calls modules to handle them.
- *@author electricnet
- *@author SubjectX52873M <SubjectX52873M@gmail.com>
- *@origin Tarbot 0.2e
- *@modlevel Medium
- *@version 0.5
- */
- /* sorry for those reading the source. I haven't cleaned up the comments on this function yet */
- function process($data){
- global $rooms, $config, $debug, $whoisroom, $latestwhois, $packetping;
- $rawdata=$data; //Raw data should be available to modules with this.
- //This is for the time based disconnection
- $packetping=microtime(true);
- $data = $this->parseTablumps($data);
- $datas = explode("\n", $data);
- $mainDatas = explode(" ", $datas[0]);
- $name = str_replace("\n", "", $mainDatas[0]);
- $param = $mainDatas[1];
- if($debug){
- echo ts() . " ** PROCESS " . time() . " **\n";
- var_dump($name);
- var_dump($data);
- }
- switch($name){
- case "dAmnServer":
- internalMessage("Hello there, we got connected! :D");
- internalMessage("You are running on dAmnServer " . $param);
- $event = "handshake";
- /**
- * Check for a module to handle event
- */
- include f("system/callables/event.php");
- break;
- case "login":
- $params = params($data);
- if($debug){ var_dump($params); }
- if($params['e'] == "ok"){
- internalMessage("You are successfully logged in as " . $config['bot']['username'] . ".");
- $this->UseToken=true;
- if (isset($login)) {unset($login);}
- $event = "login-success";
- include f("system/callables/event.php");
- } elseif($params['e'] == "authentication failed"){
- if ($this->UseToken) {
- $this->UseToken=false;
- $this->reconSocket();
- $this->connected=true;
- } else {
- internalMessage("Couldn't log in as " . $config['bot']['username'] . ", authentication failed. Please check that your username and/or password is right.");
- }
- } else {
- internalMessage("An unexpected error happened logging in as " . $botdom['username'] . ". Error recieved: \"" . $params['e'] . "\"");
- }
- $event = "login";
- include f("system/callables/event.php");
- break;
- case "ping":
- //electricnet: Let's respond to the ping!
- $this->pingpong();
- $event = "ping";
- include f("system/callables/event.php");
- break;
- case "join":
- $chatroom=$this->parseRoom($param);
- $params = params($data);
- if($debug){ var_dump($params); }
- if($params['e'] == "ok"){
- $output = "Joined " . $chatroom . "!";
- //internalMessage($output);
- registerChat("** " . $output, $param, false);
- //X52 open. Joined a room. Need to store
- $rooms[degenerateChatName($chatroom)]['joined']=true;
- //X52 close.
- $c = $chatroom = $param;
- //New Event, join-success
- $event = "join-success";
- include f("system/callables/event.php");
- break;
- } else {
- internalMessage("Couldn't join " . $chatroom . ", got error: \"" . ucfirst($params['e']) . "\".");
- //New Event, join-fail
- $event = "join-fail";
- include f("system/callables/event.php");
- break;
- }
- $event = "join";
- include f("system/callables/event.php");
- break;
- case "kicked":
- $params = params($data);
- $chatroom=$this->parseRoom($param);
- $by = $params['by'];
- $message = $params[0];
- $output = "Kicked from " . $chatroom ." by ".$by.", reason: ".$message;
- registerChat("** " . $output, $param, false);
- $event = "kicked";
- include f("system/callables/event.php");
- break;
- case "get": //electricnet: A whois was requested, but an error gets returned.
- $params = params($data);
- if($debug){ var_dump($params); }
- if($params['e'] == "bad namespace"){
- $message = "This user isn't currently on dAmn.";
- } else {
- $message = "An unexpected error happened to your whois query: \"" . $params['e'] . "\"";
- }
- if(!empty($whoisroom)){
- $this->say($message, $whoisroom);
- } else {
- internalMessage("Didn't know where to echo userinfo!");
- }
- $event = "get";
- include f("system/callables/event.php");
- break;
- case "part":
- //Pchat:chat
- $chatroom=$this->parseRoom($param);
- $params = params($data);
- if($debug){ var_dump($params); }
- if($params['e'] == "ok"){
- $output = "Parted " . $chatroom . ".";
- //internalMessage($output);
- registerChat("** " . $output, $param, false);
- $c = $chatroom = $param;
- //X52 open. Parted a room. Need to store
- $rooms[degenerateChatName($chatroom)]['joined']=false; //X52 Notice this does not affect other room data
- $event = "part-success";
- include f("system/callables/event.php");
- break;
- //X52 close.
- } else {
- internalMessage("Couldn't part " . $chatroom . ", got error: \"" . ucfirst($params['e']) . "\".");
- //How does a part fail unless you aren't in the room to begin with?
- // Add new events
- $event = "part-fail";
- include f("system/callables/event.php");
- }
- $event = "part";
- include f("system/callables/event.php");
- break;
- case "recv":
- $params = array();
- $paramblocks = explode("\n\n", $data);
- foreach($paramblocks as $paramblock){
- switch(count($params)){
- case 0:
- $params[] = params($paramblock);
- break;
- case 1:
- $params[] = params($paramblock, false);
- break;
- case 2:
- $params[] = array($paramblock);
- break;
- }
- }
- $action = explode(" ", $params[1][0]);
- $c = $chatroom = $param;
- switch($action[0]){
- case "msg":
- $message = trim($params[2][0]);
- $output = "<" . $params[1]['from'] . "> " . $message;
- $output = "[" . $this->parseRoom($param) . "] " . $output;
- if(!empty($output)){ registerChat($output, $param); }
- processMessage($message, $params[1]['from'], $param, $action[0]);
- $from = $params[1]['from'];
- $event = "recv-msg";
- include f("system/callables/event.php");
- break;
- case "action":
- $message = trim($params[2][0]);
- $output = "* " . $params[1]['from'] . " " . $message;
- $output = "[" . $this->parseRoom($param) . "] " . $output;
- if(!empty($output)){ registerChat($output, $param); }
- processMessage($message, $params[1]['from'], $param, $action[0]);
- $from = $params[1]['from'];
- $event = "recv-action";
- include f("system/callables/event.php");
- break;
- case "join":
- $output = "** " . $action[1] . " has joined";
- $event = "recv-join";
- $from = $action[1];
- if ($debug) {
- intmsg('JOINED... DUMPING PARAMS');
- var_dump($params);
- }
- //X52 open Set user as joined
- $stuffs=$this->parseUserDatas($params[2][0]);
- $rooms[degenerateChatName($c)]['members'][$from]= array(
- "name"=>$from,
- "status"=>"joined",
- "usericon"=>$stuffs['usericon'],
- "symbol"=>$stuffs['symbol'],
- "symbolname" => $this->symproc($stuffs['symbol']),
- "realname"=>$stuffs['realname'],
- "typename"=>$stuffs['typename'],
- "pc"=>$stuffs['pc'],
- );
- //X52 close
- $output = "[" . $this->parseRoom($param) . "] " . $output;
- if(!empty($output)){ registerChat($output, $param); }
- include f("system/callables/event.php");
- break;
- case "part":
- $output = "** " . $action[1] . " has left" . ((!empty($params[1]['r'])) ? " [" . $params[1]['r'] . "]" : "");
- $event = "recv-part";
- $from = $action[1];
- //X52 open Set user as parted
- $rooms[degenerateChatName($chatroom)]['members'][$from]["status"]="parted";
- //X52 close
- $output = "[" . $this->parseRoom($param) . "] " . $output;
- if(!empty($output)){ registerChat($output, $param); }
- include f("system/callables/event.php");
- break;
- case "kicked":
- $output = "** " . $action[1] . " was kicked by " . $params[1]['by'] . " * " . $params[2][0];
- $event = "recv-kicked";
- $from = $action[1];
- $by = $params[1]['by'];
- $message = $params[2][0];
- //X52 open Set user as kicked
- $rooms[degenerateChatName($chatroom)]['members'][$from]["status"]="kicked";
- //X52 close
- $output = "[" . $this->parseRoom($param) . "] " . $output;
- if(!empty($output)){ registerChat($output, $param); }
- include f("system/callables/event.php");
- break;
- case "privchg":
- //Need to set $rooms[degenerateChatName($chatroom)][$user]["privclass"]=$params[1]['pc'];
- $output = "** " . $action[1] . " has been made a member of '" . $params[1]['pc'] . "' by " . $params[1]['by'] . " *";
- $event = "recv-privchg";
- $from = $action[1];
- $by = $params[1]['by'];
- //X52 open Set user's privclass
- //X52 Add $members global later.
- $rooms[degenerateChatName($chatroom)][$from]["privclass"]=$params[1]['pc'];
- //X52 close
- $output = "[" . $this->parseRoom($param) . "] " . $output;
- if(!empty($output)){ registerChat($output, $param); }
- include f("system/callables/event.php");
- break;
- case "admin":
- switch($action[1]){
- case "create":
- if($params[1]['p'] == "privclass"){
- /*X52 Need to set ... and need to parse out the changes
- $rooms[degenerateChatName($chatroom)]["privclasses"][##]=level and
- $rooms[degenerateChatName($chatroom)]["privclasses"][level]=##
- */
- $output = "** Privilege class '" . $params[1]['name'] . "' has been created by " . $params[1]['by'] . " with: " . $params[1]['privs'];
- if ($this->parseOrder($params[1]['privs'])==false) {
- $output = $output.' error registering pc with bot';
- } else {
- $num=$this->parseOrder($params[1]['privs']);
- $rooms[degenerateChatName($chatroom)]["privclasses"][$num]=$params[1]['name'];
- $rooms[degenerateChatName($chatroom)]["privclasses"][$params[1]['name']]=$num;
- }
- //X52 need to parse out the priv level
- }
- break;
- case "update":
- /*X52 Need to set
- $rooms[degenerateChatName($chatroom)]["privclasses"][##]=level and
- $rooms[degenerateChatName($chatroom)]["privclasses"][level]=##
- Need to parse the privs to do this. :|
- */
- if($params[1]['p'] == "privclass"){
- $output = "** Privilege class '" . $params[1]['name'] . "' has been updated by " . $params[1]['by'] . " with: " . $params[1]['privs'];
- }
- if ($this->parseOrder($params[1]['privs'])==false) {
- $output = $output.' error registering pc with bot';
- } else {
- $target_level=$rooms[degenerateChatName($chatroom)]["privclasses"][$params[1]['name']];
- unset($rooms[degenerateChatName($chatroom)]["privclasses"][$target_level]);
- $num=$this->parseOrder($params[1]['privs']);
- $rooms[degenerateChatName($chatroom)]["privclasses"][$num]=$params[1]['name'];
- $rooms[degenerateChatName($chatroom)]["privclasses"][$params[1]['name']]=$num;
- }
- break;
- case "rename":
- if($params[1]['p'] == "privclass"){
- $output = "** Privilege class '" . $params[1]['prev'] . "' has been renamed to '" . $params[1]['name'] . "' by " . $params[1]['by'] . " *";
- //X52 open Set new privclass
- $prev_room=$params[1]['prev'];
- $target_name=$params[1]['name'];
- $target_priv=$rooms[degenerateChatName($chatroom)]["privclasses"][$prev_room];
- unset($rooms[degenerateChatName($chatroom)]["privclasses"][$prev_room]);
- $rooms[degenerateChatName($chatroom)]["privclasses"][$target_priv]=$target_name;
- $rooms[degenerateChatName($chatroom)]["privclasses"][$target_name]=$target_priv;
- //X52 close
- }
- break;
- case "move":
- //X52 Maybe do this? Much Later
- if($params[1]['p'] == "users"){
- $output = "** All members of '" . $params[1]['prev'] . "' has been moved to '" . $params[1]['name'] . "' by " . $params[1]['by'] . " -- " . $params[1]['n'] . " members were affected.";
- }
- break;
- case "remove":
- /*
- Me: "I don't know if I can pull 5 pages out of that"
- Amanda: "I'm going 5 out of my ass. I need that extra credit."
- */
- if($params[1]['p'] == "privclass"){
- $output = "** Privilege class '" . $params[1]['name'] . "' has been removed by " . $params[1]['by'] . " -- " . $params[1]['n'] . " members were affected.";
- //X52 open delete privclass and create the new one.
- //X52 will need code to mod $members (Create new global to store stuff.)
- $target_class=$params[1]['name'];
- $target_num=$rooms[degenerateChatName($chatroom)]["privclasses"][$target_class];
- unset($rooms[degenerateChatName($chatroom)]["privclasses"][$target_class]);
- unset($rooms[degenerateChatName($chatroom)]["privclasses"][$target_num]);
- //X52 close
- }
- break;
- }
- $output = "[" . $this->parseRoom($param) . "] " . $output;
- if(!empty($output)){ registerChat($output, $param); }
- $event = "recv-admin";
- include f("system/callables/event.php");
- break;
- }
- break;
- case "property":
- if($debug){ echo "****** -> PROPERTY\n"; }
- $params = array();
- $paramblocks = explode("\n\n", $data);
- foreach($paramblocks as $paramblock){
- if(empty($params)){
- $params[] = params($paramblock);
- $proptype = $params[0]['p'];
- } else {
- switch($proptype){
- case "topic":
- case "title":
- $params[] = $paramblock;
- break;
- default:
- $params[] = params($paramblock, false);
- break;
- }
- }
- }
- if($debug){
- echo "PROPTYPE = " . $proptype . "\n";
- echo "PARAMS = ";
- var_dump($params);
- echo "\n";
- }
- if ($params[0]['property chat']) {$c = $chatroom =$params[0]['property chat'];}
- else{$c = $chatroom =$params[0]['property pchat'];}
- switch($proptype){
- case "privclasses":
- $privclasses = $params[1];
- //X52 open Setup privclasses.
- foreach($privclasses as $i => $o) {
- //$i = int($i);
- $rooms[degenerateChatName($chatroom)]['privclasses'][$i] = $o;
- $rooms[degenerateChatName($chatroom)]['privclasses'][$o] = $i;
- }
- //X52 close
- //electricnet: A var_dump($privclasses); gives something like
- /* array(9) {
- [99]=>
- string(8) "Founders"
- [75]=>
- string(9) "Operators"
- [25]=>
- string(6) "Guests"
- [1]=>
- string(6) "Banned"
- } */
- //electricnet: NOTE_TO_DEV: Maybe post privclasses to the web here? At least do something with it.
- //X52, better idea. Put all classes in the bot. Store a copy locally to save bandwidth.
- internalMessage("Got privclasses for ".$this->propRoom($params[0]));
- $event = "property-privclasses";
- include f("system/callables/event.php");
- break;
- case "members":
- // need to manually parse this one.
- /*X52
- property chat:${channel}\np=members\n\nmember ${nick}\npc=${privclass}\nusericon=${usericon}\nsymbol=${symbol}\nrealname=${realname}\ntypename=${typename}\n\n\0
- */
- if(isset($rooms[degenerateChatName($chatroom)]["members"])){
- unset($rooms[degenerateChatName($chatroom)]["members"]);
- }
- //Interesting note. This is code from Dante 0.0 :) Pre-Tarbot core
- //Start with data
- //X52 Okay this blows up the list :)
- //Talk to eletricnet and use $params instead >.<
- //This code actually works... if the bot can grab the members packet
- $temp=explode("\n\n",$data,2); //New in 0.4, better splitting.
- $temp=explode("\n\n",$temp[1]);
- $datar=array();
- foreach($temp as $i => $xx) {
- if(!empty($xx)){
- $x=explode("\n",$xx,2);
- $member=$x[0];
- $infos=$x[1];
- $marray=$this->parseUserDatas($infos);
- $member=str_replace("member ","",$member);
- $datar[$member]=$marray;
- $datar[$member]['name']=$member;
- $datar[$member]['status']='notset';
- $datar[$member]['symbolname'] = $this->symproc($datar[$member]['symbol']);
- }
- }
- $rooms[degenerateChatName($chatroom)]["members"]=$datar;
- internalMessage("Got members for ".$this->propRoom($params[0]));
- $event = "property-members";
- include f("system/callables/event.php");
- break;
- case "title":
- $message = $params[1];
- $by = $params[0]['by'];
- $ts = $params[0]['ts'];
- //X52 open Set rooms info
- $rooms[dChatName($chatroom)]["title"]= array(
- "value" => $message,
- "by" => $by,
- "time" => $ts);
- //X52 close
- internalMessage("Got title for ".$this->propRoom($params[0]));
- $event = "property-title";
- include f("system/callables/event.php");
- break;
- case "topic":
- //X52 $rooms[degenerateChatName($chatroom)]["topic"]
- $message = $params[1];
- $by = $params[0]['by'];
- $ts = $params[0]['ts'];
- //X52 open Set rooms info
- $rooms[dChatName($chatroom)]["topic"]= array(
- "value" => $message,
- "by" => $by,
- "time" => $ts);
- //X52 close
- internalMessage("Got topic for ".$this->propRoom($params[0]));
- $event = "property-topic";
- include f("system/callables/event.php");
- break;
- case "info":
- $message = ":icon" . $params[0]['property login'] . ": <strong>:dev" . $params[0]['property login'] . ":</strong>";
- $message .= "<ul><li>" . $params[1]['realname'] . "</li><li>" . $params[1]['typename'] . "</li>";
- $message .= ($params[1]['gpc'] != "guest") ? "<li>dAmn " . $params[1]['gpc'] . "</li></ul>" : "</ul>";
- $connNumber = 1;
- foreach($params as $number => $thisParam){
- if($params > 1){
- if($params[$number][0] == "conn"){
- $message .= "<br /><em>Connection " . $connNumber . "</em>";
- $message .= "<br />● <strong>Online:</strong> " . date("D M j Y [H:m:s]", time() - $params[$number]['online']);
- $message .= "<br />● <strong>Idle:</strong> " . $this->parseWhoisTS($params[$number]['idle']);
- $message .= "<br />● <strong>Chatrooms:</strong>";
- $connNumber++;
- } elseif(!empty($params[$number]['ns chat'])){
- $message .= " #" . $params[$number]['ns chat'];
- }
- }
- }
- $username = $params[0]['property login'];
- if(!empty($whoisroom)){
- $this->say($message, $whoisroom);
- $whoisroom = "";
- }
- $latestwhois[$username] = $params;
- $latestwhois[$username]['t'] = time();
- break;
- }
- break;
- }
- }
- }
- ?>
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement