0

由于不可能只使用 Long Id,我正在尝试使用生成的 String 键。我有三个 Classes User, Topic,Comments带有User- 1:n - Topic- 1:n - Comments

班级评论:

@Entity
public class Comment implements Serializable{
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Extension(vendorName = "datanucleus", key = "gae.encoded-pk", value = "true")
    private String key;
    @ManyToOne
    private User author;
    @ManyToOne
    private Topic topic;

班级用户:

@Entity
public class User implements Serializable{
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Extension(vendorName = "datanucleus", key = "gae.encoded-pk", value = "true")
    private String key;

    @Unique
    private String username;

课堂主题:

@Entity
public class Topic implements Serializable{
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Extension(vendorName="datanucleus", key="gae.encoded-pk", value="true")
    private String key;
    @ManyToOne(cascade = CascadeType.ALL)
    private User author;
    @OneToMany(cascade = CascadeType.ALL)
    private List<Comment> comments;

现在,当我尝试保存新用户时,会发生以下异常

Invalid primary key for User.  Cannot have a null primary key field if the field is unencoded and of type String.  Please provide a value or, if you want the datastore to generate an id on your behalf, change the type of the field to Long. 

是否可以在不手动使用 KeyFactory 的情况下生成字符串 ID?如果是,我的代码有什么问题?

谢谢

4

2 回答 2

1

IIRC IDENTITY 策略是生成数字(或键)ID。如果您使用的是 JDO,则可以使用自动生成的 UUID 样式的 id。请参阅https://developers.google.com/appengine/docs/java/datastore/jdo/creatinggettinganddeletingdata#Keys

于 2012-10-26T07:30:28.313 回答
0

我用TableGenerator. want无论您喜欢哪种风格,它都很有用。假设即使您想获得诸如此类的GroupidGRP0000001GRP0000500。您必须使用属性注入,而不是实体中的字段注入。它基于您的 setter ID 方法。如果generate生成的id是201 EntityManager,实体管理器会调用setId()setter注入。如果是这样,id 将是GRP0000201.

我的例子:

@Entity
@TableGenerator(name = "GROUP_GEN", table = "ID_GEN", pkColumnName = "GEN_NAME", 
                valueColumnName = "GEN_VAL", pkColumnValue = "GROUP_GEN", allocationSize = 1)
@Access(value = AccessType.FIELD)
public class Group implements Serializable {
    @Transient
    private String id;
    private String name;
    //name getter and setter
    public void setId(String id) {
        if(id != null) {
            this.id = Utils.formatId(id, "GRP", 10);    
        }
    }

    @Id
    @GeneratedValue(strategy = GenerationType.TABLE, generator = "GROUP_GEN")
    @Access(value = AccessType.PROPERTY)
    public String getId() {
        return id;
    }
}

实用程序.java

public class Utils {
    /**
     * E.g.
     * Input: id=523, prefix="AAA", maxLength=15
     * Output: AAA000000000523
     */
    public static String formatId(String id, String prefix, int maxLength) {
        if (!id.startsWith(prefix)) {
            int length = id.length() + prefix.length();
            for (; (maxLength - length) > 0; length++) {
                id = '0' + id;
            }
            id = prefix + id;
        }
        return id;
    }
}
于 2012-10-25T10:05:51.943 回答