001 package railo.commons.io; 002 import javax.servlet.jsp.JspWriter; 003 import javax.servlet.jsp.tagext.BodyContent; 004 005 import railo.runtime.writer.BodyContentImpl; 006 import railo.runtime.writer.CFMLWriter; 007 import railo.runtime.writer.DevNullBodyContent; 008 009 /** 010 * Stack for the Body Content Objects 011 */ 012 public final class BodyContentStack { 013 014 private CFMLWriter base; 015 016 private final DevNullBodyContent nirvana=new DevNullBodyContent(); 017 private Entry current; 018 private final Entry root; 019 020 021 /** 022 * Default Constructor 023 */ 024 public BodyContentStack() { 025 current=new Entry(null,null); 026 root=current; 027 } 028 029 /** 030 * initialize the BodyContentStack 031 * @param rsp 032 */ 033 public void init(CFMLWriter writer) { 034 this.base=writer; 035 } 036 037 /** 038 * release the BodyContentStack 039 */ 040 public void release() { 041 this.base=null; 042 current=root; 043 current.body=null; 044 current.after=null; 045 current.before=null; 046 } 047 048 049 /** 050 * push a new BodyContent to Stack 051 * @return new BodyContent 052 */ 053 public BodyContent push() { 054 if(current.after==null) { 055 current.after=new Entry(current,new BodyContentImpl(current.body==null?(JspWriter)base:current.body)); 056 } 057 else { 058 current.after.doDevNull=false; 059 current.after.body.init(current.body==null?(JspWriter)base:current.body); 060 } 061 current=current.after; 062 return current.body; 063 } 064 065 /** 066 * pop a BodyContent from Stack 067 * @return BodyContent poped 068 */ 069 public JspWriter pop() { 070 if(current.before!=null) current=current.before; 071 return getWriter(); 072 } 073 074 /** 075 * set if actuell BodyContent is DevNull or not 076 * @param doDevNull 077 */ 078 public void setDevNull(boolean doDevNull) { 079 current.doDevNull=doDevNull; 080 } 081 082 /** 083 * @return returns actuell writer 084 */ 085 public JspWriter getWriter() { 086 if(!current.doDevNull) { 087 if(current.body!=null) return current.body; 088 return base; 089 } 090 return nirvana; 091 } 092 093 094 class Entry { 095 private Entry before; 096 private Entry after; 097 private boolean doDevNull=false; 098 private BodyContentImpl body; 099 private Entry(Entry before, BodyContentImpl body) { 100 this.before=before; 101 this.body=body; 102 } 103 104 } 105 106 /** 107 * @return returns DevNull Object 108 */ 109 public boolean getDevNull() { 110 return current.doDevNull; 111 } 112 113 /** 114 * @return returns DevNull Object 115 */ 116 public DevNullBodyContent getDevNullBodyContent() { 117 return nirvana; 118 } 119 120 /** 121 * @return Returns the base. 122 */ 123 public CFMLWriter getBase() { 124 return base; 125 } 126 127 }