如何使用自定义Java类在Cassandra中创建用户定义的函数?

问题描述 投票:5回答:3

我无法在网上找到这个。如何在cassandra中创建自定义用户定义函数?

对于Ex:

CREATE OR REPLACE FUNCTION customfunc(custommap map<text, int>)
CALLED ON NULL INPUT
RETURNS map<int,bigint> 
LANGUAGE java AS 'return MyClass.mymethod(custommap);';

“MyClass”是哪个类我可以在Classpath中注册?

cassandra cassandra-2.0 cassandra-2.1
3个回答
1
投票

在我尝试构建外部类方法来支持类似的东西时,只需将2美分添加到此线程中。在使用Datastax Sandbox 5.1尝试了几个小时后,我无法使用它,因为它似乎无法找到我的类并且不断引发类型错误。

我的猜测是不支持UDF的外部基于JAR的代码(参见http://koff.io/posts/hll-in-cassandra/https://issues.apache.org/jira/browse/CASSANDRA-9892)。支持“TRUSTED”JAR正处于Cassandra 4的规划阶段。它可能适用于3.0之前的早期版本,但我使用的是Datastax的最新版本。

要解决这个问题,我不得不回避使用Javascript版本(我试图将JSON字符串转换为Map对象)。

虽然我意识到Java UDF表现更好,但我测试的代码仍然使用Java Nashorn javascript支持,所以使用Javascript可能不是一件坏事。它最终会得到一个更简单的单行UDF。


0
投票

1.首先构建包含类的java项目。请记住,您必须向您的班级添加包名称。

示例:

package exp;

import java.lang.Math;
import java.util.*;

public class MyClass
{
  public static Map<Integer,Long> mymethod(Map<String, Integer> data) {
      Map<Integer,Long> map = new HashMap<>();
      map.put(1, 10L);
      map.put(2, 20L);
      map.put(3, 30L);
      return map;
  }
}

编译和构建后我有jar test.jar

2.将jar文件复制到所有cassandra节点的$CASSANDRA_HOME/lib目录

3.重新启动所有Cassandra节点

4.创建自定义功能

示例:

 CREATE OR REPLACE FUNCTION customfunc(custommap map<text, int>) 
    CALLED ON NULL INPUT 
    RETURNS map<int,bigint>  
    LANGUAGE java 
    AS 'return exp.MyClass.mymethod(custommap);';

现在你可以使用这个功能:

cassandra@cqlsh:test> SELECT * FROM test_fun ;

 id | data
----+------------------
  1 | {'a': 1, 'b': 2}

(1 rows)
cassandra@cqlsh:test> SELECT customfunc(data) FROM test_fun ;

 test.customfunc(data)
-----------------------
 {1: 10, 2: 20, 3: 30}

(1 rows)

0
投票

我也有同样的问题。 UDF中的自定义类是cassandra 2.2.14中的支持,但不适用于cassandra 3.11.4。

浏览源代码,cassandra 3.11.4设置没有父类加载器的UDF类加载器,以便它可以完全控制UDF使用的类/资源。在org.apache.cassandra.cql3.functions.UDFunction.java中,白名单和黑名单用于控制哪些类/包可以访问。

对于您的问题,您应该将MyClass的全名添加到白名单中,然后重新构建cassandra。

© www.soinside.com 2019 - 2024. All rights reserved.