Opérations courantes dans des UDFs Java

Cette rubrique montre comment des UDFs Java peuvent effectuer des opérations courantes, comme la lecture d’un fichier (par exemple, un fichier de configuration).

Dans ce chapitre :

Lecture d’un fichier à partir d’une UDF Java

Exemple de code pour la lecture d’un fichier

Une UDF Java peut lire des fichiers (par exemple, des fichiers de configuration) qui ont été stockés dans une zone de préparation. Le nom du fichier et le nom de la zone de préparation doivent avoir été spécifiés dans la clause IMPORTS de la commande CREATE FUNCTION.

Lorsqu’un fichier est spécifié dans la clause IMPORTS d’une UDF, Snowflake copie ce fichier de la zone de préparation vers le répertoire d’accueil (également appelé répertoire d’importation) de l’UDF, qui est le répertoire à partir duquel l’UDF lit réellement le fichier.

Étant donné que les fichiers importés sont copiés dans un seul répertoire et qu’ils doivent avoir des noms uniques au sein de ce répertoire, chaque fichier de la clause IMPORTS doit avoir un nom distinct, même si les fichiers commencent dans différentes zones de préparation ou différents sous-répertoires au sein d’une zone de préparation.

L’exemple suivant crée et appelle une UDF Java qui lit un fichier :

Le code source Java ci-dessous crée une méthode Java nommée read_file(). Cette UDF utilise cette méthode.

import java.io.IOException;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.stream.Stream;

class TestReadRelativeFile {
    public static String read_file(String fileName) throws IOException {
        StringBuilder contentBuilder = new StringBuilder();
        String importDirectory = System.getProperty("com.snowflake.import_directory");
        String fPath = importDirectory + fileName;
        Stream<String> stream = Files.lines(Paths.get(fPath), StandardCharsets.UTF_8);
        stream.forEach(s -> contentBuilder.append(s).append("\n"));
        return contentBuilder.toString();
    }
}

Le code SQL suivant crée l” UDF. Ce code suppose que le code source Java a été compilé et placé dans un fichier JAR nommé TestReadRelativeFile.jar, que l’UDF importe. Les deuxième et troisième fichiers importés, my_config_file_1.txt et my_config_file_2.txt, sont des fichiers de configuration que l’UDF peut lire.

CREATE FUNCTION file_reader(file_name VARCHAR)
RETURNS VARCHAR
LANGUAGE JAVA
IMPORTS = ('@my_stage/my_package/TestReadRelativeFile.jar',
           '@my_stage/my_path/my_config_file_1.txt',
           '@my_stage/my_path/my_config_file_2.txt')
HANDLER = 'my_package.TestReadRelativeFile.read_file';

Ce code appelle l’UDF :

SELECT file_reader('my_config_file_1.txt') ...;
...
SELECT file_reader('my_config_file_2.txt') ...;

Choisir d’accéder à un fichier dans un format compressé ou non compressé

Les fichiers d’une zone de préparation peuvent être stockés en format compressé ou non compressé. Les utilisateurs peuvent compresser le fichier avant de le copier dans la zone de préparation, ou demander à la commande PUT de compresser le fichier.

Lorsque Snowflake copie un fichier compressé au format GZIP d’une zone de préparation vers le répertoire d’accueil de l’UDF, Snowflake peut écrire la copie telle quelle, ou Snowflake peut décompresser le contenu avant d’écrire le fichier.

Si le fichier de la zone de préparation est compressé et si vous souhaitez que la copie dans le répertoire d’accueil de l’UDF soit également compressée, lorsque vous spécifiez le nom du fichier dans la clause IMPORTS, utilisez simplement le nom du fichier original (par ex. « MyData.txt.gz ») dans la clause IMPORTS. Par exemple :

... imports = ('@MyStage/MyData.txt.gz', ...)

Si le fichier de la zone de préparation est compressé au format GZIP et si vous souhaitez que la copie dans le répertoire d’accueil de l’UDF soit également compressée, lorsque vous spécifiez le nom du fichier dans la clause IMPORTS, retirez l’extension « .gz ». Par exemple, si votre zone de préparation contient « MyData.txt.gz », mais que vous voulez que votre UDF lise le fichier au format non compressé, spécifiez « MyData.txt » dans la clause IMPORTS. S’il n’existe pas déjà un fichier non compressé nommé « MyData.txt », alors Snowflake recherche « MyData.txt.gz » et écrit automatiquement une copie décompressée dans « MyData.txt » dans le répertoire personnel de l’UDF. Votre UDF peut alors ouvrir et lire le fichier non compressé « MyData.txt ».

Notez que la décompression intelligente ne s’applique qu’à la copie dans le répertoire d’accueil de l’UDF ; le fichier original dans la zone de préparation n’est pas modifié.

Suivez ces meilleures pratiques pour la manipulation des fichiers compressés :

  • Respectez les conventions de dénomination des fichiers. Si un fichier est au format compressé GZIP, incluez l’extension « .gz » à la fin du nom du fichier. Si un fichier n’est pas au format compressé GZIP, il ne faut pas terminer le nom du fichier par l’extension « .gz ».

  • Évitez de créer des fichiers dont les noms ne diffèrent que par l’extension « .gz ». Par exemple, ne créez pas à la fois « MyData.txt » et « MyData.txt.gz » dans la même zone de préparation et le même répertoire, et n’essayez pas d’importer à la fois « MyData.txt » et « MyData.txt.gz » dans la même commande CREATE FUNCTION.

  • Ne compressez pas les fichiers deux fois. Par exemple, si vous compressez un fichier manuellement, puis vous placez (PUT) ce fichier sans utiliser AUTO_COMPRESS=FALSE, le fichier sera compressé une seconde fois. La décompression intelligente ne le décompressera qu’une seule fois, de sorte que le fichier de données (ou JAR) sera toujours compressé lorsqu’il sera stocké dans le répertoire d’accueil de l’UDF.

  • À l’avenir, Snowflake pourrait étendre la décompression intelligente à des algorithmes de compression autres que GZIP. Pour éviter les problèmes de compatibilité à l’avenir, appliquez ces meilleures pratiques aux fichiers qui utilisent tout type de compression.

Note

Les fichiers JAR peuvent également être stockés en format compressé ou non compressé dans une zone de préparation. Snowflake décompresse automatiquement tous les fichiers JAR compressés avant de les mettre à la disposition de l’UDF Java.