# Exposing methods from plugin

**URL:** <https://discuss.gradle.org/t/exposing-methods-from-plugin/12275>\
**Category:** Help/Discuss\
**Created:** [October 18, 2015, 11:21am UTC](https://discuss.gradle.org/t/exposing-methods-from-plugin/12275 "2015-10-18T11:21:54Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![kdabir](https://sea1.discourse-cdn.com/gradle/user_avatar/discuss.gradle.org/kdabir/32/3180_2.png) [@kdabir](https://discuss.gradle.org/u/kdabir)\
**Post date:** [October 18, 2015, 11:21am UTC](https://discuss.gradle.org/t/exposing-methods-from-plugin/12275/1 "2015-10-18T11:21:54Z")

</div>

What is the correct/idiomatic way for a plugin to expose a method such that it can be called in the build script that applies the plugin. So far I could only think of either method on an extension object or a closure on extra properties (ext namespace) and both of which are apparently discouraged

[here](https://discuss.gradle.org/t/is-it-possible-to-put-a-groovy-function-into-a-file-in-buildsrc-and-simply-call-it-from-a-task-in-the-main-build-gradle/6931/6)

> Extensions are meant as a way of extending the build script DSL.

and [here](https://discuss.gradle.org/t/ext-vs-extensions/3429/2)

> The ‘ext’ space is for adhoc storage. Plugins should never use this

All I want to be able to do in build.gradle is to call `my.namespace.method(with, some, params)`. And, if at all there is no other way, which one of the two above is lesser evil 😈

---

<div class="post-metadata">

**Author:** ![sterling](https://sea1.discourse-cdn.com/gradle/user_avatar/discuss.gradle.org/sterling/32/5395_2.png) [@sterling](https://discuss.gradle.org/u/sterling)\
**Post date:** [October 18, 2015, 2:48pm UTC](https://discuss.gradle.org/t/exposing-methods-from-plugin/12275/2 "2015-10-18T14:48:05Z")

</div>

I think the preference is:

No method \> method on custom extension \> method on custom type \> method (extra property) on existing extension \> method (extra property) on existing type \> method (extra property) on Project.

I say “No method” is the most preferred to mean that it can be too magical if someone using your plugin does something like this:

```gradle
apply plugin: 'my-plugin'

myPlugin.setup("foo", 1, ["x", "y", "z"])

```

to mean “set the `domainName` to foo, the `threshold` to 1 and the `list of widgets` to x, y, z”.

Instead, you’d prefer to give better names to things and make it a little more explicit, e.g.,

```gradle
apply plugin: 'my-plugin'

myPlugin {
   domainName = "foo"
   threshold = 1
   listOfWidgets = ['x', 'y', 'z']
}

```

Then as part of configuring tasks/other things, you can validate that everything is configured correctly and complain if it isn’t.

I think the only exception to this might be where you need a utility or builder method that creates a complicated object (this would be something like `project.fileTree` or `project.file`). I’d put a method like that on the extension to give it a namespace.

HTH

---

<div class="post-metadata">

**Author:** ![kdabir](https://sea1.discourse-cdn.com/gradle/user_avatar/discuss.gradle.org/kdabir/32/3180_2.png) [@kdabir](https://discuss.gradle.org/u/kdabir)\
**Post date:** [October 18, 2015, 5:12pm UTC](https://discuss.gradle.org/t/exposing-methods-from-plugin/12275/3 "2015-10-18T17:12:22Z")

</div>

Wow. Thanks for such an elaborate explanation.

I’d totally agree that setting up domain model using DSL block is way better than calling a method. However the methods I am looking to expose are more action oriented utility methods which apply only context of our build.

To quote some example from Gradle API, I think `project.copy()` or `project.delete()` would be closest.

---

<div class="post-metadata">

**Author:** ![sterling](https://sea1.discourse-cdn.com/gradle/user_avatar/discuss.gradle.org/sterling/32/5395_2.png) [@sterling](https://discuss.gradle.org/u/sterling)\
**Post date:** [October 18, 2015, 5:52pm UTC](https://discuss.gradle.org/t/exposing-methods-from-plugin/12275/4 "2015-10-18T17:52:23Z")

</div>

No worries, glad to help.

Something like `project.copy()` or `project.delete()` I would expose either as custom task types (if that makes sense), as a utility class (for someone to build their own custom task types/plugins on top of) or a method on the extension. Wrapping actions in a task are usually the way to go so you can make them incremental, but it would really depend on exactly what the action-like methods are doing.

---

<div class="post-metadata">

**Author:** ![wszebor](https://avatars.discourse-cdn.com/v4/letter/w/bc79bd/32.png) [@wszebor](https://discuss.gradle.org/u/wszebor)\
**Post date:** [November 6, 2018, 12:40pm UTC](https://discuss.gradle.org/t/exposing-methods-from-plugin/12275/5 "2018-11-06T12:40:21Z")

</div>

I’m facing exactly this code design problem. I would like my binary plugin to provide the helper util method for manipulating RelativePaths, one to be used in many places of the build scripts. I can put it into my extension class, but this looks a bit wrong for me, as extensions seems to be thought to provide DSL constructs for modeling and not the general helper methods. So, maybe I should provide the utility class as suggested above and put my method into it - but how to make this utility class available for use in the build scripts? Please help. Code examples are welcome.
