001    /**
002     * Copyright (c) 2000-2012 Liferay, Inc. All rights reserved.
003     *
004     * This library is free software; you can redistribute it and/or modify it under
005     * the terms of the GNU Lesser General Public License as published by the Free
006     * Software Foundation; either version 2.1 of the License, or (at your option)
007     * any later version.
008     *
009     * This library is distributed in the hope that it will be useful, but WITHOUT
010     * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
011     * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
012     * details.
013     */
014    
015    package com.liferay.portal.tools;
016    
017    import com.liferay.portal.kernel.util.StringBundler;
018    import com.liferay.portal.kernel.util.StringUtil;
019    import com.liferay.portal.kernel.util.TextFormatter;
020    import com.liferay.portal.tools.comparator.JavaMethodComparator;
021    import com.liferay.portal.tools.servicebuilder.ServiceBuilder;
022    import com.liferay.portal.util.InitUtil;
023    
024    import com.thoughtworks.qdox.JavaDocBuilder;
025    import com.thoughtworks.qdox.model.JavaClass;
026    import com.thoughtworks.qdox.model.JavaMethod;
027    import com.thoughtworks.qdox.model.JavaParameter;
028    import com.thoughtworks.qdox.model.Type;
029    
030    import java.io.File;
031    import java.io.IOException;
032    
033    import java.util.Arrays;
034    import java.util.LinkedHashSet;
035    import java.util.Set;
036    import java.util.TreeSet;
037    
038    /**
039     * @author Brian Wing Shun Chan
040     */
041    public class CopyInterfaceBuilder {
042    
043            public static void main(String[] args) {
044                    InitUtil.initWithSpring();
045    
046                    if (args.length == 2) {
047                            new CopyInterfaceBuilder(args[0], args[1]);
048                    }
049                    else {
050                            throw new IllegalArgumentException();
051                    }
052            }
053    
054            public CopyInterfaceBuilder(String parentDir, String srcFile) {
055                    try {
056                            _copyInterface(parentDir, srcFile);
057                    }
058                    catch (Exception e) {
059                            e.printStackTrace();
060                    }
061            }
062    
063            private void _copyInterface(String parentDir, String srcFile)
064                    throws IOException {
065    
066                    JavaClass javaClass = _getJavaClass(parentDir, srcFile);
067    
068                    JavaMethod[] methods = javaClass.getMethods();
069    
070                    Arrays.sort(methods, new JavaMethodComparator());
071    
072                    StringBundler sb = new StringBundler();
073    
074                    // Package
075    
076                    sb.append("package ");
077                    sb.append(javaClass.getPackage().getName());
078                    sb.append(";");
079    
080                    // Imports
081    
082                    sb.append("[$IMPORTS$]");
083    
084                    // Class declaration
085    
086                    sb.append("public class Copy");
087                    sb.append(javaClass.getName());
088                    sb.append(" implements ");
089                    sb.append(javaClass.getName());
090                    sb.append(" {");
091    
092                    String varName = "_" + TextFormatter.format(
093                            javaClass.getName(), TextFormatter.I);
094    
095                    // Methods
096    
097                    Set<String> imports = new TreeSet<String>();
098    
099                    for (int i = 0; i < methods.length; i++) {
100                            JavaMethod javaMethod = methods[i];
101    
102                            String methodName = javaMethod.getName();
103    
104                            if (javaMethod.isPublic()) {
105                                    String returnValueName = javaMethod.getReturns().getValue();
106    
107                                    imports.add(returnValueName);
108    
109                                    sb.append("public ");
110                                    sb.append(javaMethod.getReturns().getJavaClass().getName());
111                                    sb.append(_getDimensions(javaMethod.getReturns()));
112                                    sb.append(" ");
113                                    sb.append(methodName);
114                                    sb.append("(");
115    
116                                    JavaParameter[] parameters = javaMethod.getParameters();
117    
118                                    for (int j = 0; j < parameters.length; j++) {
119                                            JavaParameter javaParameter = parameters[j];
120    
121                                            sb.append(javaParameter.getType().getJavaClass().getName());
122                                            sb.append(_getDimensions(javaParameter.getType()));
123                                            sb.append(" ");
124                                            sb.append(javaParameter.getName());
125                                            sb.append(", ");
126    
127                                            imports.add(javaParameter.getType().getValue());
128                                    }
129    
130                                    if (parameters.length > 0) {
131                                            sb.setIndex(sb.index() - 1);
132                                    }
133    
134                                    sb.append(")");
135    
136                                    Type[] thrownExceptions = javaMethod.getExceptions();
137    
138                                    Set<String> newExceptions = new LinkedHashSet<String>();
139    
140                                    for (int j = 0; j < thrownExceptions.length; j++) {
141                                            Type thrownException = thrownExceptions[j];
142    
143                                            newExceptions.add(thrownException.getJavaClass().getName());
144    
145                                            imports.add(thrownException.getValue());
146                                    }
147    
148                                    if (newExceptions.size() > 0) {
149                                            sb.append(" throws ");
150    
151                                            for (String newException : newExceptions) {
152                                                    sb.append(newException);
153                                                    sb.append(", ");
154                                            }
155    
156                                            sb.setIndex(sb.index() - 1);
157                                    }
158    
159                                    sb.append("{");
160    
161                                    if (!returnValueName.equals("void")) {
162                                            sb.append("return ");
163                                    }
164    
165                                    sb.append(varName);
166                                    sb.append(".");
167                                    sb.append(methodName);
168                                    sb.append("(");
169    
170                                    for (int j = 0; j < parameters.length; j++) {
171                                            JavaParameter javaParameter = parameters[j];
172    
173                                            sb.append(javaParameter.getName());
174                                            sb.append(", ");
175                                    }
176    
177                                    if (parameters.length > 0) {
178                                            sb.setIndex(sb.index() - 1);
179                                    }
180    
181                                    sb.append(");");
182                                    sb.append("}");
183                            }
184                    }
185    
186                    // Fields
187    
188                    sb.append("private ");
189                    sb.append(javaClass.getName());
190                    sb.append(" ");
191                    sb.append(varName);
192                    sb.append(";");
193    
194                    // Class close brace
195    
196                    sb.append("}");
197    
198                    // Imports
199    
200                    String content = sb.toString();
201    
202                    sb = new StringBundler(imports.size() * 3);
203    
204                    for (String importClass : imports) {
205                            if (importClass.equals("boolean") || importClass.equals("byte") ||
206                                    importClass.equals("double") || importClass.equals("float") ||
207                                    importClass.equals("int") || importClass.equals("long") ||
208                                    importClass.equals("short") || importClass.equals("void")) {
209    
210                                    continue;
211                            }
212    
213                            sb.append("import ");
214                            sb.append(importClass);
215                            sb.append(";");
216                    }
217    
218                    content = StringUtil.replace(content, "[$IMPORTS$]", sb.toString());
219    
220                    // Write file
221    
222                    File file = new File(
223                            parentDir + "/" +
224                                    StringUtil.replace(javaClass.getPackage().getName(), ".", "/") +
225                                            "/Copy" + javaClass.getName() + ".java");
226    
227                    ServiceBuilder.writeFile(file, content);
228            }
229    
230            private String _getDimensions(Type type) {
231                    String dimensions = "";
232    
233                    for (int i = 0; i < type.getDimensions(); i++) {
234                            dimensions += "[]";
235                    }
236    
237                    return dimensions;
238            }
239    
240            private JavaClass _getJavaClass(String parentDir, String srcFile)
241                    throws IOException {
242    
243                    String className = StringUtil.replace(
244                            srcFile.substring(0, srcFile.length() - 5), "/", ".");
245    
246                    JavaDocBuilder builder = new JavaDocBuilder();
247    
248                    builder.addSource(new File(parentDir + "/" + srcFile));
249    
250                    return builder.getClassByName(className);
251            }
252    
253    }