[ 
https://issues.apache.org/jira/browse/CASSANDRA-11533?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel
 ]

Henry Manasseh updated CASSANDRA-11533:
---------------------------------------
    Description: 
UDFs support returning UDTs. I see the various test cases which validate by 
returning the parameter UDT as the return UDT (which works because it returns 
an already existing UDTValue instance). But there is currently no way to create 
a new instance of an UDTValue and return it.

It seems creating a new UDTValue instance to return from the UDF would require 
getting an instance of the KeyspaceMetadata but that requires access to 
packages which are not white listed. 

A solution could be to add a method to the JavaUDT class to get the UserType 
(encapsulating use of the Schema class).


e.g. change to org.apache.cassandra.cql3.functions.JavaUDF:

protected UserType getUserType(String userTypeName) {

    org.apache.cassandra.schema.KeyspaceMetadata ksm = 
org.apache.cassandra.config.Schema.instance.getKSMetaData("test_ks");

    com.datastax.driver.core.UserType myUdt = 
ksm.types.get("my_other_udt").get();

  return nyUdt;
}

To illustrate, I wrote a simple UDF to transform one UDT into another UDT. This 
fails compilation because Schema is not whitelisted. 

CREATE OR REPLACE FUNCTION test_ks.transform_udt (val my_udt)
 RETURNS NULL ON NULL INPUT
 RETURNS my_other_udt
 LANGUAGE java
  AS '
    String fieldA = val.getString("field_a");

    org.apache.cassandra.schema.KeyspaceMetadata ksm = 
org.apache.cassandra.config.Schema.instance.getKSMetaData("test_ks");

    com.datastax.driver.core.UserType myUdt = 
ksm.types.get("my_other_udt").get();

    com.datastax.driver.core.UDTValue transformedValue = myUdt.newValue();

    transformedValue.setUUID("id", java.util.UUID.randomUUID());
    transformedValue.setString("field_a", fieldA);
    transformedValue.setString("field_b", "value b");

    return transformedValue;
  ';

This is the error:
<stdin>:88:InvalidRequest: code=2200 [Invalid query] message="Could not compile 
function 'test_ks.transform_udt' from Java source: 
org.apache.cassandra.exceptions.InvalidRequestException: Java source 
compilation failed:
Line 4: org.apache.cassandra.schema.KeyspaceMetadata cannot be resolved to a 
type
Line 4: org.apache.cassandra.config.Schema.instance cannot be resolved to a type
"




  was:
UDFs support returning UDTs. I see the various test cases which validate by 
returning the parameter UDT as the return UDT (which works because it returns 
an already existing UDTValue instance). But there is currently no way to create 
a new instance of an UDTValue and return it.

It seems that to accomplish that it would require getting an instance of the 
KeyspaceMetadata but that requires use of packages which are not white listed. 

A solution could be to add a method to getUserType(String) which calls schema 
in the super class org.apache.cassandra.cql3.functions.JavaUDF.

e.g.
protected UserType getUserType(String userTypeName) {

    org.apache.cassandra.schema.KeyspaceMetadata ksm = 
org.apache.cassandra.config.Schema.instance.getKSMetaData("test_ks");

    com.datastax.driver.core.UserType myUdt = 
ksm.types.get("my_other_udt").get();

  return nyUdt;
}

To illustrate, I wrote a simple UDF to transform one UDT into another UDT. This 
fails compilation because Schema is not whitelisted. 

CREATE OR REPLACE FUNCTION test_ks.transform_udt (val my_udt)
 RETURNS NULL ON NULL INPUT
 RETURNS my_other_udt
 LANGUAGE java
  AS '
    String fieldA = val.getString("field_a");

    org.apache.cassandra.schema.KeyspaceMetadata ksm = 
org.apache.cassandra.config.Schema.instance.getKSMetaData("test_ks");

    com.datastax.driver.core.UserType myUdt = 
ksm.types.get("my_other_udt").get();

    com.datastax.driver.core.UDTValue transformedValue = myUdt.newValue();

    transformedValue.setUUID("id", java.util.UUID.randomUUID());
    transformedValue.setString("field_a", fieldA);
    transformedValue.setString("field_b", "value b");

    return transformedValue;
  ';

This is the error:
<stdin>:88:InvalidRequest: code=2200 [Invalid query] message="Could not compile 
function 'test_ks.transform_udt' from Java source: 
org.apache.cassandra.exceptions.InvalidRequestException: Java source 
compilation failed:
Line 4: org.apache.cassandra.schema.KeyspaceMetadata cannot be resolved to a 
type
Line 4: org.apache.cassandra.config.Schema.instance cannot be resolved to a type
"





> Support creating and returning UDTs from a UDF
> ----------------------------------------------
>
>                 Key: CASSANDRA-11533
>                 URL: https://issues.apache.org/jira/browse/CASSANDRA-11533
>             Project: Cassandra
>          Issue Type: Improvement
>          Components: Core
>            Reporter: Henry Manasseh
>            Priority: Minor
>
> UDFs support returning UDTs. I see the various test cases which validate by 
> returning the parameter UDT as the return UDT (which works because it returns 
> an already existing UDTValue instance). But there is currently no way to 
> create a new instance of an UDTValue and return it.
> It seems creating a new UDTValue instance to return from the UDF would 
> require getting an instance of the KeyspaceMetadata but that requires access 
> to packages which are not white listed. 
> A solution could be to add a method to the JavaUDT class to get the UserType 
> (encapsulating use of the Schema class).
> e.g. change to org.apache.cassandra.cql3.functions.JavaUDF:
> protected UserType getUserType(String userTypeName) {
>     org.apache.cassandra.schema.KeyspaceMetadata ksm = 
> org.apache.cassandra.config.Schema.instance.getKSMetaData("test_ks");
>     com.datastax.driver.core.UserType myUdt = 
> ksm.types.get("my_other_udt").get();
>   return nyUdt;
> }
> To illustrate, I wrote a simple UDF to transform one UDT into another UDT. 
> This fails compilation because Schema is not whitelisted. 
> CREATE OR REPLACE FUNCTION test_ks.transform_udt (val my_udt)
>  RETURNS NULL ON NULL INPUT
>  RETURNS my_other_udt
>  LANGUAGE java
>   AS '
>     String fieldA = val.getString("field_a");
>     org.apache.cassandra.schema.KeyspaceMetadata ksm = 
> org.apache.cassandra.config.Schema.instance.getKSMetaData("test_ks");
>     com.datastax.driver.core.UserType myUdt = 
> ksm.types.get("my_other_udt").get();
>     com.datastax.driver.core.UDTValue transformedValue = myUdt.newValue();
>     transformedValue.setUUID("id", java.util.UUID.randomUUID());
>     transformedValue.setString("field_a", fieldA);
>     transformedValue.setString("field_b", "value b");
>     return transformedValue;
>   ';
> This is the error:
> <stdin>:88:InvalidRequest: code=2200 [Invalid query] message="Could not 
> compile function 'test_ks.transform_udt' from Java source: 
> org.apache.cassandra.exceptions.InvalidRequestException: Java source 
> compilation failed:
> Line 4: org.apache.cassandra.schema.KeyspaceMetadata cannot be resolved to a 
> type
> Line 4: org.apache.cassandra.config.Schema.instance cannot be resolved to a 
> type
> "



--
This message was sent by Atlassian JIRA
(v6.3.4#6332)

Reply via email to