luacomponent.cpp

Sat, 27 Mar 2010 17:43:08 +0000

author
Matthew Wild <mwild1@gmail.com>
date
Sat, 27 Mar 2010 17:43:08 +0000
changeset 0
cc66ad6b0d75
permissions
-rw-r--r--

Initial commit (importing from old SVN repo which got lost)

// g++ -Wall -O2 -pipe -march=i686 "%f" /usr/local/lib/libgloox.so /usr/lib/liblua5.1.so
#include </usr/local/include/gloox/gloox.h>
#include </usr/local/include/gloox/client.h>
#include </usr/local/include/gloox/clientbase.h>
#include </usr/local/include/gloox/messagehandler.h>
#include </usr/local/include/gloox/tag.h>
#include </usr/local/include/gloox/stanza.h>
#include </usr/local/include/gloox/connectionlistener.h>
#include </usr/local/include/gloox/presencehandler.h>
#include </usr/local/include/gloox/component.h>

extern "C" {
#include <lua.h>
#include <lualib.h>
#include <lauxlib.h>
}

using namespace gloox;

lua_State *L = NULL;
lua_State *calcL = NULL;
char BotName[26];
class Bot* theBot = NULL;

int lcJoinMUC(lua_State* L);
int lcSleep(lua_State* L);
int lcMemUsage(lua_State* L);
int lcSendPresence(lua_State* L);
int lcSendMessage(lua_State* L);

class Bot : public MessageHandler, ConnectionListener , PresenceHandler, LogHandler
{
 public:
   Bot()
   {
   	::theBot = this;
   	lua_getglobal(L, "BotPass");
	if(!lua_isstring(L, -1))
	{
		printf("Please, in the body of the script, set BotJID, BotPass, and BotName!\n");
		return;
	}
      // JID jid( lua_tostring(L, -3) );
      j = new Component ( "jabber:component:accept", "localhost", "xmoo", "secret", 5347);

      j->registerConnectionListener( this );
      j->registerMessageHandler( this );
      j->registerPresenceHandler( this );
      j->logInstance().registerLogHandler( LogLevelDebug, LogAreaAll, this );
      // j->setInitialPriority( 5 );
      // j->setAutoPresence( true );
      printf("Connecting...\n");
      j->connect();
   }

   virtual void handleMessage( Stanza *stanza, MessageSession *session )
   {
		if(stanza->findChildWithAttrib("xmlns","jabber:x:delay"))
		{
			printf("History message, ignoring.\n");
			return;
		}
		
		printf("Message.\n");
			    /* push functions and arguments */
		lua_getglobal(L, "onMessage");  /* function to be called */
		if(!lua_isfunction(L, -1))
		{
			printf("Unhandled message... please add an onMessage function to the script\n");
			return;
		}
		lua_newtable(L);
		lua_pushstring(L, stanza->body().c_str());
		lua_setfield(L,-2, "body");
		lua_pushstring(L, stanza->from().full().c_str());
		lua_setfield(L,-2, "fromFull");
		lua_pushstring(L, stanza->from().bare().c_str());
		lua_setfield(L,-2, "fromBare");
		lua_pushstring(L, stanza->to().full().c_str());
		lua_setfield(L,-2, "to");
		lua_pushnumber(L, stanza->subtype());
		lua_setfield(L,-2, "type");
	
		/* do the call (1 argument, 1 result) */
		if (lua_pcall(L, 1, 1, 0) != 0)
		{
			printf("Error running function `onMessage': %s",lua_tostring(L, -1));
			return;
		}
		if(lua_istable(L, -1))
		{
			Tag *t = new Tag( "message" );
			
			lua_getfield(L, -1, "type");
			t->addAttribute( "type", luaL_optlstring(L, -1, "chat", NULL) );
			lua_pop(L,1);
			lua_getfield(L, -1, "to");
			t->addAttribute( "to", luaL_optlstring(L, -1, stanza->from().bare().c_str(), NULL )); // 
			lua_pop(L,1);
			lua_getfield(L, -1, "from");
			t->addAttribute( "from", luaL_optlstring(L, -1, j->jid().full().c_str(), NULL ));
			lua_pop(L,1);
			lua_getfield(L, -1, "body");
			t->addChild( new Tag( "body", luaL_optlstring(L, -1, "", NULL) ) );
			lua_pop(L,1);
			j->send( t ); // Send it!
		}
	
		
	}
   
	virtual void onConnect()
	{
		// do something when the connection is established
	printf("Connecting...");
	if(L)
	{
		lua_pushinteger(L, StanzaMessageChat);
		lua_setglobal(L, "MSG_CHAT");
		lua_pushinteger(L, StanzaMessageGroupchat);
		lua_setglobal(L, "MSG_GROUPCHAT");
		lua_pushinteger(L, StanzaMessageNormal);
		lua_setglobal(L, "MSG_NORMAL");
		lua_pushinteger(L, StanzaMessageError);
		lua_setglobal(L, "MSG_ERROR");
		
		lua_pushinteger(L, StanzaPresenceError);
		lua_setglobal(L, "PRE_ERROR");
		lua_pushinteger(L, StanzaPresenceAvailable);
		lua_setglobal(L, "PRE_AVAILABLE");
		lua_pushinteger(L, StanzaPresenceUnavailable);
		lua_setglobal(L, "PRE_UNAVAILABLE");

		lua_register(L, "JoinMUC", lcJoinMUC);
		lua_register(L, "Sleep", lcSleep);
		lua_register(L, "MemUsage", lcMemUsage);
		lua_register(L, "SendPresence", lcSendPresence);
		lua_register(L, "SendMessage", lcSendMessage);
	}
	else
		printf("Lua not loaded?!\n");
	
	 printf("Connected.\n");
	 
	 		lua_getglobal(L, "onConnect");  /* function to be called */
		if(!lua_isfunction(L, -1))
		{
			printf("No onConnect() function found.\n");
			return;
		}
		
		/*Tag *t = new Tag( "presence" );
		t->addAttribute( "to", "test@conference.jabber.org/Betty" );
		t->addChild(new Tag( "status", "Betty!" ) );
		j->send( t ); */
	
		/* do the call (0 arguments, 0 results) */
		if (lua_pcall(L, 0, 0, 0) != 0)
			return; // error(L, "error running function `f': %s",lua_tostring(L, -1));
     
	}
	
	virtual void handlePresence( Stanza * stanza)
	{
				printf("Presence.\n");
			    /* push functions and arguments */
		lua_getglobal(L, "onPresence");  /* function to be called */
		if(!lua_isfunction(L, -1))
			return;
			
		lua_newtable(L);
		lua_pushstring(L, stanza->body().c_str());
		lua_setfield(L,-2, "body");
		lua_pushstring(L, stanza->from().full().c_str());
		lua_setfield(L,-2, "fromFull");
		lua_pushstring(L, stanza->from().bare().c_str());
		lua_setfield(L,-2, "fromBare");
		lua_pushstring(L, stanza->to().full().c_str());
		lua_setfield(L,-2, "to");
		lua_pushnumber(L, stanza->subtype());
		lua_setfield(L,-2, "ntype");
		lua_pushstring(L, stanza->findAttribute("type").c_str());
		lua_setfield(L,-2, "type");
		
		
	
		/* do the call (1 arguments, 0 results) */
		if (lua_pcall(L, 1, 0, 0) != 0)
		{
			printf("Error running function `onPresence': %s",lua_tostring(L, -1));
			return;
		}
		return;
	}

	virtual bool onTLSConnect( const CertInfo& info )
	{
		// decide whether you trust the certificate, examine the CertInfo structure
		// It's not like a bot is bothered with this :)
		return true; // if you trust it, otherwise return false
	}
	
	virtual void onDisconnect(gloox::ConnectionError e)
	{
		std::string msg;
		if (e == ConnStreamError)
		{
			
		}
		switch(e)
		{
			case ConnStreamError:
				msg = j->streamErrorText();
				break;
			case ConnIoError:
				msg = "An I/O error occured";
				break;
			default:
				msg = "Unknown error";
		}
		printf("Disconnected: %s\n", msg.c_str());
	}
	
	virtual void handleLog( LogLevel level, LogArea area, const std::string & message)
	{
		printf("Log: %s\n", message.c_str());
	}	
	
 public:
   Component* j;
};


int main( int argc, char* argv[] )
{
	L = lua_open();   /* opens Lua */
	if(L == NULL)
	{
		printf("Unable to initialize Lua.\n");
		exit(1);
	}
	else
	{
		
	}
	luaL_openlibs(L);
	if(luaL_dofile(L, "bot.lua"))
	{
		printf("Unable to load/run the bot file\n\t%s\n", lua_tostring(L, -1));
		exit(1);
	}
	else
		printf("File loaded successfully.\n");
	
	Bot b;
}

int lcJoinMUC(lua_State* L)
{
	printf("Joining MUC...\n");
	if(!lua_isstring(L,1))
	{
		printf("Ooops, not passed a string :(\n");
		return 0;
	}
	Tag *t = new Tag( "presence" );
	t->addAttribute( "to", lua_tostring(L, 1) );
	if (lua_isstring(L, 2))
		t->addAttribute( "type", lua_tostring(L, 2) );
	
	// t->addChild("status", "Betty!");
	t->addChild(new Tag( "status", "" ) );
	printf(t->xml().c_str() );
	theBot->j->send( t );
	// 
	printf("Conference (%s) joined.\n",lua_tostring(L, 1));
	return 0;
}

int lcLeaveMUC(lua_State* L)
{
	if(!lua_isstring(L,1))
	{
		printf("Ooops, not passed a string :(\n");
		return 0;
	}
	Tag *t = new Tag( "presence" );
	t->addAttribute( "to", lua_tostring(L, 1) );
	t->addAttribute( "type", "unavailable" );
	t->addChild(new Tag( "status", "" ) );
	theBot->j->send( t );
	printf("Conference (%s) joined.\n",lua_tostring(L, 1));
	return 0;
}

int lcSleep(lua_State* L)
{
	sleep((int)lua_tonumber(L, 1));
	return 0;
}	

int lcMemUsage(lua_State* L)
{
	lua_pushinteger(L, lua_gc(L, LUA_GCCOUNT, 0));
	return 1;
}

// function SendPresence(to, type, text[, from]);
int lcSendPresence(lua_State* L)
{
	if(!lua_isstring(L,1))
	{
		printf("Ooops, not passed a string :(\n");
		// lua_error(L, 
		return 0;
	}
	Tag *t = new Tag( "presence" );
	t->addAttribute( "to", lua_tostring(L, 1) );
	if (lua_isstring(L, 2))
		t->addAttribute( "type", lua_tostring(L, 2) );
	else
		t->addAttribute( "type", "available" );
	
	if (lua_isstring(L, 3))
		t->addChild(new Tag( "status", lua_tostring(L, 3) ) );	
	else
		t->addChild(new Tag( "status", "" ) );
	
	if (lua_isstring(L, 4))
		t->addAttribute( "from", lua_tostring(L, 4) );
	
	t->addChild(new Tag("x", "xmlns", "http://jabber.org/protocol/muc#user"));
			
	theBot->j->send( t );
	return 0;
}

int lcSendMessage(lua_State* L)
{
	if(!lua_isstring(L,1))
	{
		printf("Ooops, not passed a string :(\n");
		// lua_error(L, 
		return 0;
	}
	Tag *t = new Tag( "message" );
	t->addAttribute( "to", lua_tostring(L, 1) );
	
	if (lua_isstring(L, 2))
		t->addAttribute( "from", lua_tostring(L, 2) );
	
	if (lua_isstring(L, 3))
		t->addChild(new Tag( "body", lua_tostring(L, 3) ) );	
	else
		t->addChild(new Tag( "body", "" ) );
	
	if (lua_isstring(L, 4))
		t->addAttribute( "type", lua_tostring(L, 4) );
	else
		t->addAttribute( "type", "normal" );
	
			
	theBot->j->send( t );
	return 0;
}

mercurial