该设计一共五个类
接口类,接口实现类,回调类,结果类,异常类。
项目代码见附件
1.JcoTemplate接口类
/**
*
*/
package com.youisoft.sap;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
import org.apache.commons.logging.Log;
import com.sap.conn.jco.JCoDestination;
import com.sap.conn.jco.JCoDestinationManager;
import com.sap.conn.jco.JCoException;
import com.sap.conn.jco.JCoFunction;
import com.sap.conn.jco.JCoStructure;
import com.sap.conn.jco.JCoTable;
/**
* @author janly
*
*/
public abstract class JcoTemplate {
protected static Log logger=org.apache.commons.logging.LogFactory.getLog(JcoTemplate.class);
private String jcoproperties;
public void init(){
if(jcoproperties!=null) this.addJcoDestinationData(JcoTemplate.class.getSimpleName(),jcoproperties);
}
public void setJcoproperties(String jcoproperties) {
this.jcoproperties = jcoproperties;
}
public abstract void removeJcoDestinationData(String destinationName);
public abstract void addJcoDestinationData(String destinationName,java.util.Properties jcoproperties);
public void addJcoDestinationData(String destinationName){
URL url=Thread.currentThread().getContextClassLoader().getResource("jco3.properties");
this.addJcoDestinationData(destinationName, url.getFile());
}
public void addJcoDestinationData(String destinationName,String jcoproperties){
InputStream fis=null;
try {
fis=new FileInputStream(jcoproperties);
java.util.Properties properties = new java.util.Properties();
properties.load(fis);
this.addJcoDestinationData(destinationName, properties);
} catch (Exception e) {
logger.error(e);
}finally{
try {
if(fis!=null) fis.close();
} catch (IOException e) {
}
}
}
public final JCoDestination getJcoDestination(String destinationName) throws SapException{
try {
return JCoDestinationManager.getDestination(destinationName);
} catch (JCoException e) {
logger.error(e);
throw new SapException(e);
}
}
public final void callFunctionForParameterInTableAndStructure(final String destinationName,
final String rfcName,JcoCallback jcoCallback) throws SapException{
if (rfcName == null) {
throw new SapException("rfcName is empty");
}
try {
JCoFunction function = JCoDestinationManager.getDestination(destinationName).getRepository().getFunction(rfcName);
jcoCallback.beforeInvoke(function);
long be=System.currentTimeMillis();
function.execute(JCoDestinationManager.getDestination(destinationName));
long en=System.currentTimeMillis();
logger.debug("rfcName:"+rfcName+",time:"+(en-be));
jcoCallback.afterInvoke(function);
} catch (Exception e) {
logger.error(e);
throw new SapException(e);
}
}
public final SapResult callFunctionForParameterInTableAndStructure(
final String destinationName,
final String rfcName,
final Map<String, String> inParams,
final String[] inParamsStructureNames,
final Map<String, String>[] inParamsStructureValues,
final String[] inParamsTableNames,
final List<Map<String, String>>[] inParamsTableValues,
final String[] returnParameterColumns,
final String[] returnParamsStructureNames,
final List<String>[] returnParamsStructureColumns,
final String[] returnTableNames,
final List<String>[] returnTableColumns)
throws SapException{
final SapResult sapResult=new SapResult();
this.callFunctionForParameterInTableAndStructure(destinationName,rfcName, new JcoCallback(){
public void beforeInvoke(JCoFunction function) {
if (inParams != null) {
Set<String> inParamsKeys = inParams.keySet();
for (String inParamsKey : inParamsKeys)
function.getImportParameterList().setValue(inParamsKey,
inParams.get(inParamsKey));
}
if (inParamsStructureNames != null) {
String inStructureName = null;
Set<String> columnSet;
for (int i = 0; i < inParamsStructureNames.length; i++) {
inStructureName = inParamsStructureNames[i];
Map<String, String> inStructureValues = inParamsStructureValues[i];
JCoStructure inStructure = function.getImportParameterList()
.getStructure(inStructureName);
columnSet = inStructureValues.keySet();
for (String columnName : columnSet) {
inStructure.setValue(columnName,
inStructureValues.get(columnName));
}
}
}
if (inParamsTableNames != null) {
Set<String> columnSet;
for (int i = 0; i < inParamsTableNames.length; i++) {
String inTableName = inParamsTableNames[i];
List<Map<String, String>> inTableValues = inParamsTableValues[i];
JCoTable inTable = function.getTableParameterList().getTable(
inTableName);
for (Map<String, String> rowMap : inTableValues) {
inTable.appendRow();
columnSet = rowMap.keySet();
for (String columnName : columnSet)
inTable.setValue(columnName, rowMap.get(columnName));
}
}
}
}
public void afterInvoke(JCoFunction function) {
if (returnParameterColumns != null) {
Map<String, String> retRecords = new HashMap<String, String>();
for (int i = 0; i < returnParameterColumns.length; i++) {
String columnName = returnParameterColumns[i];
Object value = function.getExportParameterList().getValue(
columnName);
retRecords.put(columnName, value==null?null:value.toString());
}
sapResult.setResultParams(retRecords);
}
if (returnParamsStructureNames != null) {
Map<String, Map<String, String>> resultStructures = new HashMap<String, Map<String, String>>();
for (int i = 0; i < returnParamsStructureNames.length; i++) {
resultStructures.put(returnParamsStructureNames[i],new HashMap<String, String>());
JCoStructure js = function.getExportParameterList().getStructure(returnParamsStructureNames[i]);
for (int j = 0; j < returnParamsStructureColumns[i].size(); j++) {
Object obj=js.getValue(returnParamsStructureColumns[i].get(j));
resultStructures.get(returnParamsStructureNames[i]).put(
returnParamsStructureColumns[i].get(j),obj==null?null:obj.toString());
}
}
sapResult.setResultStructures(resultStructures);
}
if (returnTableNames != null) {
Map<String,List<Map<String, String>>> retTableRecords = new HashMap<String,List<Map<String, String>>>();
for (int i = 0; i < returnTableNames.length; i++) {
JCoTable table = function.getTableParameterList().getTable(returnTableNames[i]);
List<Map<String, String>> records = new ArrayList<Map<String, String>>();
if (table != null)
for (int k = 0; k < table.getNumRows(); k++) {
table.setRow(k);
Map<String, String> recordRow = new HashMap<String, String>();
for (int j = 0; j < returnTableColumns[i].size(); j++) {
Object obj=table.getValue(returnTableColumns[i].get(j));
recordRow.put(returnTableColumns[i].get(j),obj==null?null:obj.toString() );
}
records.add(recordRow);
}
retTableRecords.put(returnTableNames[i], records);
}
sapResult.setResultTables(retTableRecords);
}
}
});
return sapResult;
}
}
2.模板实现类
package com.youisoft.sap;
import java.util.HashMap;
import java.util.Properties;
import java.util.concurrent.Semaphore;
import com.sap.conn.jco.ext.DestinationDataEventListener;
import com.sap.conn.jco.ext.DestinationDataProvider;
import com.sap.conn.jco.ext.Environment;
/**
* @author janly
*
*/
public class DefaultJcoTemplate extends JcoTemplate{
private static DefaultDestinationDataProvider defaultDestinationDataProvider=new DefaultDestinationDataProvider();
private static Semaphore semaphore=new Semaphore(1);
static {
defaultDestinationDataProvider.setDestinationDataEventListener(new DestinationDataEventListener(){
public void deleted(String arg0) {
logger.info("deleted:"+arg0);
}
public void updated(String arg0) {
logger.info("updated:"+arg0);
}
});
Environment.registerDestinationDataProvider(defaultDestinationDataProvider);
}
public void removeJcoDestinationData(String destinationName){
defaultDestinationDataProvider.deleteDestination(destinationName);
}
@Override
public void addJcoDestinationData(String destinationName,java.util.Properties jcoproperties){
try {
semaphore.acquire();
if(defaultDestinationDataProvider.getDestinationProperties(destinationName)==null){
logger.info("Add destinationName:"+destinationName+",jcoproperties:"+jcoproperties);
defaultDestinationDataProvider.addDestination(destinationName, jcoproperties);
}else{
logger.info("destinationName:"+destinationName+" alread exist");
}
} catch (Exception e) {
logger.error(e);
}finally{
semaphore.release();
}
}
private static class DefaultDestinationDataProvider implements DestinationDataProvider {
private DestinationDataEventListener destinationDataEventListener;
private HashMap<String, Properties> destinations=new HashMap<String, Properties>();
private DefaultDestinationDataProvider(){
}
public Properties getDestinationProperties(String arg0) {
return this.destinations.get(arg0);
}
public void setDestinationDataEventListener(
DestinationDataEventListener arg0) {
destinationDataEventListener=arg0;
}
public boolean supportsEvents() {
return true;
}
public void addDestination(String destinationName, Properties properties) {
destinationDataEventListener.updated(destinationName);
synchronized (destinations) {
destinations.put(destinationName, properties);
}
}
public void deleteDestination(String destinationName) {
destinationDataEventListener.deleted(destinationName);
synchronized (destinations) {
destinations.remove(destinationName);
}
}
}
}
3.模板回调类
/**
*
*/
package com.youisoft.sap;
import com.sap.conn.jco.JCoFunction;
/**
* @author janly
*
*/
public interface JcoCallback {
public void beforeInvoke(JCoFunction function) throws Exception;
public void afterInvoke(JCoFunction function) throws Exception;
}
4.结果返回类
/**
*
*/
package com.youisoft.sap;
import java.util.List;
import java.util.Map;
/**
* @author janly
*
*/
public final class SapResult {
private Map<String, String> resultParams;
private Map<String,List<Map<String, String>>> resultTables;
private Map<String, Map<String, String>> resultStructures;
public Map<String, String> getResultParams()
{
return this.resultParams;
}
public void setResultParams(Map<String, String> resultParams) {
this.resultParams = resultParams;
}
public final Map<String, List<Map<String, String>>> getResultTables() {
return resultTables;
}
public final void setResultTables(
Map<String, List<Map<String, String>>> resultTables) {
this.resultTables = resultTables;
}
public Map<String, Map<String, String>> getResultStructures() {
return this.resultStructures;
}
public void setResultStructures(Map<String, Map<String, String>> resultStructures) {
this.resultStructures = resultStructures;
}
}
5.异常类
/**
*
*/
package com.youisoft.sap;
/**
* @author janly
*
*/
public class SapException extends Exception {
/**
*
*/
private static final long serialVersionUID = 1L;
public SapException(String message){
super(message);
}
public SapException(Throwable cause) {
super(cause);
}
}