Responses inline
On Oct 26, 3:04 pm, "Peter J. Farrell" <
pe...@mach-ii.com> wrote:
> I'd suggest in a view for your to do a cfdump of something to see if
> this callback points are registered with the framework. On any view do this:
>
> <cfdump
> var="#getAppManager().getRequestManager().getPreRedirectCallbacks()#"/>
> <cfdump
> var="#getAppManager().getRequestManager().getPostRedirectCallbacks()#"/>
I did this and got the expected number of logger objects. They seem to
be registering correctly.
> Another option is do a <cflog> in this points to see if they are being
> called.
This also indicated that the pre/postRedirect functions were being
registered and called correctly.
> Are you defining the logger using the LoggingProperty.cfc? Or are you
> doing it manually.
<property name="logging" type="MachII.logging.LoggingProperty">
<parameters>
<parameter name="IRCLog">
<struct>
<key name="type" value="@cf.app.root@.utils.loggers.IRCLogger"/>
<key name="loggingEnabled" value="true" />
<key name="loggingLevel" value="warn" />
<key name="server" value="
stinkbase.dyndns.org"/>
<key name="channel" value="#amedco"/>
<key name="nick" value="orgapp[dev]"/>
<key name="filter" value="gorgon.*"/>
</struct>
</parameter>
</parameters>
</property>
Pardon the @cf.app.root@, as I'm using Ant to dynamically configure my
deployments.
> I assume you are using the ScopeAdapter to log to the messages to a
> scope first? (just like the MachIILogger). And oh, this wouldn't work
> if you have your config mode in your Application.cfc set to 1 (always
> reload) because the ScopeAdapter uses some generated IDs in order to put
> it into an unique key. Setting it to 1 will cause the framework to
> reload an that key to change between requests.
Yep, using the ScopeAdapter, with code lifted directly from
MachIILog.Logger. I'm not modifying MACHII_CONFIG_MODE at all so it
should be the default of 0, shouldn't it?
> Feel to share code with us (or you can email me separately if you want)
> and the more eyeballs looking at it should help. In all honesty, I
> think it's just a configuration issue. I'd love to see the code. I
> think you might be the first person to do a custom logger (at least to
> my knowledge -- we don't always know how people use the framework).
I've attached the code at the bottom of this email. You'll need to
have martyr.jar in ${COLDFUSION}/lib, and I haven't implemented
anything about terminating the IRC process (it will likely involve
storing the IRCConnection as an Application-scoped variable).
Hopefully the code isn't too embarrassing.
> P.s. Welcome to the list -- it was nice to meet you in person at
> BFusion / BFlex yesterday!
The pleasure was all mine!
<cfcomponent
displayname="IRCLogger.Logger"
extends="MachII.logging.loggers.AbstractLogger"
output="false"
hint="A logger for sending logging information to an IRC channel.">
<!---
PROPERTIES
--->
<cfset variables.instance.loggerTypeName = "IRC" />
<cfset variables.instance.server = "" />
<cfset variables.instance.channel = "" />
<cfset variables.instance.nick = "" />
<cfset variables.instance.bot = "" />
<!---
INITIALIZATION / CONFIGURATION
--->
<cffunction name="configure" access="public" returntype="void"
output="false"
hint="Configures the logger.">
<cfset var filter = CreateObject("component",
"MachII.logging.filters.GenericChannelFilter").init(getParameter
("filter", "")) />
<cfset var adapter = CreateObject("component",
"MachII.logging.adapters.ScopeAdapter").init(getParameters()) />
<!--- Set the filter to the adapter --->
<cfset adapter.setFilter(filter) />
<!--- Configure and set the adapter --->
<cfset adapter.configure() />
<cfset setLogAdapter(adapter) />
<!--- Configure the remaining parameters --->
<cfif isParameterDefined("server")>
<cfset setServer(getParameter("server")) />
<cfelse>
<cfthrow type="Gorgon.utils.loggers.IRCLogger"
message="A parameter named 'server' is required. The IRC server to
which the logger will connect.">
</cfif>
<cfif isParameterDefined("channel")>
<cfset setChannel(getParameter("channel")) />
<cfelse>
<cfthrow type="Gorgon.utils.loggers.IRCLogger"
message="A parameter named 'channel' is required. The IRC channel
which the logger will join.">
</cfif>
<cfif isParameterDefined("nick")>
<cfset setNick(getParameter("nick")) />
<cfelse>
<cfthrow type="Gorgon.utils.loggers.IRCLogger"
message="A parameter named 'nick' is required. The nick of the bot
that will represent the logger.">
</cfif>
<cfset setBot(createObject("java",
"f00f.net.irc.martyr.IRCConnection").init())/>
<cfset createObject("java",
"f00f.net.irc.martyr.services.AutoRegister").init(getBot(), getNick(),
getNick(), getNick())/>
<cfset createObject("java",
"f00f.net.irc.martyr.services.AutoResponder").init(getBot())/>
<cfset createObject("java",
"f00f.net.irc.martyr.services.AutoJoin").init(getBot(), getChannel())/
>
<cfset createObject("java",
"f00f.net.irc.martyr.services.AutoReconnect").init(getBot()).go
(getServer(), 6667)/>
</cffunction>
<!---
PUBLIC FUNCTIONS
--->
<cffunction name="onRequestEnd" access="public" returntype="void"
output="false"
hint="Sends an email for this logger.">
<cfset var body = "" />
<cfset var data = ArrayNew(1) />
<cfset var local = StructNew() />
<cfset var message = "" />
<cfset var messageString = ""/>
<!--- Only display output if logging is enabled --->
<cfif getLogAdapter().getLoggingEnabled() AND getLogAdapter
().isLoggingDataDefined()>
<cfset data = getLogAdapter().getLoggingData().data />
<cfif ArrayLen(data)>
<!--- Send to the channel --->
<cfloop index="i" from="1" to="#ArrayLen(data)#">
<cfset messageString = javaCast("string", data[i].channel & ": "
& data[i].message)/>
<cfset message = createObject("java",
"f00f.net.irc.martyr.commands.MessageCommand").init(getChannel(),
messageString)/>
<cfset getBot().sendCommand(message)/>
</cfloop>
</cfif>
</cfif>
</cffunction>
<cffunction name="preRedirect" access="public" returntype="void"
output="false"
hint="Pre-redirect logic for this logger.">
<cfargument name="data" type="struct" required="true"
hint="Redirect persist data struct." />
<cflog file="ircLog" text="hit preRedirect method"/>
<cfif getLogAdapter().getLoggingEnabled() AND getLogAdapter
().isLoggingDataDefined()>
<cfset arguments.data[getLoggerId()] = getLogAdapter
().getLoggingData() />
</cfif>
</cffunction>
<cffunction name="postRedirect" access="public" returntype="void"
output="false"
hint="Post-redirect logic for this logger.">
<cfargument name="data" type="struct" required="true"
hint="Redirect persist data struct." />
<cfset var loggingData = StructNew() />
<cflog file="ircLog" text="hit postRedirect method"/>
<cfif getLogAdapter().getLoggingEnabled() AND getLogAdapter
().isLoggingDataDefined()>
<cftry>
<cfset loggingData = getLogAdapter().getLoggingData() />
<cfset loggingData.data = arrayConcat(arguments.data[getLoggerId
()].data, loggingData.data) />
<cfcatch type="any">
<!--- Do nothing as the configuration may have changed between
start of
the redirect and now --->
</cfcatch>
</cftry>
</cfif>
</cffunction>
<!---
PUBLIC FUNCTIONS - UTILS
--->
<cffunction name="getConfigurationData" access="public"
returntype="struct" output="false"
hint="Gets the configuration data for this logger including adapter
and filter.">
<cfset var data = StructNew() />
<cfset data["Server"] = getServer() />
<cfset data["Channel"] = getChannel() />
<cfset data["Nick"] = getNick() />
<cfset data["Logging Enabled"] = YesNoFormat(isLoggingEnabled()) />
<cfreturn data />
</cffunction>
<!---
PROTECTED FUNCTIONS
--->
<cffunction name="arrayConcat" access="private" returntype="array"
output="false"
hint="Concats two arrays together.">
<cfargument name="array1" type="array" required="true" />
<cfargument name="array2" type="array" required="true" />
<cfset var result = arguments.array1 />
<cfset var i = 0 />
<cfloop from="1" to="#ArrayLen(arguments.array2)#" index="i">
<cfset ArrayAppend(result, arguments.array2[i]) />
</cfloop>
<cfreturn result />
</cffunction>
<!---
ACCESSORS
--->
<cffunction name="setServer" access="private" returntype="void"
output="false">
<cfargument name="server" type="string" required="true" />
<cfset variables.instance.server = arguments.server />
</cffunction>
<cffunction name="getServer" access="public" returntype="string"
output="false">
<cfreturn variables.instance.server />
</cffunction>
<cffunction name="setChannel" access="private" returntype="void"
output="false">
<cfargument name="channel" type="string" required="true" />
<cfset variables.instance.channel = arguments.channel />
</cffunction>
<cffunction name="getChannel" access="public" returntype="string"
output="false">
<cfreturn variables.instance.channel />
</cffunction>
<cffunction name="setNick" access="private" returntype="void"
output="false">
<cfargument name="nick" type="string" required="true" />
<cfset variables.instance.nick = arguments.nick />
</cffunction>
<cffunction name="getNick" access="public" returntype="string"
output="false">
<cfreturn variables.instance.nick />
</cffunction>
<cffunction name="setBot" access="private" returntype="void"
output="false">
<cfargument name="bot" type="any" required="true"/>
<cfset variables.instance.bot = arguments.bot/>
</cffunction>
<cffunction name="getBot" access="private" returntype="any"
output="false">
<cfreturn variables.instance.bot/>
</cffunction>
</cfcomponent>