Я учу RequestFactory. У меня простой пример работы. Теперь я хотел бы реализовать для РФ этих субъектов снизу:RequestFactory Параметр Entity: List <OfOtherEntity> имеет значение null для клиента. На сервере нормально
пакет сервера
@Entity
public class Pizza implements Identifiable, Versionable {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Version
private Long version;
private String name;
@ManyToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER)
private List<Ingredient> ingredients;
/* Getters and Setters */
}
@Entity
public class Ingredient implements Identifiable, Versionable {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Version
private Long version;
private String name;
private boolean vegan;
/* Getters and Setters */
}
Вот DAO
класс для Pizza Entity
:
@Override
public List<Pizza> get() {
CriteriaBuilder cb = JPA.em().getCriteriaBuilder();
CriteriaQuery<Pizza> q = cb.createQuery(Pizza.class);
Root<Pizza> c = q.from(Pizza.class);
q.select(c);
TypedQuery<Pizza> query = JPA.em().createQuery(q);
List<Pizza> results = query.getResultList();
for(Pizza p: results) {
for(Ingredient i: p.getIngredients()) {
logger.info(i.getName());
}
}
return results;
}
Shared пакет
Я написал Proxies для этих классов:
@ProxyFor(value = Pizza.class, locator = PizzaLocator.class)
public interface PizzaProxy extends EntityProxy {
public Long getId();
public String getName();
public void setName(String name);
public Long getVersion();
public List<IngredientProxy> getIngredients();
public void setIngredients(List<IngredientProxy> ingredients)
}
@ProxyFor(value = Ingredient.class)
public interface IngredientProxy extends EntityProxy {
public void setId(Long id);
public Long getId();
public Long getVersion();
public void setVersion(Long version);
public String getName();
public void setName(String name);
public boolean isVegan();
public void setVegan(boolean vegan);
}
связанные радиочастотные интерфейсы:
public interface RequestFactoryServices extends RequestFactory {
PizzaRequest pizzaRequest();
}
@Service(value = PizzaDao.class, locator = DaoLocator.class)
public interface PizzaRequest extends RequestContext {
Request<PizzaProxy> findById(Long id);
Request<Void> save(PizzaProxy pizza);
Request<List<PizzaProxy>> get();
}
пакета Client
И вот так я получить данные из сервер:
List<PizzaProxy> pizzas = new LinkedList<PizzaProxy>();
PizzaRequest context = createFactory().pizzaRequest();
context.get().to(new Receiver<List<PizzaProxy>>() {
@Override
public void onSuccess(List<PizzaProxy> response) {
for(PizzaProxy p: response) {
RootPanel.get().add(new Label(
p.getId() + " " +
p.getName() + ", " +
p.getVersion() + ", " +
p.getIngredients()
));
}
}
}).fire();
Как Вы можете видеть в DAO
классе в get()
методы я печать на инфокоды об ингредиентах. На стороне сервера все работает.
Проблема в том, что когда я звоню p.getIngredients()
, я получаю null
, а не список IngredientsProxies
.
Это происходит потому, что у меня нет классов Dao и Locator для Ingredients
Entity?
Пожалуйста, помогите.
Ответ: Entity Отношения
Изменения связанных объектов могут быть сохранены в одном запросе. Например, этот код из примера примера DynatableRF в соединительной линии GWT создает новое лицо и адрес в одно и то же время:
PersonRequest context = requestFactory.personRequest(); AddressProxy address = context.create (AddressProxy.class); PersonProxy person = context.create (PersonProxy.class); человек.setAddress (адрес); context.persist() используя (человек) .fire (...); RequestFactory автоматически отправляет весь граф объекта в одном запросе. В этом случае реализация Person.persist() на сервере отвечает за сохранение связанного адреса также, который может или не может произойти автоматически, в зависимости от структуры ORM и того, как определяется связь. Обратите внимание, что RequestFactory в настоящее время не поддерживает внедренные объекты (@Embedded в различных структурах ORM), потому что он ожидает, что каждая сущность будет существовать независимо со своим собственным идентификатором.
При запросе сервера RequestFactory автоматически не заполняет отношения в графе объектов. Для этого используйте метод with() по запросу и укажите имя связанного свойства в виде строки:
Запрос findReq = requestFactory.personRequest(). Find (personId) .with ("address"); Также необходимо использовать метод with() для получения любых свойств с типами, расширяющими ValueProxy. Метод with() принимает несколько аргументов String, поэтому вы можете сразу указать несколько имен свойств. Чтобы указать вложенные свойства, используйте точечную нотацию. Собираем все вместе, вы можете иметь
Запрос findReq = найти (PersonId) .with ("телефон", "address.city", "address.zip")
Может ли «ингредиенты» пройти каким-то образом сохранить? Я хотел бы избегать струн, сколько смогу :-) – masterdany88
У меня было такое же чувство и на самом деле было предложено усилить добавление поддержки аннотаций @Eager к классу Proxy, чтобы идентифицировать коллекции, которые нужно получать с нетерпением. Я могу на самом деле сделать это сам в какой-то момент, но переключился на использование GWT-RESTY, чтобы мои api были более портативными. Я создал константы в прокси в качестве помощников, чтобы я мог использовать что-то вроде (PizzaProxy.Ingredients) вместо того, чтобы использовать строку и изменять ее в нескольких местах. Имейте в виду, что это значительное увеличение производительности, чтобы не отправлять коллекции по умолчанию. –
Это можно сделать также с отражением или генерацией кода. Придется ждать, пока Google его выполнит. – masterdany88