How to link Room database entities on android? - android

I am quite familiar with these kind of thing on Spring JPA but I can not make it work on Android. I post my code below so you can understand the question better. I have two classes and a third class that needs to contain objects of class 1 and 2. I know that the code for the third class is not correct, since Room does not support object references like that. If I save just the id-s of the objects as foreign keys I am not able to query after the results.
There must be some kind of nice solution for this problem. Thank you.
#Entity(tableName = "soup")
public class Soup {
#PrimaryKey(autoGenerate = true)
private long id;
private String name;
// getter and setters
}
#Entity(tableName = "main_course")
public class MainCourse {
#PrimaryKey(autoGenerate = true)
private long id;
private String name;
// getter and setters
}
#Entity(tableName = "menu")
public class Menu {
#PrimaryKey(autoGenerate = true)
private long id;
private Soup soupOptionOne;
private Soup soupOptionTwo;
private Soup soupOptionThree;
private MainCourse courseOptionOne;
private MainCourse courseOptionTwo;
private MainCourse courseOptionThree;
}

Related

How to Join in ObjectBox

How can I join two classes in ObjectBox which have one two many relationship?
I have two tables as following:
#Entity
public class Animal {
#Id(assignable = true)
public long id;
private String name;
private boolean flying;
private boolean swimming;
private boolean walking;
private ToOne<Zoo> zoo;
.../*setters and getters*/
}
and:
#Entity
public class Zoo {
#Id
public long id;
private String name;
// a Zoo can have many Animals
#Backlink
ToMany<Animal> animals;
.../*setters and getters*/
}
How can I implement Join operation?
Since version 2.0.0 you can do something like:
val builder = box.query().equal(Zoo_.name, "The Big Zoo")
builder.link(Zoo_.animals).equal(Animal_.flying, true)
val flyingAnimals = builder.build().find()
This is called "links" and there is documentation on it with an additional example.

One-to-many relation in Room

I've been using SugarDB for most of my projects in the past. It was easy to use and satisfied most of my requirements but since that project has been abandoned, decided to look at alternatives and Room seems like the best option.
However, some basic things are quite confusing in Room. My Object uses Gson to populate data from a webservice, and as such as links to other objects. As an example, consider the classes below:
#Entity
public class TestModel
{
#PrimaryKey(autoGenerate = true)
private int id;
private String name;
private String age;
private List<Book> issuedBooks;
}
public class Book
{
private String title;
private int ISBN;
}
Now if my first class is annotated as the Entity, will this automatically treat classes referenced inside it as entities as well?
If I save an object of TestModel, will it save the list of Books with it to the database?
I guess you can do it this way.
#Entity
public class TestModel {
#PrimaryKey
public int id; // TestModel id
public String name;
public String age;
}
#Entity
public class Book {
#PrimaryKey
public int id; // Book id
public int testModelId; // TestModel id
public String title;
public int ISBN;
}
public class TestModelWithBooks {
#Embedded
public TestModel testModel;
#Relation(parentColumn = "id", entityColumn = "testModelId", entity = Book.class)
public List<Book> books;
}
For their Dao, you can write it this way.
#Dao
public interface TestModelDao {
#Query("SELECT * FROM TestModel")
public List<TestModelWithBooks> loadTestModelsWithBooks();
}
will this automatically treat classes referenced inside it as entities as well?
No. In fact, I would expect your code to fail to compile. You would need to:
Make Book be an #Entity
Remove issuedBooks from TestModel
Set up a #ForeignKey relationship between Book and TestModel
If I save an object of TestModel, will it save the list of Books with it to the database?
No.
Room is not an ORM. Room is a thin object wrapper around SQLite. #Entity and #ForeignKey model the table structure. IMHO, the simplest way to think of Room as it being DTOs to the database. Your model objects that represent your object graph are not the entities, but instead are built from the entities. This is akin to how responses from a Web service (e.g., Retrofit) are DTOs to the server, and you may need to map from those objects to the "real" model objects that you want to use in the app.

Class with collection of itself ORMLite

How can i create one-to-many relation with the table itself in ormlite? I have a class that holds collection of itself. I don't know how to map this class.
#DatabaseTable(tableName = "USER")
public class User {
#DatabaseField(generatedId = true)
private long id;
#DatabaseField
private String username;
#ForeignCollectionField
private ForeignCollection<User> friends;
...
Thanks in advance.
I have a class that holds collection of itself. I don't know how to map this class.
I think the best way would be to define a UserFriend entity that has a reference to the owner User, friend User, and an id. Something like:
#DatabaseTable(tableName = "USERFRIEND")
public class UserFriend {
#DatabaseField(generatedId = true)
private long id;
// corresponds to the user who has the friend
#DatabaseField(foreign = true)
private User user;
// corresponds to the friend of the user
#DatabaseField(foreign = true)
private User friend;
...
Then your foreign collection becomes:
#ForeignCollectionField(foreignFieldName = 'user')
private ForeignCollection<UserFriend> friends;
Notice the foreignFieldName which has to point to the user so the user's friends can be found.

How to use bi-directional Many To Many relationship with GreenDAO?

After Reading the doc's Relations pages, I can use a many to many relation like this:
#Entity
public class Product {
#Id private Long id;
#ToMany
#JoinEntity(
entity = JoinProductsWithOrders.class,
sourceProperty = "productId",
targetProperty = "orderId"
)
private List<Order> ordersWithThisProduct;
}
#Entity
public class JoinProductsWithOrders {
#Id private Long id;
private Long productId;
private Long orderId;
}
#Entity
public class Order {
#Id private Long id;
}
Now, with this code, can I have a bi-directionel relations and access from an Order the list of Products associated with it?
Or should I add a Product List in the Order class too? Something like this:
...
#Entity
public class Order {
#Id private Long id;
#ToMany //I don't know if this is corect btw.
private List<Product> productsForThisOrder;
}
This is how you should do it:
#Entity
public class Order {
#Id private Long id;
#ToMany
#JoinEntity(
entity = JoinProductsWithOrders.class,
sourceProperty = "orderId",
targetProperty = "productId"
)
private List<Product> productsForThisOrder;
}

ActiveAndroid Nested Model

I am using ActiveAndroid and have two models:
#Table(name = "Topics")
public class Topic extends Model {
#Column(name = "Name") String name;
#SerializedName("id")
#Column(index = true,
unique = true,
onUniqueConflict = Column.ConflictAction.REPLACE) public long topic_id;
#Column(name = "Counts",
onUpdate = Column.ForeignKeyAction.CASCADE,
onDelete = Column.ForeignKeyAction.CASCADE) Counts counts;
}
and
#Table(name = "Counts")
public class Counts extends Model {
#Column(name = "Users") int users;
}
Constructors have been excluded for brevity.
Now, when i save Topic, I expect the Counts to be saved. But it does not.
I am using gson to create the models from json. Any reason why counts are not being loaded?
First you have to call count.save() then you can call topic.save(). ActiveAndroid needs the id to get the reference and that happen when you save it.

Categories

Resources