チェンジセット 196

差分発生行の前後
無視リスト:
コミット日時:
2008/04/07 14:55:11 (14 年前)
コミッタ:
shinomiya
ログメッセージ:

WSDLより、Webサービスのパラメータクラスのプロパティ順を取得。
(∵SOAPClient#オペレーション()に指定した引数の順序(=arguments オブジェクト)とあわせるため)

ファイル:

凡例:

変更無し
追加
削除
更新
コピー
移動
  • trunk/im-jssp-extention/src/main/java/org/intra_mart/jssp/script/api/SOAPClientObject.java

    r194 r196  
    1111import java.io.PrintStream; 
    1212import java.io.Writer; 
     13import java.lang.reflect.Field; 
    1314import java.lang.reflect.Method; 
    1415import java.lang.reflect.Modifier; 
     16import java.net.URL; 
    1517import java.util.ArrayList; 
    1618import java.util.Iterator; 
     
    2224import javassist.CtMethod; 
    2325import javassist.CtNewMethod; 
     26 
     27import javax.xml.namespace.QName; 
     28import javax.xml.parsers.DocumentBuilder; 
     29import javax.xml.parsers.DocumentBuilderFactory; 
     30import javax.xml.parsers.ParserConfigurationException; 
     31import javax.xml.xpath.XPath; 
     32import javax.xml.xpath.XPathConstants; 
     33import javax.xml.xpath.XPathExpression; 
     34import javax.xml.xpath.XPathExpressionException; 
     35import javax.xml.xpath.XPathFactory; 
    2436 
    2537import org.apache.axis2.description.AxisService; 
     
    4759import org.mozilla.javascript.ScriptableObject; 
    4860import org.mozilla.javascript.WrappedException; 
     61import org.w3c.dom.Document; 
    4962import org.w3c.dom.Element; 
     63import org.w3c.dom.NamedNodeMap; 
    5064import org.w3c.dom.NodeList; 
     65import org.xml.sax.SAXException; 
    5166 
    5267public class SOAPClientObject extends ScriptableObject implements Cloneable, java.io.Serializable { 
     
    137152                        ){ 
    138153                                // Stubクラスを呼び出すJSソース生成 
    139                                 generateStubJS(stubClassName, _soapClientWorkDir); 
     154                                generateStubJS(wsdlUri, stubClassName, _soapClientWorkDir); 
    140155                        } 
    141156 
     
    342357        } 
    343358 
    344         // TODO Unix で実行可能かをチェック 
    345359        protected synchronized int compileStub(String className, File srcDir, File destDir) throws IOException{ 
    346360             
     
    432446        private static final String LINE_SEP = System.getProperty("line.separator"); 
    433447 
    434         protected synchronized void generateStubJS(String stubClassName, File destDir) throws IOException, IntrospectionException, ClassNotFoundException { 
     448        protected synchronized void generateStubJS(String wsdlUri, String stubClassName, File destDir)  
     449                                                                        throws IOException, IntrospectionException, ClassNotFoundException,  
     450                                                                                   NoSuchFieldException, IllegalArgumentException,  
     451                                                                                   IllegalAccessException, XPathExpressionException,  
     452                                                                                   ParserConfigurationException, SAXException { 
    435453 
    436454                StringBuilder sb = new StringBuilder(); 
     
    478496                                sb.append("    var operationParam = new Packages." + operationParamType.getName() + "();")                                              .append(LINE_SEP); 
    479497                                sb.append("    var classLoader    = " + name4SOAPClientObject + ".getCurrentThreadClassLoader4SOAPClient();")   .append(LINE_SEP); 
    480                          
     498 
     499                                // WSDLより、Webサービスのパラメータクラスのプロパティ順を取得。 
     500                                // (∵SOAPClient#オペレーション()に指定した引数の順序(=arguments オブジェクト)とあわせるため) 
     501                                Field field4MyQName = operationParamType.getField("MY_QNAME"); 
     502                                QName myQName = (QName) field4MyQName.get(null); 
     503                                 
     504                                List<String> propNameList = getPropertyNameListFromWSDL(wsdlUri, myQName); 
     505                                Iterator<String> propNameIt = propNameList.iterator(); 
     506                                 
    481507                                // Webサービスのパラメータクラスを取得 
    482508                                int idx = 0; 
    483509                                Map<String, PropertyDescriptor> beanPropMap = JavaScriptUtility.getBeansPropertyMap(operationParamType); 
    484                                 Iterator<Map.Entry<String, PropertyDescriptor>> it = beanPropMap.entrySet().iterator(); 
    485          
    486                                 // PLAN SOAPClient#オペレーション()に指定した引数の順序(=arguments オブジェクト)と、Webサービスのパラメータクラスのプロパティ取得順が異なる場合は修正が必要。 
    487                                 // Axis2のCodeGenerationEngineで作成されるJavaStubクラス内のパラメータクラスは、 
    488                                 // WSDLの 「definitions/types/schema/element[@name=\"エレメント名\"]/*/sequence/*」 と 
    489                                 // 同じ順番でプロパティが生成されているので、現状はOK。 
    490                                 while(it.hasNext()){ 
    491                                         Map.Entry<String, PropertyDescriptor> entry = it.next(); 
     510 
     511                                while(propNameIt.hasNext()){ 
     512                                        String propName = propNameIt.next(); 
     513                                        PropertyDescriptor propDescriptor = beanPropMap.get(propName); 
    492514                                         
    493                                         PropertyDescriptor propDescriptor = entry.getValue(); 
     515                                        if(propDescriptor == null){ 
     516                                                throw new IllegalStateException("'" + propName + "' is not found in " + operationParamType.getName() + ". (MyQName=" + myQName + ", WSDL=" + wsdlUri + ")"); 
     517                                        } 
     518                                         
    494519                                        Method setter = propDescriptor.getWriteMethod(); 
    495520                                        if(setter == null){ 
    496521                                                continue; 
    497522                                        } 
    498          
     523 
    499524                                        sb.append(LINE_SEP); 
    500525                                        sb.append("    var jsArg_" + idx + "    = (arguments[" + idx + "] == undefined) ? null : arguments[" + idx + "];")      .append(LINE_SEP); 
     
    690715                } 
    691716        } 
     717 
     718        private static List<String> getPropertyNameListFromWSDL(String wsdlUrl, QName myQName)  
     719                                                throws ParserConfigurationException, IOException, XPathExpressionException, SAXException{ 
     720 
     721                List<String> list = new ArrayList<String>(); 
     722                 
     723                StringBuilder exp = new StringBuilder();  
     724                exp.append("//definitions/types/schema[@targetNamespace=\"" + myQName.getNamespaceURI() + "\"]"); 
     725                exp.append("/element[@name=\"" + myQName.getLocalPart() + "\"]/*/sequence/*"); 
     726                 
     727                URL url = new URL(wsdlUrl); 
     728                InputStream is = url.openStream(); 
     729 
     730                try{ 
     731                        DocumentBuilder builder = DocumentBuilderFactory.newInstance().newDocumentBuilder(); 
     732                        Document doc = builder.parse(is); 
     733                 
     734                        // XPathで取得 
     735                        XPathFactory factory = XPathFactory.newInstance(); 
     736                        XPath xpath = factory.newXPath(); 
     737                        XPathExpression expr = xpath.compile(exp.toString()); 
     738                        Object result = expr.evaluate(doc, XPathConstants.NODESET); 
     739                         
     740                        NodeList nodeList = (NodeList) result; 
     741                        for (int i = 0; i < nodeList.getLength(); i++) { 
     742                                Element elem = (Element)nodeList.item(i); 
     743                            NamedNodeMap namedNodeMap = elem.getAttributes(); 
     744                             
     745                            _logger.trace("{}", namedNodeMap.getNamedItem("name")); 
     746                                _logger.trace("{}", namedNodeMap.getNamedItem("type")); 
     747                                _logger.trace("{}", namedNodeMap.getNamedItem("minOccurs")); 
     748                                _logger.trace("{}", namedNodeMap.getNamedItem("nillable")); 
     749                                _logger.trace("{}", elem.getNodeName()); 
     750                                 
     751                                list.add(namedNodeMap.getNamedItem("name").getNodeValue()); 
     752                        } 
     753                         
     754                        if(list.size() == 0){ 
     755                                throw new IllegalStateException("Not found '" + myQName + "' element in WSDL(='" + wsdlUrl + "')."); 
     756                        } 
     757                         
     758                        return list; 
     759                } 
     760                finally{ 
     761                        if(is != null){ 
     762                                is.close(); 
     763                        } 
     764                } 
     765        } 
    692766         
    693767        /**