Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Realm and auto increment Behavior (Android)

I'm trying to get data from Realm using an ID as a reference. However, when querying for an ID, I've found that Realm is giving me the same ID for all elements (ID of 0). Why doesn't the ID auto-increment when I use the @PrimaryKey annotation on the model's ID?

Here's the shortened class for the model:

public class Child_pages extends RealmObject {
    @PrimaryKey
    private int id_cp;

    private int id;
    private String day;
    private int category_id;

And the query I'm executing is: realm.where(Child_pages.class).equalTo("id_cp",page_id).findFirst()

like image 423
Bachlet Tansime Avatar asked May 04 '15 10:05

Bachlet Tansime


3 Answers

Realm currently doesn't support auto incrementing primary keys. However you can easily implement it yourself using something like:

public int getNextKey() { 
    try { 
         Number number = realm.where(object).max("id");
         if (number != null) {
             return number.intValue() + 1;
         } else {
             return 0;
         }
    } catch (ArrayIndexOutOfBoundsException e) { 
         return 0;
    }
}

I hope that can get you started.

like image 84
Bachlet Tansime Avatar answered Oct 15 '22 07:10

Bachlet Tansime


The Java binding does not support primary keys yet, but it's on the roadmap and with high priority - see: https://groups.google.com/forum/#!topic/realm-java/6hFqdyoH67w . As a workaround you can use this piece of code for generating keys:

int key;
try {
  key = realm.where(Child_pages.class).max("id").intValue() + 1;
} catch(ArrayIndexOutOfBoundsException ex) {
 key = 0;
}

I use singleton factory for generating primary keys as a more generic solution with better performance (no need to query for max("id") every time thanks to AtomicInteger).

There is a long discussion in Realm Git Hub if you need more context: Document how to set an auto increment id?

like image 31
zacheusz Avatar answered Oct 15 '22 06:10

zacheusz


As already mentioned, auto-increment isn't supported yet.

But for those who use kotlin and wants to have an auto-increment behavior with realm, this is one of the possibilities:

open class Route(
    @PrimaryKey open var id: Long? = null,
    open var total: Double? = null,
    open var durationText: String? = null,
    open var durationMinutes: Double? = null,
    open var distanceText: String? = null,
    open var distanceMeters: Int? = null): RealmObject() {

companion object {
    @Ignore var cachedNextId:Long? = null
        get() {
            val nextId =    if (field!=null) field?.plus(1)
                            else Realm.getDefaultInstance()?.where(Route::class.java)?.max("id")?.toLong()?.plus(1) ?: 1
            Route.cachedNextId = nextId
            return nextId
        }
}}
like image 4
Vinicius Lima Avatar answered Oct 15 '22 06:10

Vinicius Lima