⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 57.html

📁 写给JSP初级程序员的书
💻 HTML
📖 第 1 页 / 共 2 页
字号:
     // 获得现有的 loan
  }
  // Sync the Loan object values to values in the submitted form.
  ltTrans.syncModelToGui(lnTheLoan);

  // 确保未出现任何错误
  if (ltTrans.hasErrors() == false)
  {
    // 提交 Loan 信息,然后将重定向设置为正确的尾随页
    sRedirect = LOAN_CONFIRMATION;
  }

  // 将网站访问者重定向为当前工资。
try  {
    response.sendRedirect(sRedirect);
  }
  catch (Exception e)
  {
    // 错误逻辑
  }
}
</pre></td></tr><P>servlet 的主要用途是控制 JSP 文件之间的导航流以及对业务对象执行持久化。此 servlet 的代码很简单。 
<ul>
	<li>servlet 执行的第一个操作就是从 <code>HttpServletRequest</code> 中获取 <code>Translator</code> 对象的一个实例。</li> 
	<li>随后 servlet 使用 <code>processForm()</code> 方法将对所提交的 HTML 表单的处理委派给 <code>Translator</code>。</li> 

	<li>在 <code>Translator</code> 分析表单之后,servlet 将确定是否需要从第二存储中创建或检索业务对象(示例中的 <code>Loan</code>)。</li> 

	<li>在 servlet 拥有业务对象的一个实例之后,servlet 就会调用 <code>Translator</code> 对象的 <code>syncModelToGui()</code>。<code>syncModelToGui()</code> 随后将网站访问者提交的全部值转换为业务对象可识别的值。</li> 

	<li>在 <code>Translator</code> 完成值的同步之后,servlet 将检查当试图转换网站访问者输入的值时,<code>Translator</code> 是否记录了任何错误。 
	<ul><li>如果没有记录任何错误,servlet 就会将网站访问者重定向到确认页(通常是另一个 JSP 文件,它同样能显示来自 <code>Translator</code> 的值)。</li> 
	<li>如果记录了错误,servlet 就将网站访问者重定向到输入表单,这样他就可以修正错误。</li></ul></li></ul> 

<p><b><code>Translator</code> 对象</b><br>
因为 <code>Translator</code> 对象是 JSP 文件、servlet 和业务对象之间的联系纽带,所以要求它是有状态的,并且要求它在 HTTP 请求(或线程)之间维护状态。为了符合这个标准,<code>Translator</code> 对象需要起到类似伪孤子 (pseudo singleton) 那样的作用。<code>Translator</code> 类有五个主要部分,另外还有一个前面未曾提及的 <code>Object Translator</code> 类库。 
<ul>
       <LI> <code>getInstance()</code></LI>
	<LI><code>syncGuiToModel()</code></LI>
	<LI>若干 getter 方法</LI> 
	<LI><code>processForm()</code></LI>
	<LI><code>syncModelToGui()</code></LI>
	<LI><code>Object Translators</code> 库</LI> 
</ul>

<P>为了调用 <code>Translator</code> 对象的一个实例,调用程序必须调用静态方法 <code>getInstance(HttpServletRequest)</code>。<code>getInstance()</code> 方法将确定是否应返回 <code>Translator</code> 的一个新实例,或者是否应从 <code>HttpSession</code> 中重用某个实例。该方法通过查看定制参数 <code>action</code> 来实现这一点。此参数是随 HTTP 请求(例如,<code>http://localhost/registerLoan.jsp?action=new</code>)一起传递的。下面的样例代码段显示了 <code>getInstance()</code> 的内容:</P> 

<tr><td><pre>public static LoanRegistrationTranslator getInstance(HttpServletRequest request)
{
   // 声明返回值变量。
   LoanRegistrationTranslator lrtRV = null;

   // HttpSession 是必需的,因此在此处将它提取出来。
   HttpSession session = request.getSession();

   // 从 request 对象中检索 action 参数。
   String sAction = parseString(request, ACTION);

   // 确定我们要返回哪种 Translator。
   if (ACTION_PROCESS.equals(sAction) == true)
   {
      // 因为 action 参数被设置为 process,这表示我们正在处理一个现有的
      // Translator,所以从 HttpSession 中将这个 translator 提取出来。
      lrtRV = (LoanRegistrationTranslator)
         session.getValue(HttpSessionValueKeys.LOAN_REGISTRATION_TRANSLATOR);
   }
   else if (sAction == null || &quot;&quot;.equals(sAction) == true ||
            ACTION_NEW.equals(sAction) == true)
   {
      // 由于未设置或根本未传递 action,所以缺省操作是创建一个新的 translator。
      // 另一种可能是 action 为 &quot;new&quot;
      lrtRV = new LoanRegistrationTranslator();
      session.putValue(HttpSessionValueKeys.LOAN_REGISTRATION_TRANSLATOR, lrtRV);
   }
else
   {
      // 由于 action 不满足前面的任何检查,即 action 值是位于辅助存储器中的
      // 一个现有 Loan 的 ID,所以这次创建一个 LoanRegistrationTranslator,
      // 其值被预设为已保存的 loan 中的值。
      lrtRV = new LoanRegistrationTranslator(sAction);
      session.putValue(HttpSessionValueKeys.LOAN_REGISTRATION_TRANSLATOR, lrtRV);
   }

   // 返回 Translator 对象的一个实例。
   return lrtRV;
}</pre></td></tr><P>对于要在 JSP 文件中显示的每个业务对象值,<code>Translator</code> 都提供了一个 getter 方法。这些 getter 方法由 JSP 文件调用。必须在 JSP 文件中显示的每个业务对象属性都有一个 getter 方法。getter 方法总是返回一个 <code>String</code>。返回的 <code>String</code> 值已被预先格式化,以便直接在 JSP 文件中显示。预先格式化 <code>String</code> 是为了使 JSP 文件中的 Java 代码尽可能少。对这些值的格式化改为在 <code>syncGuiToModel()</code> 中进行。</P> 

<P><code>Translator</code> 使用 <code>processForm()</code> 清除以前显示的错误,并从提交的表单中分析此信息。当 servlet 接收到一个提交的表单时,它就会将对该表单的处理委托给 <code>Translator</code>。在本委托期间,<code>Translator</code> 分析提交表单的值,并将这些值分别存储在 <code>String</code> 变量中。这些存储变量随后通过 <code>syncModelToGui()</code>(由 servlet 调用)转换为业务对象的值。</P> 

<P><code>syncGuiToModel()</code> 和 <code>syncModelToGui()</code> 是两个类似的方法,顾名思义,其中一个方法按某个方向对值执行同步,而另一个方法按相反的方向执行同步。<code>syncGuiToModel()</code> 从业务对象的属性中提取这些值,并使用 <code>Object Translator</code> 预先格式化每个属性值。<code>Object Translator</code> 将值预先格式化为要在屏幕上显示的值。随后,它将 <code>Translator</code> 的对应 <code>String</code> 变量设置为这个值。<code>syncModelToGui()</code> 执行的操作相同,但方向相反。下面是从典型的 <code>syncGuiToModel()</code> 中摘出的一小段代码:</P> 

<P><tr><td><pre>DoubleTranslator dtDouble = new DoubleTranslator();
String sTemp = dtDouble.translate(loan.getInterestRate());
setInterestRate(sTemp);</pre></td></tr><P>为了使转换代码具有最大的可重用性,并为整个站点提供一种共同的转换,<code>syncGuiToModel()</code> 和 <code>syncModelToGui()</code> 使用的都是 <code>Object Translator</code> 类。<code>Object Translators</code> 与 <code>Translator</code> 对象联系得如此紧密,以致于几乎可将它们看作是 <code>Translator</code> 对象的规则。<code>Object Translator</code> 类是一个简单的类,它的唯一用途就是将一种数据类型转换为格式化字符串,以及将格式化字符串转换为它的数据类型。下面是一个很简单的 <code>Object Translator</code> 类的代码:</P> 

<tr><td><pre>public class DoubleTranslator extends ObjectTranslator
{
   public String translate(double doubleValue)
   {
      return Double.toString(doubleValue);
   }

   public double translate(String stringToBeTranslated) throws Exception
   {
      double dRV = 0.0;

try      {
         Double dbDouble = Double.valueOf(stringToBeTranslated);
         dRV = dbDouble.doubleValue();
      }
      catch(Exception e)
      {
         Exception eTranslation =
           new Exception(&quot;Please enter a numeric value like 1.0 or 1.25&quot;);
         throw eTranslation;
      }

      return dRV;
   }
}</pre></td></tr><P>当这个样例 <code>Object Translator</code> 将 <code>double</code> 转换为格式化的 <code>String</code> 时,它只需调用 <code>Double.toString()</code>。这个方法可实现更强大的功能,例如,可以添加几行代码,使得当格式化类似 <code>1000.25</code> 这样的大 <code>double</code> 值时,可预格式化这个值,以便显示为 <code>1,000.25</code>。</P> 

<P>对于 <code>DoubleTranslator.translate(String)</code>,须注意的重要一点是,它会发出一个可读性很好的异常,而不是标准的 <code>Java.lang.NumberFormatException</code> 异常。JSP 文件将此异常的消息直接显示给网站访问者,因此,让网站的普通访问者很容易地理解该方法发出的异常是非常重要的。</P> 

<a name="4"></a><p><strong class="subhead">小结</strong><br>
使用 <code>Translator</code> 模式框架的优点很多,不仅可以降低网站的成本,而且可以提高用户的满意度。由于不同组件都只执行专门的任务,因而网站的构建成本降低了。这些专门任务分配给生产小组,如 HTML 小组或 Java 程序员小组。因为 <code>Translator</code> 模式的 <code>ObjectTranslators</code> 在整个网站重用,所有全部格式化和分析都是以相同的方式进行的。因为每项任务都以相同的方式完成,所以网站访问者就能够以一致的方式查看整个网站的信息。这进一步提高了用户的满意度。</p>

<a name="resources"><p><strong class="subhead">参考资源</strong>
<ul>
<!-- <li>下载本文所用示例的<a href="http://www.chinajavaworld.com/doc/lang/sourcecode.zip">源代码</a>。</li> -->
<li>下面的 developerWorks 教程可帮助您进一步了解 servlet 和 JSP 文件:<ul>
	<li><a href="http://www-105.ibm.com/developerWorks/education.nsf/java-onlinecourse-bytitle/0EE353D3449DB625862569530047CD1A?OpenDocument">Building Java HTTP servlets</a></li>
	<li><a href="http://www-105.ibm.com/developerWorks/education.nsf/java-onlinecourse-bytitle/80CC54124F0ABE25862569B300554AFB?OpenDocument">Building servlets with session tracking</a></li>
	<li><a href="http://www-105.ibm.com/developerWorks/education.nsf/java-onlinecourse-bytitle/882707E838C672A185256770004BDE72?OpenDocument">Introduction to JavaServer Pages technology</a></li>

	</ul></li>
</ul>

<a name="author"><p><strong class="subhead">作者简介</strong>
<br><!-- <img SRC="author.jpg" tppabs="http://www.chinajavaworld.com/doc/lang/author.jpg" BORDER=0 width=64 height=71 align=LEFT> -->
Donald Bell 是 IBM 全球服务中心的 IT 专家,他为客户提供有关基于 Web 的技术应用指导。可以通过 <a HREF="mailto:bellds@us.ibm.com">bellds@us.ibm.com</a> 与他联系。</p>

        </td>
      </tr>
    </td>
  </tr>
</body>
</html>

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -