Query Listeners

This is available as an experimental feature (i.e. hidden) in Lucee 5.3 and is officially supported in Lucee 6.0.

5 Likes

Also, lucee has a listener for mail listener

LDEV-1452 add support for mail listener

2 Likes

Yup, if anyone feels like jumping in and writing up some docs, that would be great!

waves to @Gavin_Baumanis :slight_smile:

2 Likes

It’s a really interesting idea. I’m gonna let it settle in the back of my brain, see what it comes up with. One thought that I had was that in my SQL, I almost always prefix the query with a SQL-comment defining where it comes from so that when it shows up in the Slow-Logs or in FusionReactor, I know which query it was. As in:

<cfquery name="local.results">
    /* DEBUG: userGateway.getUserByID(). */
    SELECT .....
</cfquery>

Given that you pass-in the caller, it seems like this might be something I could automatically prefix to every query. Granted, the caller information (looks like file + line in your screenshots) isn’t exactly the same; but, it would give me the ability to blanket-apply to the entire app.

3 Likes

Great idea! This is also great for generated code or dynamic query runners (we have a CRUDModel) for example that various components run. Will see about adding it.

Where is the path to the component specified? It looks like the examples presume it’s in the root.

it’s just an instance of a component, up to u

the query listener can be a struct(that has a key before/after with closure as value)/ closure (that calls after the query execution is completed)

this.query.listener = {
	    before = function (caller,args) {
	        systemOutput(arguments,1,1);
	        dump(arguments);
	        return args;
	    }
	    ,after = function () {
	        systemOutput(arguments,1,1);
	        dump(arguments);
	    }
	};

OR

this.query.listener = function () {
        systemOutput(arguments,1,1);
        dump(arguments);
    };

LDEV-1881 add listener for cfquery in application.cfc/cfapplication

We can define the listener in Application.cfc(using this.query.listener)/ Application datasource definition / query tag( using listener attribute) as mentioned in the ticket.

Sure!

1 Like

The docs for the Mail Listeners Mail Listeners :: Lucee Documentation

3 Likes

I tried using this with the following code.

component {
  // https://docs.lucee.org/guides/cookbooks/query_listeners.html
	function before( caller, args ) {
    args.sql = "/* #listLast(arguments.caller.template,'\')# (#arguments.caller.line#)  */
    " & args.sql
		return arguments;
	}
	function after( caller, args, result, meta ) { 
		return arguments;
	}
}

But the comment I’m hoping to see looks like this in every query. https://www.screencast.com/t/iHiAoIC5hY2R Running the latest version of 5.3.9 (whatever commandbox thinks that is)

try returning args not arguments

I tried both since the docs show it both ways. Query Listeners :: Lucee Documentation

The queries are making it to the database, so I don’t think the return is the problem. When I add systemoutput(caller), I see this in the terminal. 09.19.2022-04.36.08

Following up, this is still an issue in 5.3.9+160, though the character seems to change randomly. Interestingly, everything is getting sent to systemOutput() as well. I presume this won’t be the case when it’s fixed. 10.19.2022-14.05.42

I’ve tried it locally and caller is being properly populated correctly

can you provide a working example to reproduce the problem?

looks like you are using GitHub - coldbox-modules/cbq: A protocol-based queueing system for ColdBox

does it work with plain old normal queries for u?

The code I posted above is what I’m using. I use coldbox and QB extensively, but QB uses queryExecute under the hood. Plain old normal query at the end of the day.

I will try to provide an example, but I’m swamped right now, so we’ll see how that goes.

I tried this in a brand new application and I’m getting the same results. This is the result of using the following code.

component {
  // https://docs.lucee.org/guides/cookbooks/query_listeners.html
	function before( caller, args ) {
    dump(caller);dump(args);abort;
    args.sql = "/* #listLast(arguments.caller.template,'\')# (#arguments.caller.line#)  */
    " & args.sql
		return arguments;
	}
	function after( caller, args, result, meta ) {
		return arguments;
	}
}

can you try throw an exceptioning or dumping callStackGet()?

Tho, I’m not sure if that will work in the context of a listener

I’m not clear on how you want me to throw an exception, but this is callStackGet(): 11.25.2022-15.52.38 BaseGrammar.cfc runs queryExecute().

Can you provide a reproducible example?