This message was deleted.
# plugin-development
s
This message was deleted.
🔝 2
🙌 2
🤯 4
3
🚀 3
j
Are the extensions generated too? They are isolated so they can be seen as a
data class
to contain all properties and any behavior on it can be a method. I haven't checked the internal details, but I guess you are mapping everything into lazy values, so
Copy code
@GExtension
data class MyFancyExtension(
    val prop1: String,
    val prop2: GFile, // or `GInputFile` ?
    @Assisted val randomThing: RandomThing,
) {
    fun foo() {
         // do something with props
    }
}
Copy code
// generated, automatically add `ProjectLayout`, `ObjectFactory`, 
// and any `@Assisted` value.
open class MyFancyExtension @Inject constructor(...) {

    val prop1: Property<String> = ...

    val prop2: FileProperty = ...

    fun foo() {
         // do something with props
    }
}
m
Extensions are not generated by design because they are the "public API" of your plugin and in most of my cases, that doesn't map 1:1 to the task properties
i.e. very often a task property is computed from something else than user input (project model, other tasks, configurations, ....)
j
Yeah, my idea is more about creating them based on some existing extensions. Just removing a bit of boilerplate and the need of understand anything around lazy APIs. Just normal "kotlin types" and the plugin generates the correct things under the hood.
Check the
@GExtension
class in my sample above
m
Oh sorry I missed that!
That could definitely be a thing 👍
It might be a bit problematic though if you want to use any Gradle symbol in your extension
The KSP processor runs in a context that doesn't have access to the Gradle APIs
The extension is more "plugin" code than "implementation" code
j
Can you share an example about this problem?
m
Not really 🙃
You're right, maybe the extension is implementation
But it's a bit weird. The whole point of the separation is to have reflection and classpath isolation which you don't need for extensions
j
I don't know at which point you can generate this in a different module. The setup can become a bit complicated.
m
There are 2 Gradle plugins so we could add a second KSP processor to the "wiring" part if we wanted to
The "wiring" module would also need to depend on
gratatouille-core
(for the
@GExtension
annotation)
Want to open an issue?
j
I have added a clarification about nested extensions Nested extensions should be supported automatically:
Copy code
@GExtension
data class RootFancyExtension(val nestedFancy: NestedFancyExtension, ...)

@GExtension
data class NestedFancyExtension(...)
should be consumed on the user side:
Copy code
rootFancy {
    // ...
    
    nestedFancy {
        // ...
    }
}
t
Have you measured performance impact of classloader isolation workaround? 🤔
m
Not at all at this point but there are a bunch of things we can do to make it better if this is an issue
Like caching the classloader mainly (and try to not leak it too 🙃 )
And the alternative is running everything in the same classloader, right? Which also has issues.