Extending NavigatorFactory to log actions like click(), sendKeys()

160 views
Skip to first unread message

Jeevan Adiga

unread,
Apr 12, 2019, 11:26:39 AM4/12/19
to Geb User Mailing List
Hello,

I'm trying to override few methods like click() and leftShift()/value() to log the action using any logging lib like log4j / slf4j.

Can NavigatorFactory(http://gebish.org/manual/current/#navigator-factory) be used to extend/override methods in EmptyNavigator and NonEmptyNavigator class?

If yes, can you please provide pointer/steps/code snippet that needs to be done to achieve this.

If not possible, please suggest any other way of achieving this.

Thank you.

Marcin Erdmann

unread,
Apr 14, 2019, 2:44:59 PM4/14/19
to geb-...@googlegroups.com
Yes, InnerNavigatorFactory has been conceived to allow users to provide their own implementation of Navigator. Your use case of adding some logging to certain methods defined on Navigator is exactly what this mechanism is for.

Simply extend NonEmptyNavigator and EmptyNavigator with what's needed, and then copy the snippet from the manual section you mentioned in your email (http://gebish.org/manual/current/#navigator-factory) into the config file (http://gebish.org/manual/current/#the-config-script) replacing MyCustomNavigator and MyCustomEmptyNavigator with the names of your custom Navigator implementation classes.

--
You received this message because you are subscribed to the Google Groups "Geb User Mailing List" group.
To unsubscribe from this group and stop receiving emails from it, send an email to geb-user+u...@googlegroups.com.
To post to this group, send email to geb-...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/geb-user/f3d8efea-b285-47d0-90c4-0ba459332dc5%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Jeevan Adiga

unread,
Apr 15, 2019, 6:23:05 AM4/15/19
to Geb User Mailing List
Thank you Marcin. I'm able to override the method following your instruction :)

Below is the snippet which did the trick for me.

GebConfig.groovy
innerNavigatorFactory = { Browser browser, List<WebElement> elements ->
 elements
? new NonEmptyCustomNavigator(browser, elements) : new EmptyCustomNavigator()
}


NonEmptyCustomNavigator.groovy
import geb.Browser
import geb.navigator.Navigator
import geb.navigator.NonEmptyNavigator
import groovy.util.logging.Log4j
import org.openqa.selenium.WebElement

@Log4j
class NonEmptyCustomNavigator extends NonEmptyNavigator{

 
NonEmptyCustomNavigator(Browser browser, Collection<? extends WebElement> contextElements) {
 
super(browser, contextElements)
 
}

 
@Override
 
Navigator click() {
 ensureContainsSingleElement
("click")
 contextElements
.first().click()
 log
.info("[" + contextElements.first().toString() + "] Click element")
 
this
 
}
}

EmptyCustomNavigator.groovy
import geb.Browser
import geb.navigator.EmptyNavigator

class EmptyCustomNavigator extends EmptyNavigator {

 
EmptyCustomNavigator(Browser browser) {
 
super(browser)
 
}
}


___________________________

On Monday, 15 April 2019 00:14:59 UTC+5:30, Marcin Erdmann wrote:
Yes, InnerNavigatorFactory has been conceived to allow users to provide their own implementation of Navigator. Your use case of adding some logging to certain methods defined on Navigator is exactly what this mechanism is for.

Simply extend NonEmptyNavigator and EmptyNavigator with what's needed, and then copy the snippet from the manual section you mentioned in your email (http://gebish.org/manual/current/#navigator-factory) into the config file (http://gebish.org/manual/current/#the-config-script) replacing MyCustomNavigator and MyCustomEmptyNavigator with the names of your custom Navigator implementation classes.

On Fri, Apr 12, 2019 at 4:26 PM Jeevan Adiga <adiga...@gmail.com> wrote:
Hello,

I'm trying to override few methods like click() and leftShift()/value() to log the action using any logging lib like log4j / slf4j.

Can NavigatorFactory(http://gebish.org/manual/current/#navigator-factory) be used to extend/override methods in EmptyNavigator and NonEmptyNavigator class?

If yes, can you please provide pointer/steps/code snippet that needs to be done to achieve this.

If not possible, please suggest any other way of achieving this.

Thank you.

--
You received this message because you are subscribed to the Google Groups "Geb User Mailing List" group.
To unsubscribe from this group and stop receiving emails from it, send an email to geb-...@googlegroups.com.

Jeevan Adiga

unread,
Nov 23, 2019, 8:48:02 AM11/23/19
to Geb User Mailing List
Hi Marcin,

Follow-Up Question,

Provided below page representation,
class LoginPage extends BasePage {

    static  at = {
       username.displayed
   }

    static content = {
       username(wait:true) { $("#username input", 0) }
       password(wait: true) { $("#password input")}
       signIn(wait:true) { $("#confirmButton button") }
   }
}

Is it possible to retrieve Navigator name and Page class name in overridden method(click) in NonEmptyCustomNavigator??
ie, 
 @Override
 
Navigator click() {
     ensureContainsSingleElement
("click")
     contextElements
.first().click()

     log
.info("[" + <<NAVIGATOR NAME>> + "] Click element")
     
this
 
}

Output with above implementation is
2019-11-23 19:09:49 INFO  NonEmptyCustomNavigator - [[[ChromeDriver: chrome on XP (72de0f6d86d80aaecb4981bdabb949db)] -> css selector: #logi_confirmButton button]] Click element

Expected output: Provided navigator signIn in LoginPage
2019-11-23 19:09:49 INFO  NonEmptyCustomNavigator - [signIn] Click element                                         // retrieve navigator name
OR
2019-11-23 19:09:49 INFO  NonEmptyCustomNavigator - [LoginPage -> signIn] Click element                   // // retrieve navigator name and page name

Thank you

Marcin Erdmann

unread,
Nov 24, 2019, 3:44:05 PM11/24/19
to geb-...@googlegroups.com
No, unfortunately it's not possible to obtain that in an overridden method. You should be instead using navigator events support added in 3.2 (see https://gebish.org/manual/current/#listening-to-navigator-events). The navigator passed to NavigatorEventListener#afterClick will be an instance of geb.content.TemplateDerivedPageContent (note its getRootContainer() and getContentType() methods) when a page content element is clicked.

--
You received this message because you are subscribed to the Google Groups "Geb User Mailing List" group.
To unsubscribe from this group and stop receiving emails from it, send an email to geb-user+u...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/geb-user/8942a582-07f4-471f-94d7-44673ab4572c%40googlegroups.com.

Jeevan Adiga

unread,
Nov 25, 2019, 12:18:01 AM11/25/19
to Geb User Mailing List
Okay, I'll have a look at NavigatorEventListener. 
Reply all
Reply to author
Forward
0 new messages