Skip to content
elandau edited this page Aug 4, 2011 · 22 revisions

What is it?
Astyanax is a Java Cassandra client library. Astyanax was the son of Hector in Greek mythology. As such, Astyanax is a refactoring of Hector into a cleaner abstraction for the connection manager and a simpler API.

Getting started

Initializing Astyanax

All configuration operations are encapsulated into a single ConnectionPoolConfiguration interface. As with many Astyanax components you can implement your own configuration logic (for example, one that binds with properties or beans). A simple configuration is provided in ConnectionPoolConfigurationImpl. Many defaults are provided out of the box but you must specify at least on seed in the format of command delimited host:port pairs.


ConnectionPoolConfigurationImpl config 	= new ConnectionPoolConfigurationImpl("ClusterName", "KeyspaceName");

config.setSeeds("127.0.0.1:9160");
config.setPort(9160);
config.setSocketTimeout(30000);
config.setMaxTimeoutWhenExhausted(30);
config.setClock(new MillisecondsClock());
    	
Keyspace keyspace = new ThriftKeyspaceImpl(config);
keyspace.start();

Define your column family structure

Cassandra internally stores all keys, columns and values as byte arrays. Just like Hector, Astyanax makes use of various serializers to convert to and from various basic and more complex data types. To avoid having to specify serializers for every call you must first set up the column family definition. This definition will most likely be a static final in your DAO or other higher level wrapper. Notice that the definition is at the column family and not the keyspace level. This allows you to have different key types for column families within the same key space.


ColumnFamily<String, String> CF_USER_INFO =
  new ColumnFamily<String, String>(
    "Standard1",              // Column Family Name
    StringSerializer.get(),   // Key Serializer
    StringSerializer.get());  // Column Serializer

Inserting data

Data may be inserted either one column at a time or in batches.


// Inserting data
MutationBatch m = keyspace.prepareMutationBatch();

m.withRow(CF_USER_INFO, "acct1234")
  .putColumn("firstname", "john", null)
  .putColumn("lastname", "smith", null)
  .putColumn("address", "555 Elm St", null)
  .putColumn("age", 30, null);

m.withRow(CF_USER_STATS, “acct1234”)
  .incrementCounterColumn("loginCount", 1);

try {
  OperationResult<Void> result = m.execute();
} catch (ConnectionException e) {
}

Reading data from cassandra

There are several ways to read data from cassandra. A single Query interface is provided which lets you first specify the row level query followed by an optional column slice.

Reading a single row


OperationResult<ColumnList<String>> result =
  ks.prepareQuery(CF_USER_INFO, keyName)
    .getKey(“Key1”).
    .execute();
ColumnList<String> columns = result.getResult();

// Lookup columns in response by name 
int age        = columns.getColumnByName("age").getIntegerValue();
long counter   = columns.getColumnByName("loginCount").getLongValue();
String address = columns.getColumnByName("address").getStringValue();

// Or, iterate through the columns
for (Column<String> c : result.getResult()) {
  System.out.println(c.getName());
}

Reading a set of non-contiguous rows


OperationResult<Rows<String, String>> result =
  ks.prepareQuery(CF_STANDARD1)
    .getKeySlice(“Key1”, “Key2”, “Key3”)
       .execute();

// Iterate rows and their columns 
for (Row<String, String> row : result.getResult()) {
  System.out.println(row.getKey());
  for (Column<String> column : row.getColumns()) {
  System.out.println(column.getName());
  }
}

Composite columns


// Annotated composite class
Class SessionEvent{
  @Component String   sessiondId;
  @Component TimeUUID timestamp;
}

static AnnotatedCompositeSerializer<SessionEvent> eventSerializer
      = new AnnotatedCompositeSerializer<SessionEvent>(SessionEvent.class);
static ColumnFamily<String, SessionEvent> CF_SESSION_EVENTS
  = new ColumnFamily<String, SessionEvent>(”SessionEvents", 
    StringSerializer.get(), eventSerializer);

// Querying cassandra for an entire row
keyspace.prepareQuery(CF_SESSION_EVENTS)
  .getKey(”SomeSessionId")
  .withColumnRange(
      eventSerializer.makeEndpoint(“sessionid1", Equality.EQUAL).toBytes(),
      eventSerializer.makeEndpoint("sessionid1", Equality.LESS_THAN_EQUAL).toBytes(),
      false, 100)
  .execute();
Clone this wiki locally