001 package railo.transformer.bytecode.statement.tag; 002 003 import java.util.HashMap; 004 import java.util.Iterator; 005 import java.util.List; 006 import java.util.Map; 007 008 import railo.runtime.type.util.ComponentUtil; 009 import railo.transformer.bytecode.Body; 010 import railo.transformer.bytecode.BodyBase; 011 import railo.transformer.bytecode.BytecodeContext; 012 import railo.transformer.bytecode.BytecodeException; 013 import railo.transformer.bytecode.Statement; 014 import railo.transformer.bytecode.expression.ExprString; 015 import railo.transformer.bytecode.expression.Expression; 016 import railo.transformer.bytecode.literal.LitBoolean; 017 import railo.transformer.bytecode.literal.LitString; 018 import railo.transformer.bytecode.statement.Function; 019 import railo.transformer.bytecode.statement.IFunction; 020 021 public final class TagFunction extends TagBase implements IFunction { 022 023 private static final ExprString ANY = LitString.toExprString("any", -1); 024 025 private static final Expression PUBLIC = LitString.toExprString("public",-1); 026 027 private static final Expression EMPTY = LitString.toExprString("", -1); 028 029 public TagFunction(int startline) { 030 this(startline,-1); 031 } 032 033 public TagFunction(int startline,int endline) { 034 super(startline,endline); 035 036 } 037 038 /** 039 * @see railo.transformer.bytecode.statement.IFunction#writeOut(railo.transformer.bytecode.BytecodeContext, int) 040 */ 041 public void writeOut(BytecodeContext bc, int type) throws BytecodeException { 042 //ExpressionUtil.visitLine(bc, getStartLine()); 043 _writeOut(bc,type); 044 //ExpressionUtil.visitLine(bc, getEndLine()); 045 } 046 047 /** 048 * @see railo.transformer.bytecode.statement.tag.TagBase#_writeOut(railo.transformer.bytecode.BytecodeContext) 049 */ 050 public void _writeOut(BytecodeContext bc) throws BytecodeException { 051 _writeOut(bc,Function.PAGE_TYPE_REGULAR); 052 } 053 054 public void _writeOut(BytecodeContext bc, int type) throws BytecodeException { 055 Body functionBody = new BodyBase(); 056 Function func = createFunction(functionBody); 057 func.setParent(getParent()); 058 059 List statements = getBody().getStatements(); 060 Statement stat; 061 Tag tag; 062 Iterator it = statements.iterator(); 063 while (it.hasNext()) { 064 stat = (Statement) it.next(); 065 if (stat instanceof Tag) { 066 tag = (Tag) stat; 067 if (tag.getTagLibTag().getTagClassName().equals( 068 "railo.runtime.tag.Argument")) { 069 addArgument(func, tag); 070 continue; 071 } 072 } 073 functionBody.addStatement(stat); 074 } 075 ; 076 func._writeOut(bc,type); 077 078 } 079 080 private void addArgument(Function func, Tag tag) { 081 Attribute attr; 082 // name 083 Expression name = tag.removeAttribute("name").getValue(); 084 085 // type 086 attr = tag.removeAttribute("type"); 087 Expression type = (attr == null) ? ANY : attr.getValue(); 088 089 // required 090 attr = tag.removeAttribute("required"); 091 Expression required = (attr == null) ? LitBoolean.FALSE : attr 092 .getValue(); 093 094 // default 095 attr = tag.removeAttribute("default"); 096 Expression defaultValue = (attr == null) ? null : attr.getValue(); 097 098 // passby 099 attr = tag.removeAttribute("passby"); 100 LitBoolean passByReference = LitBoolean.TRUE; 101 if(attr!=null) { 102 // i can cast irt to LitString because he evulator check this before 103 String str = ((LitString)attr.getValue()).getString(); 104 if(str.trim().equalsIgnoreCase("value")) 105 passByReference=LitBoolean.FALSE; 106 } 107 108 109 // displayname 110 attr = tag.removeAttribute("displayname"); 111 Expression displayName = (attr == null) ? EMPTY : attr.getValue(); 112 113 // hint 114 attr = tag.removeAttribute("hint"); 115 if (attr == null) 116 attr = tag.removeAttribute("description"); 117 118 Expression hint; 119 if(attr == null)hint=EMPTY; 120 else hint=attr.getValue(); 121 122 func.addArgument(name, type, required, defaultValue, passByReference,displayName, hint,tag.getAttributes()); 123 124 } 125 126 private Function createFunction(Body body) throws BytecodeException { 127 Attribute attr; 128 129 // name 130 Expression name = removeAttribute("name").getValue(); 131 /*if(name instanceof LitString) { 132 ((LitString)name).upperCase(); 133 }*/ 134 // return 135 attr = removeAttribute("returntype"); 136 // if(attr==null) attr = getAttribute("return"); 137 // if(attr==null) attr = getAttribute("type"); 138 Expression returnType = (attr == null) ? ANY : attr.getValue(); 139 140 // output 141 attr = removeAttribute("output"); 142 Expression output = (attr == null) ? LitBoolean.TRUE : attr.getValue(); 143 144 // abstract 145 attr = removeAttribute("abstract"); 146 Expression abstr = (attr == null) ? LitBoolean.FALSE : attr.getValue(); 147 148 // access 149 attr = removeAttribute("access"); 150 Expression access = (attr == null) ? PUBLIC : attr.getValue(); 151 152 // dspLabel 153 attr = removeAttribute("displayname"); 154 Expression displayname = (attr == null) ? EMPTY : attr.getValue(); 155 156 // hint 157 attr = removeAttribute("hint"); 158 Expression hint = (attr == null) ? EMPTY : attr.getValue(); 159 160 // description 161 attr = removeAttribute("description"); 162 Expression description = (attr == null) ? EMPTY : attr.getValue(); 163 164 // returnformat 165 attr = removeAttribute("returnformat"); 166 Expression returnFormat = (attr == null) ? null : attr.getValue(); 167 168 // secureJson 169 attr = removeAttribute("securejson"); 170 Expression secureJson = (attr == null) ? null : attr.getValue(); 171 172 // verifyClient 173 attr = removeAttribute("verifyclient"); 174 Expression verifyClient = (attr == null) ? null : attr.getValue(); 175 176 String strAccess = ((LitString)access).getString(); 177 int acc = ComponentUtil.toIntAccess(strAccess,-1); 178 if(acc==-1) 179 throw new BytecodeException("invalid access type ["+strAccess+"], access types are remote, public, package, private",getLine()); 180 181 Function func = new Function(name, returnType,returnFormat, output,abstr, acc, displayname,description, 182 hint,secureJson,verifyClient, body, getStartLine(),getEndLine()); 183 184 // %**% 185 Map attrs = getAttributes(); 186 Iterator it = attrs.entrySet().iterator(); 187 HashMap<String,Attribute> metadatas=new HashMap<String,Attribute>(); 188 while(it.hasNext()){ 189 attr=(Attribute) ((Map.Entry)it.next()).getValue(); 190 metadatas.put(attr.getName(),attr); 191 } 192 func.setMetaData(metadatas); 193 return func; 194 } 195 196 }