我一直试图找出最后一段时间的这一个结果。与所有那些询问如何仅通过JPA查询得到一个结果的问题完全相反,我需要更多比一个结果 - 我需要所有这些。我最终调用实体管理器的find()
方法,但它并没有给我所有的嵌套结果。需要获得来自实体经理的更多结果
'父' 类
@Entity
@Table(name = "LANGUAGE")
public class LanguageData extends PersistedAuditedData<Long> {
@Id
@Column
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@Column(name = "ISO6391ALPHA2CODE")
private String iso6391Alpha2Code;
@OneToMany(fetch = FetchType.LAZY, mappedBy = "languageData")
@MapKeyColumn(name = "LANGUAGE_ID")
private Map<Long, LanguageDataLocalization> localizations;
@OneToMany(fetch = FetchType.LAZY, mappedBy = "localizationLanguage")
@MapKeyColumn(name = "LANGUAGE_LOCALIZATION_ID")
private Map<Long, LanguageDataLocalization> languagesLocalized;
/**
* Private no-arg constructor for reflection-based
* construction inside JPA providers.
*/
@SuppressWarnings("unused")
private LanguageData() {
// Fields initialized by JPA.
}
// Plus getters for the fields.
}
'儿童' 类
@Entity
@Table(name = "LANGUAGE_LOCALIZATION")
public class LanguageDataLocalization extends PersistedAuditedData<LanguageLocalizationKey>{
@EmbeddedId
private LanguageLocalizationKey id;
@Column(name = "REFERENCE_NAME")
private String name;
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "LANGUAGE_ID", insertable = false, updatable = false)
private LanguageData languageData;
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "LANGUAGE_LOCALIZATION_ID", insertable = false, updatable = false)
private LanguageData localizationLanguage;
/**
* Private no-arg constructor for reflection-based JPA provider instantiation.
*/
@SuppressWarnings("unused")
private LanguageDataLocalization() {
// Fields initialized by JPA.
}
// Plus getters for fields.
}
主要用于 '少年' 类。
@Embeddable
public class LanguageLocalizationKey {
@Column(name = "LANGUAGE_ID")
private Long languageId;
@Column(name = "LANGUAGE_LOCALIZATION_ID")
private Long languageLocalizationId;
/**
* No-arg constructor, for use by JPA provider implementation.
* <h1>DO NOT USE!</h1>
* <p>Ideally, this should be <code>private</code>,
* however OpenJPA doesn't appear to be allowing that at the moment
* (unsure of cause). This constructor does not initialize any data.</p>
*/
@SuppressWarnings("unused")
public LanguageLocalizationKey() {
// Field initialization performed by JPA provider.
}
// Plus getters
}
而且使用像这样:
@Transactional(readOnly = true, propagation = Propagation.SUPPORTS)
private Collection<LanguageDataLocalization> getLocalizationsById(final Long id, final Collection<String> localeCodes) {
try {
if (localeCodes == null || localeCodes.isEmpty()) {
final LanguageData data = entityManager.find(LanguageData.class, id);
if (data == null) {
return Collections.emptyList();
} else {
return data.getlocalizations().values();
}
} else {
List<LanguageDataLocalization> results = entityManager.createNamedQuery("FIND_LANGUAGE_BY_ID", LanguageDataLocalization.class)
.setParameter("iso6391Alpha2Codes", localeCodes)
.setParameter("languageId", id)
.getResultList();
return results;
}
} catch (NoResultException e) {
// TODO: add logging
return Collections.emptyList();
}
}
随着named-queries.xml
定义,像这样:
<?xml version="1.0" encoding="UTF-8"?>
<entity-mappings version="1.0"
xmlns="http://java.sun.com/xml/ns/persistence/orm"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence/orm
http://java.sun.com/xml/ns/persistence/orm_1_0.xsd ">
<named-query name="FIND_LANGUAGE_BY_ID">
<query>
SELECT localized
FROM LanguageDataLocalization localized
JOIN localized.localizationLanguage local
WHERE localized.id.languageId = :languageId
AND local.iso6391Alpha2Code IN :iso6391Alpha2Codes
</query>
</named-query>
</entity-mappings>
LANGUAGE
数据(德比内存数据库,可以肯定这并不重要):
ID, ISO6391ALPHA2CODE
123, en
137, fr
个
LANGUAGE_LOCALIZATION
数据
LANGUAGE_ID, LANGUAGE_LOCALIZATION_ID, REFERENCE_NAME
123, 123, English
123, 137, anglais
实际的问题是,没有查询当任何语言环境数据(localeCodes
为空或空),data.getLocalizations().values()
的entityManager.find()
后返回的仅一个本地化语言名称列表数据(法国的,但我假设这是SQL'随机')。我上午能够得到两个本地化,如果我明确地查询他们(单独或一起),所以我知道数据的那里,并且JPQL查询工作。
当没有针对特定查询进行查询时,我可以做些什么来使它返回两者(全部是,当我有超过2种语言的本地化数据时)本地化?
的实际查询似乎是这样的(部分结果列删除):
SELECT t0.LANGUAGE_ID, t0.LANGUAGE_LOCALIZATION_ID,
t1.ISO6391ALPHA2CODE,
t0.REFERENCE_NAME
FROM LANGUAGE_LOCALIZATION t0
LEFT OUTER JOIN LANGUAGE t1
ON t0.LANGUAGE_LOCALIZATION_ID = t1.id
WHERE t0.LANGUAGE_ID = ? [params=?]
这似乎并没有被限制以任何方式行计数。 (to.LANGUAGE_ID
匹配多个行)。尤其是因为,在同一数据集,下面得到两个结果行(部分结果列再次删除):
SELECT t0.LANGUAGE_ID, t0.LANGUAGE_LOCALIZATION_ID,
t2.id, t2.ISO6391ALPHA2CODE,
t3.id, t3.ISO6391ALPHA2CODE,
t0.REFERENCE_NAME
FROM LANGUAGE_LOCALIZATION t0
INNER JOIN LANGUAGE t1
ON t0.LANGUAGE_LOCALIZATION_ID = t1.id
LEFT OUTER JOIN LANGUAGE t2
ON t0.LANGUAGE_ID = t2.id
LEFT OUTER JOIN LANGUAGE t3
ON t0.LANGUAGE_LOCALIZATION_ID = t3.id
WHERE (t0.LANGUAGE_ID = ? AND t1.ISO6391ALPHA2CODE IN (?, ?)) [params=?, ?, ?]
(这带来了为什么它既有t1
和t3
的问题,但是这是后话)
对不起,可能应该补充一点。编辑问题以包含此信息。 – 2012-07-31 16:05:18