Używanie funkcji UDF języka Java z usługą Apache Hive w usłudze HDInsight

Dowiedz się, jak utworzyć funkcję zdefiniowaną przez użytkownika (UDF) opartą na języku Java, która współpracuje z usługą Apache Hive. Funkcja UDF języka Java w tym przykładzie konwertuje tabelę ciągów tekstowych na małe litery.

Wymagania wstępne

  • Klaster Hadoop w usłudze HDInsight. Zobacz Wprowadzenie z usługą HDInsight w systemie Linux.

  • Zestaw Java Developer Kit (JDK) w wersji 8

  • Narzędzie Apache Maven poprawnie zainstalowane zgodnie z platformą Apache. Maven to system kompilacji projektu dla projektów Java.

  • Schemat identyfikatora URI dla magazynu podstawowego klastrów. Byłoby to wasb:// dla usługi Azure Storage, abfs:// dla Azure Data Lake Storage Gen2 lub adl:// dla Azure Data Lake Storage Gen1. Jeśli bezpieczny transfer jest włączony dla usługi Azure Storage, identyfikator URI to wasbs://. Zobacz również bezpieczny transfer.

  • Edytor tekstów lub środowisko IDE Języka Java

    Ważne

    Jeśli tworzysz pliki języka Python na kliencie Windows, musisz użyć edytora, który używa LF jako zakończenia wiersza. Jeśli nie masz pewności, czy edytor używa LF lub CRLF, zobacz sekcję Rozwiązywanie problemów , aby uzyskać instrukcje dotyczące usuwania znaku CR.

Środowisko testowe

Środowisko używane w tym artykule było komputerem z systemem Windows 10. Polecenia zostały wykonane w wierszu polecenia, a różne pliki zostały edytowane za pomocą Notatnik. Zmodyfikuj odpowiednio środowisko.

W wierszu polecenia wprowadź poniższe polecenia, aby utworzyć środowisko robocze:

IF NOT EXIST C:\HDI MKDIR C:\HDI
cd C:\HDI

Tworzenie przykładowej funkcji UDF języka Java

  1. Utwórz nowy projekt Maven, wprowadzając następujące polecenie:

    mvn archetype:generate -DgroupId=com.microsoft.examples -DartifactId=ExampleUDF -DarchetypeArtifactId=maven-archetype-quickstart -DinteractiveMode=false
    

    To polecenie tworzy katalog o nazwie exampleudf, który zawiera projekt Maven.

  2. Po utworzeniu projektu usuń exampleudf/src/test katalog utworzony w ramach projektu, wprowadzając następujące polecenie:

    cd ExampleUDF
    rmdir /S /Q "src/test"
    
  3. Otwórz, pom.xml wprowadzając poniższe polecenie:

    notepad pom.xml
    

    Następnie zastąp istniejący <dependencies> wpis następującym kodem XML:

    <dependencies>
        <dependency>
            <groupId>org.apache.hadoop</groupId>
            <artifactId>hadoop-client</artifactId>
            <version>2.7.3</version>
            <scope>provided</scope>
        </dependency>
        <dependency>
            <groupId>org.apache.hive</groupId>
            <artifactId>hive-exec</artifactId>
            <version>1.2.1</version>
            <scope>provided</scope>
        </dependency>
    </dependencies>
    

    Te wpisy określają wersję usług Hadoop i Hive dołączoną do usługi HDInsight 3.6. Informacje o wersjach usług Hadoop i Hive dostępnych w usłudze HDInsight można znaleźć w dokumencie przechowywania wersji składników usługi HDInsight .

    Dodaj sekcję <build> przed wierszem </project> na końcu pliku. Ta sekcja powinna zawierać następujący kod XML:

    <build>
        <plugins>
            <!-- build for Java 1.8. This is required by HDInsight 3.6  -->
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.3</version>
                <configuration>
                    <source>1.8</source>
                    <target>1.8</target>
                </configuration>
            </plugin>
            <!-- build an uber jar -->
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-shade-plugin</artifactId>
                <version>3.2.1</version>
                <configuration>
                    <!-- Keep us from getting a can't overwrite file error -->
                    <transformers>
                        <transformer
                                implementation="org.apache.maven.plugins.shade.resource.ApacheLicenseResourceTransformer">
                        </transformer>
                        <transformer implementation="org.apache.maven.plugins.shade.resource.ServicesResourceTransformer">
                        </transformer>
                    </transformers>
                    <!-- Keep us from getting a bad signature error -->
                    <filters>
                        <filter>
                            <artifact>*:*</artifact>
                            <excludes>
                                <exclude>META-INF/*.SF</exclude>
                                <exclude>META-INF/*.DSA</exclude>
                                <exclude>META-INF/*.RSA</exclude>
                            </excludes>
                        </filter>
                    </filters>
                </configuration>
                <executions>
                    <execution>
                        <phase>package</phase>
                        <goals>
                            <goal>shade</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
        </plugins>
    </build>
    

    Te wpisy definiują sposób kompilowania projektu. W szczególności wersja języka Java używana przez projekt i sposób tworzenia uberjar do wdrożenia w klastrze.

    Zapisz plik po wprowadzeniu zmian.

  4. Wprowadź poniższe polecenie, aby utworzyć i otworzyć nowy plik ExampleUDF.java:

    notepad src/main/java/com/microsoft/examples/ExampleUDF.java
    

    Następnie skopiuj i wklej poniższy kod Java do nowego pliku. Następnie zamknij plik.

    package com.microsoft.examples;
    
    import org.apache.hadoop.hive.ql.exec.Description;
    import org.apache.hadoop.hive.ql.exec.UDF;
    import org.apache.hadoop.io.*;
    
    // Description of the UDF
    @Description(
        name="ExampleUDF",
        value="returns a lower case version of the input string.",
        extended="select ExampleUDF(deviceplatform) from hivesampletable limit 10;"
    )
    public class ExampleUDF extends UDF {
        // Accept a string input
        public String evaluate(String input) {
            // If the value is null, return a null
            if(input == null)
                return null;
            // Lowercase the input string and return it
            return input.toLowerCase();
        }
    }
    

    Ten kod implementuje funkcję UDF, która akceptuje wartość ciągu i zwraca małą wersję ciągu.

Kompilowanie i instalowanie funkcji UDF

W poniższych poleceniach zastąp wartość sshuser rzeczywistą nazwą użytkownika, jeśli jest inna. Zastąp mycluster wartość rzeczywistą nazwą klastra.

  1. Skompiluj i spakuj funkcję UDF, wprowadzając następujące polecenie:

    mvn compile package
    

    To polecenie kompiluje i pakuje funkcję UDF do exampleudf/target/ExampleUDF-1.0-SNAPSHOT.jar pliku.

  2. scp Użyj polecenia , aby skopiować plik do klastra usługi HDInsight, wprowadzając następujące polecenie:

    scp ./target/ExampleUDF-1.0-SNAPSHOT.jar sshuser@mycluster-ssh.azurehdinsight.net:
    
  3. Połączenie do klastra przy użyciu protokołu SSH, wprowadzając następujące polecenie:

    ssh sshuser@mycluster-ssh.azurehdinsight.net
    
  4. W otwartej sesji SSH skopiuj plik jar do magazynu usługi HDInsight.

    hdfs dfs -put ExampleUDF-1.0-SNAPSHOT.jar /example/jars
    

Korzystanie z funkcji UDF z programu Hive

  1. Uruchom klienta Beeline z sesji SSH, wprowadzając następujące polecenie:

    beeline -u 'jdbc:hive2://localhost:10001/;transportMode=http'
    

    W tym poleceniu założono, że użyto wartości domyślnej administratora dla konta logowania dla klastra.

  2. Po nadejściu monitu jdbc:hive2://localhost:10001/> wprowadź następujące polecenie, aby dodać funkcję UDF do programu Hive i uwidocznić ją jako funkcję.

    ADD JAR wasbs:///example/jars/ExampleUDF-1.0-SNAPSHOT.jar;
    CREATE TEMPORARY FUNCTION tolower as 'com.microsoft.examples.ExampleUDF';
    
  3. Użyj funkcji UDF, aby przekonwertować wartości pobrane z tabeli na ciągi małych liter.

    SELECT tolower(state) AS ExampleUDF, state FROM hivesampletable LIMIT 10;
    

    To zapytanie wybiera stan z tabeli, konwertuje ciąg na małe litery, a następnie wyświetla je wraz z niezmodyfikowaną nazwą. Dane wyjściowe są podobne do następującego tekstu:

    +---------------+---------------+--+
    |  exampleudf   |     state     |
    +---------------+---------------+--+
    | california    | California    |
    | pennsylvania  | Pennsylvania  |
    | pennsylvania  | Pennsylvania  |
    | pennsylvania  | Pennsylvania  |
    | colorado      | Colorado      |
    | colorado      | Colorado      |
    | colorado      | Colorado      |
    | utah          | Utah          |
    | utah          | Utah          |
    | colorado      | Colorado      |
    +---------------+---------------+--+
    

Rozwiązywanie problemów

Podczas uruchamiania zadania hive może wystąpić błąd podobny do następującego tekstu:

Caused by: org.apache.hadoop.hive.ql.metadata.HiveException: [Error 20001]: An error occurred while reading or writing to your custom script. It may have crashed with an error.

Ten problem może być spowodowany przez zakończenie wiersza w pliku języka Python. Wiele edytorów Windows domyślnie używa crLF jako zakończenia wiersza, ale aplikacje systemu Linux zwykle oczekują LF.

Następujące instrukcje programu PowerShell umożliwiają usunięcie znaków CR przed przekazaniem pliku do usługi HDInsight:

# Set $original_file to the Python file path
$text = [IO.File]::ReadAllText($original_file) -replace "`r`n", "`n"
[IO.File]::WriteAllText($original_file, $text)

Następne kroki

Aby zapoznać się z innymi sposobami pracy z programem Hive, zobacz Korzystanie z programu Apache Hive w usłudze HDInsight.

Aby uzyskać więcej informacji na temat usługi Hive User-Defined Functions, zobacz sekcję Apache Hive Operators and User-Defined Functions w witrynie typu wiki Hive pod adresem apache.org.