春季休息`@Controller` wiered行为

时间:2016-12-19 06:41:13

标签: java json spring rest spring-mvc

我正在通过@Controller尝试Spring Rest服务。但我遇到一种方法调用响应有效数据和其他过滤方法调用返回错误响应的情况。这是我的controller

@Controller 
@RequestMapping("/company")
public class CompanyDetailsController {

@Autowired
private CompanyServices companyServices;

@RequestMapping(method = RequestMethod.GET)
public @ResponseBody List<CompanyDetails> getCompanyDetails() {
    return companyServices.getCompanyDetails();
}

@RequestMapping(value = "/{companyShortCode}", method = RequestMethod.GET)
public @ResponseBody CompanyDetails getCompanyDetails(@PathVariable("companyShortCode") String companyShortCode) {
    System.out.println("companyShortCode = "+companyShortCode);
    CompanyDetails companyDetails = companyServices.getCompanyDetails(companyShortCode);
    /*CompanyDetails companyDetails = new CompanyDetails();
    companyDetails.setCompanyCode("abc");
    companyDetails.setCompanyEmail("abc@123.com");
    companyDetails.setCompanyPhone(92349234);
    companyDetails.setWebSite("abc.abc.com");
    System.out.println("companyDetails = "+companyDetails);*/
    return companyDetails;
}
}

CompanyDetails

@Entity
@Table(name = "company_details")
@JsonIgnoreProperties({ "hibernateLazyInitializer", "handler" })
public class CompanyDetails implements Serializable {

private static final long serialVersionUID = 8713608417980657723L;

@Id
@Column(name="COMPANY_CODE", nullable = false, updatable = false)
private String companyCode = null;

@Column(name = "COMPANY_NAME", nullable = false, updatable = true)
private String companyName = null;

@Column(name = "COMPANY_PHONE", nullable = true, updatable = true)
private long companyPhone = 0;

@Column(name = "COMPANY_EMAIL", nullable = true, updatable = true)
private String companyEmail = null;

@Column(name = "COMPANY_WEBSITE", nullable = true, updatable = true)
private String webSite = null;

public String getCompanyCode() {
    return companyCode;
}

public void setCompanyCode(String companyCode) {
    this.companyCode = companyCode;
}

public String getCompanyName() {
    return companyName;
}

public void setCompanyName(String companyName) {
    this.companyName = companyName;
}

public long getCompanyPhone() {
    return companyPhone;
}

public void setCompanyPhone(long companyPhone) {
    this.companyPhone = companyPhone;
}

public String getCompanyEmail() {
    return companyEmail;
}

public void setCompanyEmail(String companyEmail) {
    this.companyEmail = companyEmail;
}

public String getWebSite() {
    return webSite;
}

public void setWebSite(String webSite) {
    this.webSite = webSite;
}

@Override
public int hashCode() {
    final int prime = 31;
    int result = 1;
    result = prime * result
            + ((companyCode == null) ? 0 : companyCode.hashCode());
    result = prime * result
            + ((companyName == null) ? 0 : companyName.hashCode());
    return result;
}

@Override
public boolean equals(Object obj) {
    if (this == obj)
        return true;
    if (obj == null)
        return false;
    if (getClass() != obj.getClass())
        return false;
    CompanyDetails other = (CompanyDetails) obj;
    if (companyCode == null) {
        if (other.companyCode != null)
            return false;
    } else if (!companyCode.equals(other.companyCode))
        return false;
    if (companyName == null) {
        if (other.companyName != null)
            return false;
    } else if (!companyName.equals(other.companyName))
        return false;
    return true;
}

@Override
public String toString() {
    return "CompanyDetails [companyCode=" + companyCode + ", companyName="
            + companyName + ", companyPhone=" + companyPhone
            + ", companyEmail=" + companyEmail + ", webSite=" + webSite
            + "]";
}
}

Repository

@Repository
public class DetailsDaoImpl implements DetailsDao {

private SessionFactory sessionFactory;

public void setSessionFactory(SessionFactory sessionFactory) {
    this.sessionFactory = sessionFactory;
}
@Override
@Transactional(readOnly = true)
public List<CompanyDetails> getCompanyDetails() {
    List<CompanyDetails> details = (List<CompanyDetails>) sessionFactory.getCurrentSession().createCriteria(CompanyDetails.class).list();
    return details;
}

@Override
@Transactional(readOnly = true)
public CompanyDetails getCompanyDetails(String companyShortCode) {
    System.out.println("companyShortCode = "+companyShortCode);
    CompanyDetails details = (CompanyDetails) sessionFactory.getCurrentSession().load(CompanyDetails.class, companyShortCode);
    System.out.println("details = "+details);
    return details;
}
}

Service

public class CompanyServicesImpl implements CompanyServices {

@Autowired
DetailsDao detailsDao;

@Override
public List<CompanyDetails> getCompanyDetails() {
    return detailsDao.getCompanyDetails();

}

@Override
public CompanyDetails getCompanyDetails(String companyShortCode) {
    System.out.println("companyShortCode = "+companyShortCode);
    return detailsDao.getCompanyDetails(companyShortCode);
}

}

如果我致电List<CompanyDetails> getCompanyDetails(),则返回 -

[
  {
  "companyCode": "ABCD",
  "companyName": "Test Company",
  "companyPhone": 11226123456,
  "companyEmail": "abc@abcd.com",
  "webSite": "www.abc.com"
   },
  {
  "companyCode": "XYZA",
  "companyName": "XYZA Company",
  "companyPhone": 1122000000,
  "companyEmail": "abc@XYZA.com",
  "webSite": "www.XYZA.com"
   }
]

但是当我打电话 - Public @ResponseBody CompanyDetails getCompanyDetails(@PathVariable("companyShortCode") String companyShortCode) {时, 它返回 -

{"companyPhone": 0}

我尝试使用虚拟对象并将其转换为Json。尝试创建普通bean而不是@Entity并使用BeanUtils来复制属性并响应正确的Json。任何人都知道为什么会这样吗?

更新

在发送回复之前,它打印为CompanyDetails [companyCode=ABCD, companyName=Test Company, companyPhone=9823611147, companyEmail=abc@abcd.com, webSite=www.abc.com]

2 个答案:

答案 0 :(得分:3)

当您使用主键public CompanyDetails getCompanyDetails(String companyShortCode)检索CompanyDetails对象时,使用companyShortCode方法时,使用load方法。

load方法返回一个代理对象,其中只设置了主键属性,并且未设置所有其他属性。只有当您为session之类的属性调用任何一种getter方法时,details.getCompanyEmail()对象才会发送查询以检索实际对象。

为避免这种情况,您可以调用get方法。请参阅下面的代码段:

@Override
@Transactional(readOnly = true)
public CompanyDetails getCompanyDetails(String companyShortCode) {
    System.out.println("companyShortCode = "+companyShortCode);
    CompanyDetails details = (CompanyDetails) sessionFactory.getCurrentSession().get(CompanyDetails.class, companyShortCode);
    System.out.println("details = "+details);
    return details;
}
}

如果您想使用加载方法,请使用下面的代码段:

@Override
@Transactional(readOnly = true)
public CompanyDetails getCompanyDetails(String companyShortCode) {
    System.out.println("companyShortCode = "+companyShortCode);
    CompanyDetails details = (CompanyDetails) sessionFactory.getCurrentSession().load(CompanyDetails.class, companyShortCode);
    details.getCompanyName(); //after this all attribute of CompanyDetails object will be set
    System.out.println("details = "+details);
    return details;
}
}

有关详情,请参阅this

希望它有所帮助。

答案 1 :(得分:-1)

首先,代码没有完全发布,而且我不清楚第二次调用的响应。问题可能出在您可能正在创建新对象的公司服务中,而不是从JPA或其底层平台获取。另一个原因可能是JPA配置。