use of lucee.transformer.bytecode.statement.tag.TagOther in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method _propertyStatement.
private final Tag _propertyStatement(ExprData data, Body parent) throws TemplateException {
if (data.context != CTX_CFC || !data.srcCode.forwardIfCurrent("property "))
return null;
Position line = data.srcCode.getPosition();
TagLibTag tlt = CFMLTransformer.getTLT(data.srcCode, "property", data.config.getIdentification());
Tag property = new TagOther(data.factory, line, null);
addMetaData(data, property, IGNORE_LIST_PROPERTY);
boolean hasName = false, hasType = false;
int pos = data.srcCode.getPos();
String tmp = variableDec(data, true);
if (!StringUtil.isEmpty(tmp)) {
if (tmp.indexOf('.') != -1) {
property.addAttribute(new Attribute(false, "type", data.factory.createLitString(tmp), "string"));
hasType = true;
} else {
data.srcCode.setPos(pos);
}
} else
data.srcCode.setPos(pos);
// folgend wird tlt extra nicht uebergeben, sonst findet pruefung statt
Attribute[] attrs = attributes(property, tlt, data, SEMI, data.factory.NULL(), Boolean.FALSE, "name", true, NO_ATTR_SEP, false);
checkSemiColonLineFeed(data, true, true, false);
property.setTagLibTag(tlt);
property.setScriptBase(true);
Attribute attr;
// first fill all regular attribute -> name="value"
for (int i = attrs.length - 1; i >= 0; i--) {
attr = attrs[i];
if (!attr.getValue().equals(data.factory.NULL())) {
if (attr.getName().equalsIgnoreCase("name")) {
hasName = true;
} else if (attr.getName().equalsIgnoreCase("type")) {
hasType = true;
}
property.addAttribute(attr);
}
}
// now fill name named attributes -> attr1 attr2
String first = null, second = null;
for (int i = 0; i < attrs.length; i++) {
attr = attrs[i];
if (attr.getValue().equals(data.factory.NULL())) {
// type
if (first == null && ((!hasName && !hasType) || !hasName)) {
first = attr.getNameOC();
} else // name
if (second == null && !hasName && !hasType) {
second = attr.getNameOC();
} else // attr with no value
{
attr = new Attribute(true, attr.getName(), data.factory.EMPTY(), "string");
property.addAttribute(attr);
}
}
}
if (first != null) {
hasName = true;
if (second != null) {
hasType = true;
property.addAttribute(new Attribute(false, "name", data.factory.createLitString(second), "string"));
property.addAttribute(new Attribute(false, "type", data.factory.createLitString(first), "string"));
} else {
property.addAttribute(new Attribute(false, "name", data.factory.createLitString(first), "string"));
}
}
if (!hasType) {
property.addAttribute(new Attribute(false, "type", data.factory.createLitString("any"), "string"));
}
if (!hasName)
throw new TemplateException(data.srcCode, "missing name declaration for property");
/*Tag property=new TagBase(line);
property.setTagLibTag(tlt);
property.addAttribute(new Attribute(false,"name",data.factory.createLitString(name),"string"));
property.addAttribute(new Attribute(false,"type",data.factory.createLitString(type),"string"));
*/
property.setEnd(data.srcCode.getPosition());
return property;
}
use of lucee.transformer.bytecode.statement.tag.TagOther in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method createStaticTag.
public static TagOther createStaticTag(ExprData data, Position start) throws TemplateException {
TagLibTag tlt = CFMLTransformer.getTLT(data.srcCode, "static", data.config.getIdentification());
BodyBase body = new BodyBase(data.factory);
TagOther tag = new TagOther(data.factory, start, data.srcCode.getPosition());
tag.setTagLibTag(tlt);
tag.setBody(body);
data.ep.add(tlt, tag, data.flibs, data.srcCode);
return tag;
}
use of lucee.transformer.bytecode.statement.tag.TagOther in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method funcStatement.
/**
* Liest ein function Statement ein.
* <br />
* EBNF:<br />
* <code>identifier spaces "(" spaces identifier spaces {"," spaces identifier spaces} ")" spaces block;</code>
* @return function Statement
* @throws TemplateException
*/
private final Statement funcStatement(ExprData data, Body parent) throws TemplateException {
int pos = data.srcCode.getPos();
// read 5 tokens (returntype,access modifier,"abstract|final|static","function", function name)
String str = variableDec(data, false);
// if there is no token at all we have no function
if (str == null) {
data.srcCode.setPos(pos);
return null;
}
comments(data);
String[] tokens = new String[] { str, null, null, null, null };
tokens[1] = variableDec(data, false);
comments(data);
if (tokens[1] != null) {
tokens[2] = variableDec(data, false);
comments(data);
if (tokens[2] != null) {
tokens[3] = variableDec(data, false);
comments(data);
if (tokens[3] != null) {
tokens[4] = identifier(data, false);
comments(data);
}
}
}
// function name
String functionName = null;
for (int i = tokens.length - 1; i >= 0; i--) {
// first from right is the function name
if (tokens[i] != null) {
functionName = tokens[i];
tokens[i] = null;
break;
}
}
if (functionName == null || functionName.indexOf(',') != -1 || functionName.indexOf('[') != -1) {
data.srcCode.setPos(pos);
return null;
}
// throw new TemplateException(data.srcCode, "invalid syntax");
String returnType = null;
// search for "function"
boolean hasOthers = false, first = true;
for (int i = tokens.length - 1; i >= 0; i--) {
if ("function".equalsIgnoreCase(tokens[i])) {
// if it is the first "function" (from right) and we had already something else, the syntax is broken!
if (hasOthers && first)
throw new TemplateException(data.srcCode, "invalid syntax");
else // we already have a return type,so this is the 3th "function"!
if (returnType != null)
throw new TemplateException(data.srcCode, "invalid syntax");
else if (!first)
returnType = tokens[i];
first = false;
tokens[i] = null;
} else if (tokens[i] != null) {
hasOthers = true;
}
}
// no "function" found
if (first) {
data.srcCode.setPos(pos);
return null;
}
// access modifier
int _access, access = -1;
for (int i = 0; i < tokens.length; i++) {
if (tokens[i] != null && (_access = ComponentUtil.toIntAccess(tokens[i], -1)) != -1) {
// we already have an access modifier
if (access != -1) {
// we already have a return type
if (returnType != null)
throw new TemplateException(data.srcCode, "invalid syntax");
returnType = tokens[i];
} else
access = _access;
tokens[i] = null;
}
}
// no access defined
if (access == -1)
access = Component.ACCESS_PUBLIC;
// Non access modifier
int _modifier, modifier = Component.MODIFIER_NONE;
boolean isStatic = false;
for (int i = 0; i < tokens.length; i++) {
if (tokens[i] != null) {
_modifier = ComponentUtil.toModifier(tokens[i], Component.MODIFIER_NONE, Component.MODIFIER_NONE);
// abstract|final
if (_modifier != Component.MODIFIER_NONE) {
// we already have an Non access modifier
if (modifier != Component.MODIFIER_NONE || isStatic) {
// we already have a return type
if (returnType != null)
throw new TemplateException(data.srcCode, "invalid syntax");
returnType = tokens[i];
} else
modifier = _modifier;
tokens[i] = null;
} else // static
if (tokens[i].equalsIgnoreCase("static")) {
// we already have an Non access modifier
if (modifier != Component.MODIFIER_NONE || isStatic) {
// we already have a return type
if (returnType != null)
throw new TemplateException(data.srcCode, "invalid syntax");
returnType = tokens[i];
} else
isStatic = true;
tokens[i] = null;
}
}
}
// return type
for (int i = 0; i < tokens.length; i++) {
if (tokens[i] != null) {
if (returnType != null)
throw new TemplateException(data.srcCode, "invalid syntax");
returnType = tokens[i];
}
}
Position line = data.srcCode.getPosition();
// Name
if (!data.isCFC && !data.isInterface) {
FunctionLibFunction flf = getFLF(data, functionName);
try {
if (flf != null && flf.getFunctionClassDefinition().getClazz() != CFFunction.class) {
PageSource ps = null;
if (data.srcCode instanceof PageSourceCode) {
ps = ((PageSourceCode) data.srcCode).getPageSource();
}
String path = null;
if (ps != null) {
path = ps.getDisplayPath();
path = path.replace('\\', '/');
}
if (// TODO make better
path == null || path.indexOf("/library/function/") == -1)
throw new TemplateException(data.srcCode, "The name [" + functionName + "] is already used by a built in Function");
}
} catch (Throwable t) {
ExceptionUtil.rethrowIfNecessary(t);
throw new PageRuntimeException(Caster.toPageException(t));
}
}
Function res = closurePart(data, functionName, access, modifier, returnType, line, false);
if (isStatic) {
if (data.context == CTX_INTERFACE)
throw new TemplateException(data.srcCode, "static functions are not allowed within the interface body");
TagOther tag = createStaticTag(data, res.getStart());
tag.getBody().addStatement(res);
return tag;
}
return res;
}
use of lucee.transformer.bytecode.statement.tag.TagOther in project Lucee by lucee.
the class AbstrCFMLScriptTransformer method staticStatement.
private final Tag staticStatement(ExprData data, Body parent) throws TemplateException {
if (!data.srcCode.forwardIfCurrent("static", '{'))
return null;
// get one back to have again { so the parser works
data.srcCode.previous();
Position start = data.srcCode.getPosition();
TagOther tag = createStaticTag(data, start);
statement(data, tag.getBody(), CTX_STATIC);
return tag;
}
Aggregations