[英]Join table with column. How is possible?
Anybody to know something about this kind of queries:任何了解此类查询的人:
@Entity
@Table(name="ACCOUNT")
@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
@NamedQueries({
@NamedQuery(name = Account.GET_EXPIRATION_DATE, query="SELECT account.expirationDate FROM " +
"Domain domain JOIN domain.account WHERE domain.id = :domainId"),
@NamedQuery(name = Account.GET_BALANCE, query="SELECT account.balance FROM " +
"Domain domain JOIN domain.account WHERE domain.id = :domainId")
})
I dont understand what is this "Domain domain JOIN domain.account" we can join one table with another but it seams we join table with column .. ?我不明白这个“域加入 domain.account”是什么我们可以将一个表与另一个表连接但它接缝我们将表与列连接起来......?
these are the related classes:这些是相关的类:
package com.smsoffice.admin;
import java.io.Serializable;
import java.util.HashSet;
import java.util.Set;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
import javax.persistence.OneToMany;
import javax.persistence.OneToOne;
import javax.persistence.Table;
import static javax.persistence.CascadeType.*;
import com.smsoffice.billing.Account;
import com.smsoffice.billing.PrepaidAccount;
@Entity
@Table(name="DOMAIN")
@NamedQueries({
@NamedQuery(name=Domain.GET_ALL_DOMAINS, query="SELECT d FROM Domain d ORDER BY d.name"),
@NamedQuery(name=Domain.GET_ACCOUNT, query="SELECT d.account FROM Domain d WHERE d.id = :id"),
@NamedQuery(name=Domain.GET_DOMAIN_BY_STATUS, query="SELECT d FROM Domain d WHERE d.enabled = :enabled ORDER BY d.name"),
@NamedQuery(name=Domain.GET_DOMAIN_BY_NAME, query="SELECT d FROM Domain d WHERE d.name = :name")
})
public class Domain implements Serializable {
private static final long serialVersionUID = 1L;
public final static String GET_ALL_DOMAINS = "Domain.getAllDomains";
public final static String GET_ACCOUNT = "Domain.getAccount";
public final static String GET_DOMAIN_BY_STATUS = "Domain.getAllDomainsByStatus";
public final static String GET_DOMAIN_BY_NAME = "Domain.getDomainByName";
public final static transient Domain ROOT = new Domain("ROOT");
public static Domain SYSTEM_DOMAIN = new Domain("SYSTEM");
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private int id;
@Column(unique = true, length = 96)
private String name;
//unique id of the service - one per domain
@GeneratedValue(strategy = GenerationType.AUTO)
private int serviceId;
//indicates whether the domain is enabled
private Boolean enabled = true;
//short code for the domain sms events
private int shortCode;
//prefix for parsing
private String prefix;
private String clientPrefix = "";
//bank account
@OneToOne(cascade = {PERSIST, REFRESH, REMOVE})
private Account account = new PrepaidAccount();
@OneToMany
private Set<User> users = new HashSet<User>();
public Domain() {}
public Domain(String name) {
this.name = name;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getServiceId() {
return serviceId;
}
public void setServiceId(int serviceId) {
this.serviceId = serviceId;
}
public int getShortCode() {
return shortCode;
}
public void setShortCode(int shortCode) {
this.shortCode = shortCode;
}
public String getPrefix() {
return prefix;
}
public void setPrefix(String prefix) {
this.prefix = prefix;
}
public Account getAccount() {
return account;
}
public void setAccount(Account account) {
this.account = account;
}
public Set<User> getUsers() {
return users;
}
public boolean isEnabled() {
return enabled;
}
public void setEnabled(boolean enabled) {
this.enabled = enabled;
}
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (!(obj instanceof Domain)) {
return false;
}
Domain domain = (Domain) obj;
return getName().toUpperCase().equals(domain.getName().toUpperCase());
}
@Override
public int hashCode() {
return getName().toUpperCase().hashCode();
}
@Override
public String toString() {
return "[" + name + "("+ account + ")]";
}
public int getId() {
return id;
}
public void setClientPrefix(String clientPrefix) {
this.clientPrefix = clientPrefix != null ? clientPrefix : "";
}
public String getClientPrefix() {
return clientPrefix;
}
}
and this one:和这个:
package com.smsoffice.billing;
import static javax.persistence.CascadeType.ALL;
import java.math.BigDecimal;
import java.math.MathContext;
import java.math.RoundingMode;
import java.util.Calendar;
import java.util.Date;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Inheritance;
import javax.persistence.InheritanceType;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
import javax.persistence.OneToOne;
import javax.persistence.Table;
@Entity
@Table(name="ACCOUNT")
@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
@NamedQueries({
@NamedQuery(name = Account.GET_EXPIRATION_DATE, query="SELECT account.expirationDate FROM " +
"Domain domain JOIN domain.account account WHERE domain.id = :domainId"),
@NamedQuery(name = Account.GET_BALANCE, query="SELECT account.balance FROM " +
"Domain domain JOIN domain.account account WHERE domain.id = :domainId")
})
public abstract class Account {
public static final MathContext MATH_CONTEXT = new MathContext(9, RoundingMode.HALF_UP);
public static final int SCALE = 3;
public static final int PRECISION = 9;
public static final String GET_BALANCE = "Account.getBalance";
public static final String GET_EXPIRATION_DATE = "Account.getExpirationDate";
@Id
@GeneratedValue(strategy=GenerationType.AUTO)
private int id;
@Column(precision = PRECISION, scale = SCALE)
protected BigDecimal balance = BigDecimal.ZERO;
@OneToOne(cascade = ALL)
protected Tariff tariff;
private Date activationDate = new Date();
private Date expirationDate;
public Account() {
Calendar calendar = Calendar.getInstance();
calendar.add(Calendar.MONTH, 1);
setExpirationDate(calendar.getTime());
}
public BigDecimal getBalance() {
return balance;
}
public Tariff getTariff() {
return tariff;
}
public void setTariff(Tariff tariff) {
this.tariff = tariff;
}
void deposit(BigDecimal amount) {
balance = balance.add(amount).setScale(SCALE, MATH_CONTEXT.getRoundingMode());
}
abstract boolean hasCredit(int eventCount);
abstract void makePayment(int eventCount) throws PaymentException;
public int getId() {
return id;
}
public Date getActivationDate() {
return activationDate;
}
public void setActivationDate(Date activationDate) {
this.activationDate = normalizeActivationDate(activationDate);
}
void setExpirationDate(Date expirationDate) {
this.expirationDate = normalizeExpirationDate(expirationDate);
}
public Date getExpirationDate() {
return expirationDate;
}
public boolean isExpired() {
Date now = new Date();
return now.after(expirationDate);
}
@Override
public String toString() {
return "[balance: " + balance + "; tariff: " + (tariff != null ? tariff.getPrice() : "no tariff") + "; expiration date: " + expirationDate.toString() + "]";
}
public void setBalance(BigDecimal newBalance) {
this.balance = newBalance;
}
private static final Date normalizeActivationDate(Date date) {
Calendar cal = Calendar.getInstance();
cal.setTime(date);
cal.set(Calendar.HOUR_OF_DAY, 0);
cal.set(Calendar.MINUTE, 0);
cal.set(Calendar.SECOND, 0);
cal.set(Calendar.MILLISECOND, 0);
return cal.getTime();
}
private static final Date normalizeExpirationDate(Date date) {
Calendar cal = Calendar.getInstance();
cal.setTime(date);
cal.set(Calendar.HOUR_OF_DAY, 23);
cal.set(Calendar.MINUTE, 59);
cal.set(Calendar.SECOND, 59);
cal.set(Calendar.MILLISECOND, 0);
return cal.getTime();
}
}
Well, these are not really SQL queries, but rather JPQL queries - there is a very good tutorial describing this, along with very nice examples.好吧,这些并不是真正的 SQL 查询,而是 JPQL 查询 - 有一个非常好的教程描述了这一点,以及非常好的示例。 Note that in JPQL you do not work directly with the tables, bur rather with entities of your domain model.
请注意,在 JPQL 中,您不直接使用表,而是使用域模型的实体。
But to your question, let's take this query as an example:但是对于您的问题,让我们以这个查询为例:
SELECT account.balance FROM Domain domain JOIN domain.account WHERE domain.id = :domainId
SELECT account.balance
will return the value of balance
attribute of the account that was JOINed to the given domain record SELECT account.balance
将返回已加入给定域记录的帐户的balance
属性值FROM Domain domain
says that Domain
entity will be used to query the data from related table, defined on the Domain
entity using @Table(name="DOMAIN")
; FROM Domain domain
表示Domain
实体将用于从相关表中查询数据,使用@Table(name="DOMAIN")
在Domain
实体上定义; the lowercase domain
is just an alias to be used within this query (see eg the WHERE portion of the query)domain
只是要在此查询中使用的别名(参见例如查询的 WHERE 部分)JOIN domain.account
will be used, together with annotation @OneToOne(cascade = {PERSIST, REFRESH, REMOVE})
defined on the account
field of Domain
entity, to get the relevant record from the table represented by Account
entityJOIN domain.account
,结合Domain
实体的account
字段定义的注解@OneToOne(cascade = {PERSIST, REFRESH, REMOVE})
,从Account
实体代表的表中获取相关记录WHERE domain.id = :domainId
will limit the results to return only the Domain
with the given id
, together with its account
; WHERE domain.id = :domainId
将限制结果仅返回具有给定id
的Domain
及其account
; the part :domainId
is a "query parameter" and is most likely replaced somewhere in the code with an actual value, using code like query.setParameter("domainId", someValue);
:domainId
是一个“查询参数”,很可能在代码中的某处用实际值替换,使用类似query.setParameter("domainId", someValue);
代码query.setParameter("domainId", someValue);
So the whole query should return value of BigDecimal
type (see field balance
defined in Account
entity).所以整个查询应该返回
BigDecimal
类型的值(见Account
实体中定义的字段balance
)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.