Search code examples
cassandraastyanax

Querying columns with prefix not working using Astyanax


I have a scheme as follows:

  • TimeStamp
  • Device ID
  • Device Name
  • Device Owner
  • Device location

I have created this column family using CQL and defined the primary key as (TimeStamp,Device ID, Device Name). Through a serializable object that has fields for DeviceID, name and a field name (which stores either Device Owner or Device Location). I have inserted some records using Astyanax.

As per my understanding, the columns for a row are created by combining Device ID, Device Name and field name as column name and the value to be the value for that particular field. Thus for a particular timestamp and device, the column names would be in the pattern (Device ID:Device Name: ...).

So I believe we can use these 2 fields as prefix to obtain all the entries for a particular time-device combination.

I am using the following query to obtain the results:

  RowSliceQuery<String, ApBaseData> query = adu.keyspace
  .prepareQuery(columnFamily)
  .getKeySlice(timeStamp)
  .withColumnRange(new RangeBuilder()
   .setStart(deviceID+deviceName+"_\u00000")
   .setEnd(deviceID+deviceName+"_\uffff")
   .setLimit(batch_size)
   .build());

But on executing the above query I get the following Exception:

BadRequestException: [host=localhost(127.0.0.1):9160, latency=6(6), attempts=1]InvalidRequestException(why:Not enough bytes to read value of component 0)

@abhi The data I can have in this column family is as follows:

    stime    |  devName  | devId | Owner | Location
  1361260800 | dev:01:02 |   1   | 1234  |    1  
  1361260800 | dev:02:03 |   2   | 34    |    2
  1361260800 | dev:05:06 |   1   | 12    |    1
  1361260800 | dev:03:02 |   2   | 56    |    3

The java seriazable java class that I am using for this is:

public class BaseData implements Serializable {
    private static final long serialVersionUID = 1L;
    @Component(ordinal = 0)
    private String devName;
    @Component(ordinal = 1)
    private int devID;
    @Component(ordinal = 2)
    private String field;
}

Following the structure of the above class I can see columns in the column family as : Columne Name: dev\:01\:02:1:location Column Value: 00000001

FYI using astyanax 1.56.31


Solution

  • To overcome this problem, I changed the way I was storing data in the table. Instead of using a composite primary key, I changed the schema so as to have only single primary key and dynamic columns. So, now I have primary key on stime and my column names are constructed dynamically explicitly by my insertion code. For eg. "dev\:01\:02:1:location" the same way they were before but this has completely eliminated the need of a serialized object. This has solved my problem as of now. Lets see what problems it poses later.