Building Presto plugin for adding User Defined Functions.

Rishav Sarkar
3 min readSep 8, 2022

--

This post explains how to write a simple User Defined Function for Presto plugin.

Most of the time we can solve our problems by using Presto native functions but sometimes we might be required to write user-defined functions for specific functionality.

Creating our Presto UDF project

To start, let’s set up a Presto UDF project. We’ll create it using Java as our language of choice and Maven as the build tool. Aim for Java versions 8 or 11 — those are preferred.

Once the project structure has been created we need to add dependencies to pom.xml for maven build.

Pom.xml Dependencies:

  1. presto-spi: This helps in creating a service provider interface for Presto.
  2. presto-main: The main components of Presto.
  3. slice by Airlift: Provides efficient memory buffer management.
  4. guava by Google: Offers utility methods and data structures.
  5. javax.inject: Supports dependency injection.
  6. log by Airlift: Handles logging functionalities.
  7. joda-time: Helps with date and time manipulation.
  8. presto-spi (Facebook Version 0.275): An earlier version of Presto SPI, marked as a provided dependency.

With our project dependencies in place, it’s time to include the classes for our UDF. Start by creating a package named <package-name> under src -> main -> java. Within this package, add two essential classes for our UDF functionality to operate.

The initial class we require is UdfPlugin. Inside the UdfPlugin.java file, incorporate the following code snippet:

UdfPlugin.java:

package <package-name>;
import com.facebook.presto.spi.Plugin;
import java.util.Set;
import com.google.common.collect.ImmutableSet;
public class UdfPlugin implements Plugin
{
@Override
public Set<Class<?>> getFunctions()
{
return ImmutableSet.<Class<?>>builder()
.add(customUdf.class)
.build();
}
}

This is a boilerplate code that is required to identify our custom UDF. More information on this can be found in Presto's official documentation.

Notice the line .add(customUdf.class) in the above code. customUdf is the class we need to define which will contain our UDF.

We then proceed forward to writing the customUdf.java class file. Inside the package <package-name> we need to create a file customUdf.java. Inside customUdf.java we need to add the following code:

customUdf.java:

package <package-name>;
import com.facebook.presto.common.type.StandardTypes;
import com.facebook.presto.spi.function.Description;
import com.facebook.presto.spi.function.ScalarFunction;
import com.facebook.presto.spi.function.SqlType;
import java.util.Random;
public class customUdf {

@Description("Returns a random number")
@ScalarFunction("randomNumberGenerator")
@SqlType(StandardTypes.BIGINT)
public static long randomNumberGenerator()
{
Random rd = new Random();
return rd.nextInt();
}

}

This is a simple UDF that will generate a random number. Below is the description of the code.

@Description: Description for the UDF.

@ScalarFunction: Name of the UDF to be identified by Presto.

@SqlType: This is the return type for the UDF.

Inside the function randomNumberGenerator() we have our code block to generate and return a random integer.

More information related to function, return type, and input parameters can be found here.

Following the structure setup, let’s proceed by adding a resources folder within src -> main -> java. Inside this resources folder, create another folder named META-INF/services. Within the META-INF/services folder, create two files: com.facebook.presto.spi.Plugin and io.prestosql.spi.Plugin. Inside each file, specify <package-name>.UdfPlugin. This step is crucial as it helps the Presto plugin service locate UdfPlugin.java, which holds our UDF class.

Once these configurations are in place, the UDF setup is complete. Now, it’s time to build the JAR for deployment on the Presto server. Since this is a Maven project, execute the command mvn clean package in the command prompt or terminal from the project directory. This command will generate a JAR file for our project within the target folder located in the project directory.

Presto provides detailed documentation on how to write a user-defined function for the Presto plugin.

The source code for the project can be found here.

--

--