我在Oracle WebLogic 11g上使用Jersey 1.9建立了一个jax-rs Web服务。我的 Web 服务有两种 Web 方法:
@Path("{lid}/name")
@GET
@Produces(MediaType.TEXT_PLAIN)
public String getName(@PathParam("ebid") long ebid, @PathParam("lid") long lid)
{
System.out.println("LocationService.getName");
LocationLocalSession ejb = EJBLookup.getLocationLocalSession();
LocationVO location = ejb.getLocationInfo(ebid, lid);
System.out.println("return location name: " + location.getLocationName());
return location.getLocationName();
}
第一个(上面)完全按预期工作,没有问题。 它通过 EJB 检索位置对象,并以纯文本形式返回该位置对象的名称。我设置此方法只是为了测试Web服务是否正常工作。我真的只关心第二种方法。
下面是第二种网络方法。它的功能与第一个几乎相同。它通过 EJB 检索位置对象,但以 JSON 形式返回整个位置对象,而不仅仅是名称。当我调用此方法(ajax 或直接 Web 浏览器)时,该方法将执行,它检索位置对象,按预期将 print 语句打印到应用服务器日志中,但从不返回响应,它只是无限期挂起。
@Path("{lid}")
@GET
@Produces(MediaType.APPLICATION_JSON)
public LocationVO get(@PathParam("ebid") long ebid, @PathParam("lid") long lid)
{
System.out.println("LocationService.get");
LocationLocalSession ejb = EJBLookup.getLocationLocalSession();
LocationVO location = ejb.getLocationInfo(ebid, lid);
System.out.println("return location: " + location.getLocationName());
return location;
}
最终,由于没有响应,请求超时,我最终在 WebLogic 中遇到了一个卡住的线程。有没有人知道为什么此方法不会返回响应?我可以根据需要创建任意数量的方法来返回字符串/纯文本,并且它们始终有效,但是一旦我尝试将对象返回为 JSON,它每次都会挂起。这是我在网络中的泽西岛配置.xml以防它可以提供任何线索:
<servlet>
<display-name>JAX-RS Servlet</display-name>
<servlet-name>jersey-servlet</servlet-name>
<servlet-class>com.sun.jersey.spi.container.servlet.ServletContainer</servlet-class>
<init-param>
<param-name>javax.ws.rs.Application</param-name>
<param-value>gis.ws.ServiceApplication</param-value>
</init-param>
<init-param>
<param-name>com.sun.jersey.api.json.POJOMappingFeature</param-name>
<param-value>true</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>jersey-servlet</servlet-name>
<url-pattern>/api/*</url-pattern>
</servlet-mapping>
谢谢
编辑:添加位置VO
public class LocationVO implements Serializable
{
private static final long serialVersionUID = 1L;
//The Database Fields variable should be used in SQL queries
public static final String LOCATION_DATABASE_FIELDS =
"LOCATION.LOCATION_ID LOCATION__LOCATION_ID, "+
"LOCATION.EVENT_BOARD_ID LOCATION__EVENT_BOARD_ID, " +
"LOCATION.LOCATION_NAME LOCATION__LOCATION_NAME, " +
"LOCATION.ADDRESS LOCATION__ADDRESS, "+
"LOCATION.CITY LOCATION__CITY, "+
"LOCATION.STATE LOCATION__STATE, "+
"LOCATION.ZIPCODE LOCATION__ZIPCODE, "+
"LOCATION.COUNTRY LOCATION__COUNTRY, "+
"LOCATION.PHONE LOCATION__PHONE, "+
"LOCATION.MAP_GRID LOCATION__MAP_GRID, "+
"LOCATION.COMMENTS LOCATION__COMMENTS, "+
"LOCATION.CREATED_BY LOCATION__CREATED_BY, "+
"LOCATION.CREATED_DATE LOCATION__CREATED_DATE ";
private long locationId = 0l;
private long eventBoardId = 0l;
private String locationName = null;
private String address = null;
private String city = null;
private String state = null;
private String zipcode = null;
private String country = null;
private String phone = null;
private String mapGrid = null;
private String comments = null;
private long createdBy = 0l;
private Date createdDate = null;
private String displayName = null;
//this field is not part of the database:
private long requestor = 0l;
public LocationVO()
{}
public long getLocationId() {return this.locationId;}
public void setLocationId(long locationId) {this.locationId = locationId;}
public long getEventBoardId() {return this.eventBoardId;}
public void setEventBoardId(long eventBoardId) {this.eventBoardId = eventBoardId;}
public String getLocationName() {return this.locationName;}
public void setLocationName(String locationName) {this.locationName = StringUtilities.safeTrim(locationName);}
public String getAddress() {return this.address;}
public void setAddress(String address) {this.address = StringUtilities.safeTrim(address);}
public String getCity() {return this.city; }
public void setCity (String city) {this.city = StringUtilities.safeTrim(city);}
public String getState() {return this.state; }
public void setState(String state) {this.state = StringUtilities.safeTrim(state);}
public String getZipcode () {return this.zipcode; }
public void setZipcode (String zipcode) {this.zipcode = StringUtilities.safeTrim(zipcode);}
public String getCountry () {return this.country; }
public void setCountry (String country) {this.country = StringUtilities.safeTrim(country);}
public String getPhone() {return this.phone;}
public void setPhone(String phone) {this.phone = StringUtilities.safeTrim(phone);}
public String getMapGrid() {return this.mapGrid;}
public void setMapGrid(String mapGrid) {this.mapGrid = StringUtilities.safeTrim(mapGrid);}
public String getComments() {return this.comments;}
public void setComments(String comments) {this.comments = StringUtilities.safeTrim(comments);}
public long getCreatedBy() {return this.createdBy;}
public void setCreatedBy(long createdBy) {this.createdBy = createdBy;}
public Date getCreatedDate() {return this.createdDate;}
public void setCreatedDate(Date createdDate) {this.createdDate = createdDate;}
public long getRequestor() {return this.requestor;}
public void setRequestor(long requestor) {this.requestor = requestor;}
public String getDisplayName() {return this.displayName;}
public void setDisplayName(String displayName) {this.displayName = StringUtilities.safeTrim(displayName);}
public boolean getValid()
{
return (this.locationName != null && this.locationName.length() > 0)
|| (this.address != null && this.address.length() > 0)
|| (this.city != null && this.city.length() > 0);
}
public LocationVO copy()
{
LocationVO copy = new LocationVO();
copy.locationId = this.locationId;
copy.eventBoardId = this.eventBoardId;
copy.locationName = this.locationName;
copy.address = this.address;
copy.city = this.city;
copy.state = this.state;
copy.zipcode = this.zipcode;
copy.country = this.country;
copy.phone = this.phone;
copy.mapGrid = this.mapGrid;
copy.comments = this.comments;
copy.createdBy = this.createdBy;
copy.createdDate = this.createdDate;
copy.displayName = this.displayName;
return copy;
}
public String getLocationForDisplayAsHtml()
{
StringBuffer addressBlock = new StringBuffer();
if (locationName != null)
{
addressBlock.append(locationName);
if (address != null || city != null || state != null || zipcode != null || country != null || phone != null || mapGrid != null)
addressBlock.append("<br/>");
else return addressBlock.toString();
}
if (address != null)
{
addressBlock.append(address);
if (city != null || state != null || zipcode != null || country != null || phone != null || mapGrid != null)
addressBlock.append("<br/>");
else return addressBlock.toString();
}
if (city != null)
{
addressBlock.append(city);
if (state != null)
{
addressBlock.append(", "+state);
}
addressBlock.append(" ");
}
else if (state != null)
{
addressBlock.append(state +" ");
}
if (zipcode != null) addressBlock.append(zipcode);
if ((city != null || state != null || zipcode != null) && country != null || phone != null || mapGrid != null)
addressBlock.append("<br/>");
if (country != null) addressBlock.append(country +" ");
if (phone != null) addressBlock.append(phone +" ");
if (mapGrid != null) addressBlock.append(mapGrid);
return addressBlock.toString();
}
public String getLocationForDisplayAsHtml(String highlight)
{
return this.getLocationForDisplayAsHtml().replaceAll(highlight,"<span style='background-color: #FFFF00'>"+highlight+"</span>");
}
/**
* This method returns a String representation of this object for audit trail purposes.
*/
public String asString()
{
StringBuffer result = new StringBuffer();
boolean first = true;
if(this.locationName != null)
{
if (!first) result.append(", ");
result.append(this.locationName);
first = false;
}
if(this.address != null)
{
if (!first) result.append(", ");
result.append(this.address);
first = false;
}
if(this.city != null)
{
if (!first) result.append(", ");
result.append(this.city);
first = false;
}
if(this.state != null)
{
if (!first) result.append(", ");
result.append(this.state);
first = false;
}
if(this.zipcode != null)
{
if (!first) result.append(", ");
result.append(this.zipcode);
first = false;
}
if(this.country != null)
{
if (!first) result.append(", ");
result.append(this.country);
first = false;
}
if(this.mapGrid != null)
{
if (!first) result.append(", ");
result.append(this.mapGrid);
first = false;
}
return result.toString();
}
/**
* This method returns a String representation of this object for audit trail purposes.
*/
public String toString()
{
StringBuffer result = new StringBuffer(this.locationId +",");
if(this.eventBoardId != 0l) result.append(this.eventBoardId +",");
if(this.locationName != null) result.append(this.locationName +",");
if(this.address != null) result.append(this.address +",");
if(this.city != null) result.append(this.city +",");
if(this.state != null) result.append(this.state +",");
if(this.zipcode != null) result.append(this.zipcode +",");
if(this.country != null) result.append(this.country +",");
if(this.mapGrid != null) result.append(this.mapGrid +",");
if(this.comments != null) result.append(this.comments +",");
if(this.createdBy != 0l) result.append(this.createdBy +",");
if(this.createdDate != null) result.append(this.createdDate +",");
if(this.displayName != null) result.append(this.displayName +",");
if(result.length() > Constants.AUDIT_TRAIL_DATA_STORAGE_FIELD_LENGTH)
return result.toString().substring(0, Constants.AUDIT_TRAIL_DATA_STORAGE_FIELD_LENGTH);
else
return result.toString();
}
}
尝试使用两个基本的 REST 资源来测试您的配置。如果两者都失败了,那就是Oracle WebLogic中的东西。
@Path("test1")
@GET
@Produces(MediaType.APPLICATION_JSON)
public LocationVO test1()
{
LocationVO location = new LocationVO();
location.setLocationName("somewhere");
return location;
}
@Path("test2")
@GET
@Produces(MediaType.APPLICATION_JSON)
public JSONObject test2()
{
return new JSONObject().put("test2", "works");
}
https://jersey.java.net/documentation/1.19/json.html
为了能够正确映射 POJO,解析器必须知道如何处理对象。向对象添加@XmlRootElement可以让分析器知道从哪里开始。
@XmlRootElement
public class LocationVO implements Serializable {
...
}
附言另一个提示是使用记录器,而不是System.out.println(),因为当应用程序部署到服务器时,它也会打印logg。"sysout"只会打印到您的主机。