195 lines
6.1 KiB
Java
Executable File
195 lines
6.1 KiB
Java
Executable File
package pyUML.backend;
|
|
|
|
import java.io.BufferedWriter;
|
|
import java.io.File;
|
|
import java.io.FileWriter;
|
|
import java.io.IOException;
|
|
|
|
import org.eclipse.core.resources.IFile;
|
|
import org.eclipse.core.resources.IProject;
|
|
import org.eclipse.jface.dialogs.MessageDialog;
|
|
import org.eclipse.uml2.uml.Classifier;
|
|
import org.eclipse.uml2.uml.Model;
|
|
import org.python.pydev.parser.jython.ast.Name;
|
|
import org.python.pydev.parser.jython.ast.Num;
|
|
import org.python.pydev.parser.jython.ast.Str;
|
|
import org.python.pydev.parser.jython.ast.exprType;
|
|
|
|
import pyUML.pythonTree.PythonTreeFile;
|
|
import pyUML.pythonTree.PythonTreePackage;
|
|
import pyUML.pythonTree.PythonTreeRoot;
|
|
|
|
/**
|
|
* Some Helper methods needed for parsing Pything Code
|
|
* and handling the Python Abstract Syntax Tree
|
|
*/
|
|
public class ParseHelpers {
|
|
|
|
/**
|
|
* Reads out a file and returns the file content as a string
|
|
*
|
|
* @param file the file to read
|
|
* @return a String representing the file's content
|
|
* null on Error
|
|
*/
|
|
public static String fileToString(File file, IProject project) {
|
|
IFile iFile = EclipseHelperMethods.createFile(file.getAbsolutePath(), project);
|
|
return EclipseHelperMethods.iFileToString(iFile);
|
|
}
|
|
|
|
/**
|
|
* (Re-)Writes a string to a file and updates the file in the project,
|
|
* if the project is != null
|
|
* @param file the file to write to
|
|
* @param str the String to write to the File
|
|
* @param project (optional) the project where the file is located in
|
|
*/
|
|
public static void stringToFile(File file, String str, IProject project) {
|
|
try {
|
|
file.createNewFile();
|
|
BufferedWriter writer = new BufferedWriter(new FileWriter(file));
|
|
writer.write(str);
|
|
writer.close();
|
|
EclipseHelperMethods.updateFile(file.getAbsolutePath(), project);
|
|
}catch (IOException e) {
|
|
MessageDialog.openError(null, "IOException",
|
|
"Error writing to file "+ file.getPath());
|
|
e.printStackTrace();
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Extracts a String representation of a python expression,
|
|
* if the expression is of type String or Num.
|
|
* The quotes of Strings are preserved
|
|
*
|
|
* @param expr The Python AST expression
|
|
* @param fileContent the content of the file where the expression
|
|
* is to be read
|
|
* @param attribute if true, expressions other than Strings or numbers are
|
|
* read by just reading the pure file content to the end of the line
|
|
* (or to a # sign). This works ONLY for attributes, not for expressions in
|
|
* function definitions.
|
|
* @param abbreviate if true, long values are abbreviated; at the end "(...)"
|
|
* is appended
|
|
* @param ONLY if this reads an attribute value: the value of the next line
|
|
* (needed to read multi-line attributes)
|
|
* if this is no attribute, this value is ignored.
|
|
*
|
|
* @return The String representation of this expression, null if expr is null
|
|
*/
|
|
public static String getStringOfExpr(exprType expr, PythonTreeFile pyFile, boolean attribute, boolean abbreviate, int nextLine){
|
|
if (expr == null)
|
|
return null;
|
|
|
|
String exprString;
|
|
if (expr instanceof Str) {
|
|
Str defaultValStr = (Str) expr;
|
|
exprString = defaultValStr.s;
|
|
if (defaultValStr.type == Str.SingleDouble) {
|
|
exprString = "\"" + exprString + "\"";
|
|
}
|
|
else if (defaultValStr.type == Str.SingleSingle) {
|
|
exprString = "'" + exprString + "'";
|
|
}
|
|
} else if (expr instanceof Name) {
|
|
Name defaultValNum = (Name) expr;
|
|
exprString = defaultValNum.id;
|
|
} else if (expr instanceof Num) {
|
|
Num defaultValNum = (Num) expr;
|
|
exprString = defaultValNum.num;
|
|
} else if (attribute){
|
|
exprString = readExprAsText(expr, pyFile, nextLine);
|
|
} else {
|
|
return GlobalConstants.getUnknownExpression();
|
|
}
|
|
|
|
// cut default value, if it is too long
|
|
if (abbreviate && exprString.length() > 19) {
|
|
exprString = exprString.substring(0,14) + "(...)";
|
|
}
|
|
|
|
return exprString;
|
|
}
|
|
|
|
/**
|
|
* Helper method for getStringOfExpr()
|
|
* Can read a multi-line-expression of an attribute
|
|
*
|
|
* @param expr
|
|
* @param pyFile
|
|
* @param nextLine
|
|
* @return
|
|
*/
|
|
public static String readExprAsText(exprType expr, PythonTreeFile pyFile, int nextLine) {
|
|
String[] lines = pyFile.getSplittedFileContent();
|
|
String exprString = lines[expr.beginLine-1];
|
|
exprString = exprString.substring(exprString.indexOf("=")+1);
|
|
exprString = exprString.replaceAll("^[\\s]*","");
|
|
exprString = exprString.replaceAll(" # created by PyUML.*$", "");
|
|
|
|
exprString = exprString.replaceAll("[\\s]*$", "");
|
|
|
|
for (int i=expr.beginLine; i < nextLine - 1; i++) {
|
|
String line = lines[i];
|
|
|
|
// docString comments of static attributes have a wrong "beginLine" value
|
|
// -> manually define here to ignore docStrings!
|
|
if (line.matches("^[\\s]*\"\"\".*"))
|
|
break;
|
|
line = line.replaceAll("# created by PyUML.*$", "");
|
|
line = " " +line.replaceAll("^[\\s]*", "");
|
|
exprString += line;
|
|
exprString = exprString.replaceAll("[\\s]*$", "");
|
|
}
|
|
|
|
// if there are called other classes/packages, the index
|
|
// is on the value, not on the "a.b.c"-prefix.
|
|
// if that's the case, add the prefix afterwards:
|
|
|
|
return exprString;
|
|
}
|
|
|
|
/**
|
|
* Simple method to extract the XMI-ID out of a line
|
|
* containing the PyUML string "# PyUML: XMI_ID: ..."
|
|
* @param content
|
|
* @return
|
|
*/
|
|
public static String extractXmiFromString(String content) {
|
|
String xmi_id = null;
|
|
String[] lines = content.split("\n");
|
|
for (String line : lines) {
|
|
if (line.matches("\\s*# PyUML:.*")) {
|
|
String[] splittedLine = line.split("XMI_ID:");
|
|
if (splittedLine.length == 2) {
|
|
xmi_id = splittedLine[1];
|
|
}
|
|
}
|
|
}
|
|
return xmi_id;
|
|
}
|
|
|
|
|
|
/**
|
|
* This creates a string containing the model package structure as
|
|
* "/packSup/packSub/" , where the last package contains the
|
|
* current class.
|
|
* @param cl The class in the model to find the package structure for
|
|
* @return a string containing the parent package structure
|
|
* of this class
|
|
*
|
|
*/
|
|
public static String getModelPackageStructure(org.eclipse.uml2.uml.Type cl) {
|
|
org.eclipse.uml2.uml.Package pack = cl.getPackage();
|
|
String structure = "";
|
|
while (! (pack instanceof Model))
|
|
{
|
|
structure = "/"+pack.getName() + structure ;
|
|
pack = pack.getNestingPackage();
|
|
}
|
|
|
|
return structure + "/";
|
|
}
|
|
}
|