Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Hazelcast query in custom objects

I'm using Hazelcast as a shared map in my application. My map is like that:

Map<String, MyObject>

and MyObject:

class MyObject implements Serializeble {
    // Map FieldName -> FieldValue
    Map<String, Object> myMap;
}

So I'd like to use Hazelcast distributed query support to query in my object. I've checked that Hazelcast uses get's method to retrieve the object value, but in my case I don't have a get, instead of I'd like to implement my own getField like:

Object getField(String fieldName) {
    return myMap[fieldName];
}

And force Hazelcast to call this method. As a workaround, I've hacked Hazelcast code to use a CustomGetter in the class

/hazelcast/src/main/java/com/hazelcast/query/impl/ReflectionHelper.java

line 144:

if (localGetter == null) {
    localGetter = new CustomFieldGetter(name, obj);
}

and here My CustomFieldGetter class:

static class CustomFieldGetter extends Getter {
    final Object value;
    final Class type;
    final String fieldName;

    CustomFieldGetter(String fieldName, Object obj) throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
        super(null);
        this.fieldName = fieldName;
        this.value = obj.getClass().getMethod("getField", String.class).invoke(obj, fieldName);
        this.type = value.getClass();
    }

    @Override
    Object getValue(Object obj) throws Exception {
        return value;
    }

    @Override
    Class getReturnType() {
        return type;
    }

    @Override
    boolean isCacheable() {
        return false;
    }

    @Override
    public String toString() {
        return "FieldGetter [parent=" + parent + ", field=" + fieldName + "]";
    }
}

Ok cool, after recompilation of Hazelcast, and using this new jar, I could reach queries using plain sql. But for pagingQueries I got some errors.

So my finally question is: I'd like to avoid hack Hazelcast code (for further updates). Does Hazelcast has some supports on this issue? Is there any other solution for this problem?

PS: I'm using Hazelcast version -> hazelcast-3.3-RC3

Thanks in advance.

like image 597
Sergio Santiago Avatar asked Aug 29 '14 14:08

Sergio Santiago


Video Answer


1 Answers

one option is to implement Portable interface. Then you could write each entry as a separate field. This assumes the entry value implements the Portable interface as well.

Look at the sample code how to use Portable.

like image 182
Jaromir Hamala Avatar answered Oct 16 '22 20:10

Jaromir Hamala