Моши и комната - картографирование отношений - PullRequest
0 голосов
/ 04 апреля 2020

У меня есть Json, который я хотел бы сопоставить с Moshi и сохранить с Room

{
    "name": "My Group",
    "members": [
        {
            "id": "119075",
            "invitedUser": {
                "id": 97375,
                "email": "xxx@gmail.com"
            },
            "inviting_user": {
                "id": 323915,
                "email": "yyy@gmail.com"
            }
        },
        {
            "id": "395387",
            "invitedUser": {
                "id": 323915,
                "email": "aaa@gmail.com"
            },
            "inviting_user": {
                "id": 323915,
                "email": "bbb",
            }
        }
    ]
}

Я подготовил свои модели

@Entity(tableName = "groups")
data class Group(
    @PrimaryKey
    val id: Long,
    val members: List<Member>
)

@Entity(tableName = "members")
data class Member(
    @PrimaryKey
    val id: Long,

    @Json(name = "invited_user")
    @ColumnInfo(name = "invited_user")
    val invitedUser: User,

    @Json(name = "inviting_user")
    @ColumnInfo(name = "inviting_user")
    val invitingUser: User
)

@Entity(tableName = "users")
data class User(
    @PrimaryKey
    val id: Int,

    val email: String
)

И в настоящее время, У меня error: Cannot figure out how to save this field into database. Я прочитал это https://developer.android.com/training/data-storage/room/relationships. Однако, если я буду моделировать отношения, как в документации, я не знаю, как позволить Моши отобразить отношения? Вы нашли самое простое решение для этой проблемы?

Ответы [ 3 ]

1 голос
/ 04 апреля 2020

На мой взгляд, у вас есть 2 варианта.

  1. Вы разделяете группу и пользователей на отдельные таблицы и вставляете их отдельно.
  2. Вы используете TypeConverters для хранения участников. как поле группы.

Ваша реализация будет зависеть от вашего варианта использования.

0 голосов
/ 05 апреля 2020

Наконец, я сохранил его, используя TypeConverters

private val membersType = Types.newParameterizedType(List::class.java, Member::class.java)
private val membersAdapter = moshi.adapter<List<Member>>(membersType)

@TypeConverter
fun stringToMembers(string: String): List<Member> {
    return membersAdapter.fromJson(string).orEmpty()
}

@TypeConverter
fun membersToString(members: List<Member>): String {
    return membersAdapter.toJson(members)
}

И это мои модели

@TypeConverters(Converters::class)
@Entity(tableName = "groups")
data class Group(
    @PrimaryKey
    val id: Long,
    val name: String
) {
    companion object {

        data class Member(
            val id: Long,
            val invitedUser: User,
            val invitingUser: User
        )

        data class User(
            val id: Long,
            val email: String
        )
    }
}

Это выглядит хорошо для вас? Возможно, чище было бы иметь только идентификаторы и хранить где-то еще пользователей, но мне нравится, что это решение настолько простое.

0 голосов
/ 04 апреля 2020
Вы используете TypeConverters для хранения членов в качестве поля группы.

Я считаю, что это нужная вам реализация.

open class UserRequestConverter {

    private val moshi = Moshi.Builder().build()

    @TypeConverter
    fun fromJson(string: String): User? {
        if (TextUtils.isEmpty(string))
            return null

        val jsonAdapter = moshi.adapter(User::class.java)
        return jsonAdapter.fromJson(string)
    }

    @TypeConverter
    fun toJson(user: User): String {
        val jsonAdapter = moshi.adapter(User::class.java)
        return jsonAdapter.toJson(user)
    }
}



@Entity(tableName = "members")
data class Member(
    @PrimaryKey
    val id: Long,

    @Json(name = "invited_user")
    @ColumnInfo(name = "invited_user")
    @TypeConverters(UserRequestConverter::class)
    val invitedUser: User,

    @Json(name = "inviting_user")
    @ColumnInfo(name = "inviting_user")
    @TypeConverters(UserRequestConverter::class)
    val invitingUser: User
)
...