解読する<br>ソース


<c:out>タブは、ページで属性値を出力するためのもので、<c:out>を使用する場合、JSPページでは、以下のように宣言されます.
<%@taglib prefix="c"uri=「http://java.sun.com/jsp/jstl/core「%>
このラベルのc.tldファイルでは、outラベルについて以下のように定義されています.
 
coreラベルライブラリの説明:
  JSTL 1.1 core library  JSTL core  1.1  c 
 
outラベルの説明は以下の通りです.
<<>    out    org.apache.taglibs.standard.tag.tag.co re.OutTag//ラベルの処理類                value              //属性に対応する名称は、上のクラスが提供するsetterと一致します.        true       //この属性を提供する必要があるかどうかを示します.        <この属性値は運転時に決定できるという意味です.                >default        false        true                escapeXml        false        true       
org.apache.taglibs.standard.tag.rt.co re.OutTagのソースコードは以下の通りです.
package org.apache.taglibs.standard.tag.rt.core;

import org.apache.taglibs.standard.tag.common.core.OutSupport;

public class OutTag extends OutSupport {       
    // for tag attribute
    public void setValue(Object value) {   //            value    (  ),       
        this.value = value; //value         ,     value     
    }
      
    // for tag attribute
    public void setDefault(String def) {  //  
        this.def = def;    //def         ,     default     
    }
        
    // for tag attribute
    public void setEscapeXml(boolean escapeXml) {  //  
        this.escapeXml = escapeXml; //  ,     escapeXml    
    }
}
 OutTag類はOutSupport類を継承しています.OutSupport類のソースは以下の通りです.
package org.apache.taglibs.standard.tag.common.core;

import java.io.IOException;
import java.io.Reader;

import javax.servlet.jsp.JspException;
import javax.servlet.jsp.JspWriter;
import javax.servlet.jsp.PageContext;
import javax.servlet.jsp.tagext.BodyTagSupport;

public class OutSupport extends BodyTagSupport {

    protected Object value;                     // tag attribute
    protected String def;	            // tag attribute
    protected boolean escapeXml;          // tag attribute
    private boolean needBody;                // non-space body needed?

    public OutSupport() {
        super();
        init();
    }

    // resets local state
    private void init() {
        value = def = null;
        escapeXml = true;
        needBody = false;
    }

    // Releases any resources we may have (or inherit)
    public void release() {
        super.release();
        init();
    }

     //          
      public int doStartTag() throws JspException {

      needBody = false;	// reset state related to 'default'
      this.bodyContent = null;
      
      try {
	// print value if available; otherwise, try 'default'
	if (value != null) {  //  value    null
                    out(pageContext, escapeXml, value); //  value       
	    return SKIP_BODY; //       
	} else {
	    // if we don't have a 'default' attribute, just go to the body
	    if (def == null) { //  value  , def  (     default )
		needBody = true; //       
		return EVAL_BODY_BUFFERED;//     
	    }

	    // if we do have 'default', print it
	    if (def != null) { //     default  
               	                out(pageContext, escapeXml, def);  //      def     
	    }
	    return SKIP_BODY; //       
	}
      } catch (IOException ex) {
	throw new JspException(ex.toString(), ex);
      }
    }
     //          	
      public int doEndTag() throws JspException {
      try {
	if (!needBody)
	    return EVAL_PAGE;

	// trim and print out the body
	if (bodyContent != null && bodyContent.getString() != null)
            out(pageContext, escapeXml, bodyContent.getString().trim());
	return EVAL_PAGE;
      } catch (IOException ex) {
	throw new JspException(ex.toString(), ex);
      }
    }


    public static void out(PageContext pageContext,
                           boolean escapeXml,
                           Object obj) throws IOException {
        JspWriter w = pageContext.getOut();//            
	if (!escapeXml) { //escapeXml false,            xml    
            // write chars as is
            if (obj instanceof Reader) { //         Reader ,                
           Reader reader = (Reader)obj; 
                char[] buf = new char[4096];
                int count;
                while ((count=reader.read(buf, 0, 4096)) != -1) {
                    w.write(buf, 0, count); //  
                }
            } else {
                w.write(obj.toString()); //     ,         
            }
        } else {  //escapeXml true,           xml    ( : <   &lt,>   &gt )
            // escape XML chars
            if (obj instanceof Reader) {
                Reader reader = (Reader)obj;
                char[] buf = new char[4096];
                int count;
                while ((count = reader.read(buf, 0, 4096)) != -1) {
                    writeEscapedXml(buf, count, w); //  
                }
            } else {
                String text = obj.toString();
                writeEscapedXml(text.toCharArray(), text.length(), w); //  
             }
        }
    }
   //        xml    (<,>,",',&)
    private static void writeEscapedXml(char[] buffer, int length, JspWriter w) throws IOException{
        int start = 0; //                  

        for (int i = 0; i < length; i++) {
            char c = buffer[i];
            if (c <= Util.HIGHEST_SPECIAL) { //     ASCII     HIGHEST_SPECIAL=Ox3e, > ASCII 
                char[] escaped = Util.specialCharactersRepresentation[c]; //         	
                if (escaped != null) {//     ,      
                    // add unescaped portion
                              if (start < i) { //             
                        w.write(buffer,start,i-start);
                             }
                    // add escaped xml
                    w.write(escaped); //             
                    start = i + 1; //            
                }
            }
        }
        // add rest of unescaped portion
        if (start < length) {
            w.write(buffer,start,length-start);
        }
    }
}
     例:
<% 
	// Reader  
	String str = "Hello String";
	request.setAttribute("str",str);
	//Reader  
	Reader reader = new CharArrayReader("Hello Reader".toCharArray());
	request.setAttribute("reader",reader);
%>
<c:out value="${requestScope.str}"/> //Hello String
<c:out value="${requestScope.reader}" /> //Hello Reader

<c:out value="${requestScope.str}" default="defalut value"/> //Hello String
<c:out value="${null}" default="default value"/> //default value
<c:out value="${null}" >default body content value</c:out> //default body content value 

<c:out value="<b>Hello</b>"/> //<b>Hello</b>
<c:out value="<b>Hello</b>" escapeXml="true"/> //<b>Hello</b>
<c:out value="<b>Hello</b>" escapeXml="false"/> //   Hello
<c:out value="${null}" escapeXml="true" default="<b>Hello</b>"/> //<b>Hello</b>
<c:out value="${null}" escapeXml="false" default="<b>Hello</b>"/> //   Hello
<c:out value="${null}" escapeXml="false"><b>Hello</b></c:out>//   Hello
<c:out value="${null}" escapeXml="true"><b>Hello</b></c:out>//<b>Hello</b>