Skip to content

Composite and Compound key in Cassandra

chhavigangwal edited this page Nov 6, 2013 · 2 revisions

Cassandra provides support of composite key via CQL3.0. To use Kundera with composite key support over Cassandra, we need to make sure order of fields defined in embeddable entity(e.g. CompoundKey) should be same as while creating column family script. For example:

@Entity
@Table(name = "UserInfo", schema = "CompositeCassandra@composite_pu")
public class UserInfo
{

    @Id
    @Column(name = "userInfo_id")
    private String userInfoId;

    @Column(name = "first_name")
    private String firstName;

    @Column(name = "last_name")
    private String lastName;

    @Column(name = "age")
    private int age;

Cassandra Equivalent :

CREATE TABLE "UserInfo" (
  key text PRIMARY KEY,
  age int,
  first_name text,
  last_name text
) ;

CREATE INDEX UserInfo_age_idx ON "UserInfo" (age);

CREATE INDEX UserInfo_first_name_idx ON "UserInfo" (first_name);

CREATE INDEX UserInfo_last_name_idx ON "UserInfo" (last_name);

Here order is user_id, first_name. user_id can be termed as partition key and first_name is "cluster/remaining key".

So to ensure ordering, while defining embeddable entity within Kundera, it must be in same order. For example:

@Embeddable
public class CassandraCompoundKey
{
    @Column
    private String userId;

    @Column
    private int tweetId;

    @Column
    private UUID timeLineId;

    @Column
    private transient String fullName;

Cassandra Equivalent:

CREATE TABLE "CompositeUserAssociation" (
  "userId" text,
  "tweetId" int,
  "timeLineId" uuid,
  age int,
  first_name text,
  last_name text,
  "tweetBody" text,
  "tweetDate" timestamp,
  "userInfo_id" text,
  PRIMARY KEY ("userId", "tweetId", "timeLineId")
) ;

Here key has to be an Embeddable entity:

@Entity
@Table(name = "CompositeUserAssociation", schema = "CompositeCassandra@composite_pu")
public class CassandraEmbeddedAssociation
{

    @EmbeddedId
    private CassandraCompoundKey key;

    @Column
    private String tweetBody;

    @Column
    private Date tweetDate;

    @OneToOne(cascade = CascadeType.ALL, fetch = FetchType.LAZY)
    @JoinColumn(name = "userInfo_id")
    private UserInfo userInfo;

Cassandra Equivalent :

CREATE TABLE "CompositeUserAssociation" (
  "userId" text,
  "tweetId" int,
  "timeLineId" uuid,
  age int,
  first_name text,
  last_name text,
  "tweetBody" text,
  "tweetDate" timestamp,
  "userInfo_id" text,
  PRIMARY KEY ("userId", "tweetId", "timeLineId")
) ;

Persist using Kundera :

// Persist
UUID timeLineId = UUID.randomUUID();
Date currentDate = new Date();
CassandraCompoundKey key = new CassandraCompoundKey("mevivs", 1, timeLineId);
CassandraEmbeddedAssociation timeLine = new CassandraEmbeddedAssociation(key);
timeLine.setTweetBody("my first tweet");
timeLine.setTweetDate(currentDate);

UserInfo userInfo = new UserInfo("mevivs_info", "Vivek", "Mishra", 31);
timeLine.setUserInfo(userInfo);
em.persist(timeLine);
Clone this wiki locally