How do I add a generic method to an existing interface?

72 views
Skip to first unread message

Scott Babcock

unread,
Nov 27, 2019, 10:07:39 PM11/27/19
to Byte Buddy
This is compound confusion. I need to apply the following changes to an existing API (Google Guava):
  • Add this method to interface com.google.common.util.concurrent.TimeLimiter
    <T> T callWithTimeout(Callable<T>, long, TimeUnit, boolean) throws Exception;
  • Change accessibility of this constructor in class com.google.common.util.concurrent.SimpleTimeLimiter to public:
    SimpleTimeLimiter(ExecutorService)
  • Change accessibility of this method in class com.google.common.util.concurrent.SimpleTimeLimiter to public:
    <T> T callWithTimeout(Callable<T>, long, TimeUnit, boolean) throws Exception
These transformations will need to be performed by a Java agent so I can upgrade the dependency declared by Selenium 2.53.1 from Guava 19.0 to the current release (28.1-android). The older release of Guava contains an unbounded memory allocation vulnerability that has since been resolved. Unfortunately, the UrlChecker class in Selenium 2 uses the constructor and method shown above that have been made private, and it also refers to the method through the interface .

I've been unable to figure out how to implement the transformer to apply these changes. 
  • How do I represent the type parameter T in the method signature?
  • How do I add a method to an existing interface?
  • How do I change the accessibility of an existing constructor or method?

Message has been deleted

Scott Babcock

unread,
Nov 27, 2019, 11:32:31 PM11/27/19
to Byte Buddy
One potential complication here is that the final solution needs to work on Java 7.

Rafael Winterhalter

unread,
Nov 28, 2019, 2:52:34 PM11/28/19
to Scott Babcock, Byte Buddy
That should be quite simple:

new AgentBuilder.Default()
  .type(named("com.google.common.util.concurrent.TimeLimiter"))
  .transform((builder, type, classloader, module) -> builder
    .defineMethod("callWithTimeout", Object.class, Visibility.PUBLIC).withParameters(Callable.class, TimeUnit.class).withoutCode())
  .type(named("com.google.common.util.concurrent.SimpleTimeLimiter"))
  .transform((builder, type, classloader, module) -> builder
    .visit(new ModifierAdjustment().withInvokableModifiers(isConstructor().or(named("callWithTimeout"), Visibility.PUBLIC))

At runtime, all generic types are erased to their most specialized type. If you wanted to get the generic signatures correct for reflection purposes, you can use TypeDescription.Generic.Builder to create them and define a type variable T on the method using the DSL. As for the matchers, you can make them more specific if you wanted but making types public is always possible since you do not reduce any visibility.
    .

Am Do., 28. Nov. 2019 um 05:32 Uhr schrieb Scott Babcock <sco...@gmail.com>:
One potential complication here is that the final solution needs to work on Java 7.

--
You received this message because you are subscribed to the Google Groups "Byte Buddy" group.
To unsubscribe from this group and stop receiving emails from it, send an email to byte-buddy+...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/byte-buddy/67594a6b-396a-478b-ae3b-03d921f6d8da%40googlegroups.com.

Rafael Winterhalter

unread,
Nov 28, 2019, 2:52:59 PM11/28/19
to Scott Babcock, Byte Buddy
PS: Despite using lambdas, by using anonymous classes, you can support down to Java 5 which Byte Buddy compiles to.

Scott Babcock

unread,
Nov 29, 2019, 6:05:58 PM11/29/19
to Byte Buddy
Thanks! The Byte Buddy API is so massive that I get totally lost without examples to follow. The whole "visit" feature is still a mystery to me. Where can I find an explanation of this feature?

Rafael Winterhalter

unread,
Nov 30, 2019, 2:37:46 PM11/30/19
to Scott Babcock, Byte Buddy
Basically, visit means that existing methods are decorated. Visitors can be stacked upon one method and enrich or modify them while leaving the original implementation intact whereas interceptions are exclusive and replace the existing method's implementation.

Yes, there is a lack of documentation. I'd love to address it but time is sparse. I really hope I can change this at some point.

Am Sa., 30. Nov. 2019 um 00:06 Uhr schrieb Scott Babcock <sco...@gmail.com>:
Thanks! The Byte Buddy API is so massive that I get totally lost without examples to follow. The whole "visit" feature is still a mystery to me. Where can I find an explanation of this feature?

--
You received this message because you are subscribed to the Google Groups "Byte Buddy" group.
To unsubscribe from this group and stop receiving emails from it, send an email to byte-buddy+...@googlegroups.com.
Reply all
Reply to author
Forward
0 new messages