gpt4 book ai didi

java - 如何在 Room 2.3.0 中向我的实体添加外键?

转载 作者:行者123 更新时间:2023-12-04 07:32:31 26 4
gpt4 key购买 nike

我有一个使用 Room 2.2.5 的项目,我刚刚更新到 2.3.0 版本,这是一个名为 photo 的实体的代码:

    @Entity(tableName = Photo.TABLE_NAME, foreignKeys = @ForeignKey(entity = Event.class,
parentColumns = "_id",
childColumns = "id_event_ft",
onDelete = ForeignKey.CASCADE))
public class Photo {

public static final String TABLE_NAME = "Photo";
public static final String COLUMN_ID = BaseColumns._ID;

@PrimaryKey(autoGenerate = true)
@ColumnInfo(index = true, name = COLUMN_ID)
public Long id_photo;

@ColumnInfo(name = "path")
private String path;

@ForeignKey(entity = Event.class,
parentColumns = "_id",
childColumns = "id_event_ft",
onDelete = ForeignKey.CASCADE)
private Long id_event_ft;

public Photo(Long id_photo, String path, Long id_event_ft) {
this.id_photo = id_photo;
this.path = path;
this.id_event_ft = id_event_ft;
}

public Long getId_photo() {
return id_photo;
}

public void setId_photo(Long id_photo) {
this.id_photo = id_photo;
}

public String getPath() {
return path;
}

public void setPath(String path) {
this.path = path;
}

public Long getId_event_ft() {
return id_event_ft;
}

public void setId_event_ft(Long id_event_ft) {
this.id_event_ft = id_event_ft;
}
}
现在我在尝试编译时收到以下错误

error: annotation type not applicable to this kind of declaration@ForeignKey(entity = Event.class, parentColumns = "_id", childColumns = "id_event_ft", onDelete = ForeignKey.CASCADE)^


错误出现在变量 private Long id_event_ft; 上方的 @ForeignKey 中。
documentation我找到了这个:

Added missing target to @ForeignKey annotation preventing its usage outside of the @Entity annotation. (Iced1e)


很明显,不再允许在 @Entity 注释之外使用 @ForeignKey,但是我该如何绑定(bind) id_event_ft外键的变量?,我现在如何为其赋值?
我希望有人可以帮助我,非常感谢

最佳答案

使用 外键 不会自动(神奇地)建立关系。相反,它允许主要通过强制引用完整性来支持关系。

  • 外键(关系)的存在不需要外键定义。

  • 也就是说,它定义了一个规则,即子列的值 ( id_event_ft ) 必须是父列中存在的值 ( _id )。如果存在外键冲突,它还支持处理(例如,您使用的 onDelete)。
    实际上,提供合适的值是您必须以编程方式执行的操作,即 id 添加照片,您必须确定照片要链接/相关的事件。
    您可以使用@Relation 来简化提取相关数据的过程。
    所以考虑以下几点:
    一个 Activity 实体(很好,很简单的演示)
    @Entity
    public class Event {
    @PrimaryKey(autoGenerate = true)
    Long _id = null;
    String other_columns;

    public Event(){}
    @Ignore
    public Event(String other_columns) {
    this.other_columns = other_columns;
    }
    }
  • 照片的父列将是 _id 柱子。
  • Second Ignored (i.e. Ignored by Room) 构造函数,否则 Room 会发出警告,如 *warning: There are multiple good constructors and Room 将选择无参数构造函数。 *

  • 略有改动 照片 实体 :-
    @Entity(tableName = Photo.TABLE_NAME,
    foreignKeys = @ForeignKey(
    entity = Event.class,
    parentColumns = "_id",
    childColumns = "id_event_ft",
    onDelete = ForeignKey.CASCADE),
    indices = @Index("id_event_ft") //<<<<<<<<<< ADDED as Room warns if omitted
    )
    public class Photo {

    public static final String TABLE_NAME = "Photo";
    public static final String COLUMN_ID = BaseColumns._ID;

    @PrimaryKey(autoGenerate = true)
    @ColumnInfo(index = true, name = COLUMN_ID)
    public Long id_photo;
    @ColumnInfo(name = "path")
    private String path;
    /* <<<<<<<< COMMENTED OUT >>>>>>>>>>
    @ForeignKey(entity = Event.class,
    parentColumns = "_id",
    childColumns = "id_event_ft",
    onDelete = ForeignKey.CASCADE)

    */
    private Long id_event_ft;

    public Photo(Long id_photo, String path, Long id_event_ft) {
    this.id_photo = id_photo;
    this.path = path;
    this.id_event_ft = id_event_ft;
    }

    public Long getId_photo() {
    return id_photo;
    }

    public void setId_photo(Long id_photo) {
    this.id_photo = id_photo;
    }

    public String getPath() {
    return path;
    }

    public void setPath(String path) {
    this.path = path;
    }

    public Long getId_event_ft() {
    return id_event_ft;
    }

    public void setId_event_ft(Long id_event_ft) {
    this.id_event_ft = id_event_ft;
    }
    }
    为了演示通过关系检索 POJO EventWithPhotos :-
    public class EventWithPhotos {

    @Embedded
    Event event;
    @Relation(entity = Photo.class,parentColumn = "_id",entityColumn = "id_event_ft")
    List<Photo> photos;
    }
    现道 全道 :-
    @Dao
    interface AllDao {

    @Insert
    long insert(Event event);
    @Insert
    long insert(Photo photo);
    @Transaction
    @Query("SELECT * FROM event")
    List<EventWithPhotos> getAllEventsWithPhotos();
    }

    How do I assign a value to it now?


    现在是一个将所有事件放在一起的示例,第一个事件有 2 张照片,第二个事件有 1 张照片。请注意使用的不同技术:-
        dao = db.getAllDao();

    // Prepare to add an Event
    Event newEvent = new Event();
    newEvent.other_columns = "Event1";
    // Add the Event retrieving the id (_id column)
    long eventId = dao.insert(newEvent);
    // Prepare a photo to be added to Event1
    Photo newPhoto = new Photo(null,"photo1",eventId);
    // Add the Photo to Event1
    long photoid = dao.insert(newPhoto);
    // Add second photo to Event 1 using the 2nd constructor
    dao.insert(new Photo(null,"photo2",eventId));
    // Add Event2 with a photo all in a single line (again using the 2nd constrcutor)
    long event2Id;
    dao.insert(new Photo(null,"photo3",event2Id = dao.insert(new Event("Event2"))));

    // Get and output Each Event with the Photos for that Event
    List<EventWithPhotos> allEventsWithPhotosList = dao.getAllEventsWithPhotos();
    for (EventWithPhotos ewp: allEventsWithPhotosList) {
    Log.d("EVENTPHOTOINFO","Event is " + ewp.event.other_columns);
    for (Photo p: ewp.photos) {
    Log.d("EVENTWITHPHOTO","\tPhoto is " + p.getPath() + " ID is " + p.getId_photo());
    }
    }
    结果
    运行时日志包含:-
    D/EVENTPHOTOINFO: Event is Event1
    D/EVENTWITHPHOTO: Photo is photo1 ID is 1
    D/EVENTWITHPHOTO: Photo is photo2 ID is 2
    D/EVENTPHOTOINFO: Event is Event2
    D/EVENTWITHPHOTO: Photo is photo3 ID is 3
    数据库(使用数据库检查器查看)显示:-
    Activity table :-
    enter image description here
    照片 table :-
    enter image description here

    关于java - 如何在 Room 2.3.0 中向我的实体添加外键?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67880795/

    26 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com