我正在使用Google App engine1.9.3,Eclipse,Objectify5.03。我的班级如下:
import com.googlecode.objectify.Ref;
import com.googlecode.objectify.annotation.Entity;
import com.googlecode.objectify.annotation.Id;
import com.googlecode.objectify.annotation.Load;
@Entity
public class User {
@Id private Long userId;
private String userName;
@Load private Ref<UserDetails> userDetails;
@Load private Ref<UserPassword> userPassword;
//getters & setters
}
当我尝试通过Eclipse创建此类的google端点时,我收到以下错误: java.lang.IllegalArgumentException:参数化类型com.googlecode.objectify.Ref不受支持
这是我第一次尝试Objectify。
任何想法我做错了什么。从我到目前为止所阅读的内容看,GAE端点和Objectify应该有效,对吗?
答案 0 :(得分:10)
Google Cloud Endpoints无法序列化Ref
对象,因为它是objectify
定义的任意对象,因此不支持错误。
限制与 Cloud Endpoints 一起使用,因为它不允许使用自定义对象。如果您有兴趣,可以在这一点上有一个完整的讨论主题:Cloud endpoints .api generation exception when using objectify (4.0b1) parameterized key
您必须使用@ApiResourceProperty
为方法添加注释,并将其忽略的属性设置为true
,如下面的代码所示:
import com.googlecode.objectify.Ref;
import com.googlecode.objectify.annotation.Entity;
import com.googlecode.objectify.annotation.Id;
import com.googlecode.objectify.annotation.Load;
import com.google.api.server.spi.config.AnnotationBoolean;
import com.google.api.server.spi.config.ApiResourceProperty;
@Entity
public class User
{
@Id private Long userId;
private String userName;
@Load private Ref<UserDetails> userDetails;
@Load private Ref<UserPassword> userPassword;
//getters & setters
@ApiResourceProperty(ignored = AnnotationBoolean.TRUE)
public UserDetail getUserDetails(){
}
@ApiResourceProperty(ignored = AnnotationBoolean.TRUE)
public UserPassword getUserPassword(){
}
}
如果您仍想使用这些对象中保存的数据,请考虑在您的User
类完成加载后,在类中添加一些字段来保存数据并初始化它们:
@Ignore String firstName;
@OnLoad
void trackUserDetails()
{
this.firstName = getUserDetails().getFirstName();
// add more code here to set other fields, you get the gist
}
但在我看来,更好的方法是重新考虑你班级的设计,或者更反思你正在尝试做的事情。
答案 1 :(得分:0)
ApiResourceProperty注释不适用于Google Emdpoints + Objectify组合,因为Ref或Key是Objectify特定类,Google Endpoints无法识别它们,并且在您尝试生成客户端库时会出错。我更改了User类,如下所示。
@Id private Long userId;
@Index private String userName;
@Load private UserDetails userDetails;
@Load private UserPassword userPassword;
@Load private ArrayList<Account> userAccounts;
//getters and setters
当我按照下面的用户名检索用户时,我会通过getter(一次性)获取User,UserDetails,UserPassword以及用户帐户列表
@ApiMethod(name = "getUserByName", path = "get_user_by_name")
public User getUserByName(@Named("userName") String userName) {
User user = null;
try {
user = ofy().load().type(User.class).filter("userName", userName).first().now();
if(user != null)
log.info("UserEndpoint.getUserByName...user retrieved="+user.getUserId());
else
log.info("UserEndpoint.getUserByName...user is null");
} catch(Exception e) {
log.info("UserEndpoint.getUserByName...exception="+e.getMessage());
}
return user;
}
当我在Google Console上使用数据存储查看器查看数据时,我会在User表的userDetails,userPassword和Accounts列中看到一些条目。我假设这些是对各自表中实际数据的引用,而不是数据本身的副本。希望这会有所帮助。