在ASP中限制同一表单被多次提交


  本文介绍在ASP 利用中 预防消费者在目前会话期间 频繁提交同一表单的一个 方便 步骤 。它重要由四个子程序构成,在较为 方便的 利用场合,你 惟独将这些代码放在包括文件中直接 引用即可;关于那些较为复杂的环境,我们在文章的最终给出一些改良 提议 。

  一、 根本工作过程

  下面我们 顺次 探讨这四个子程序 。

  (一)初始化

  这里我们要在Session对象中 保留两个变量,其中:

  ⑴ 每一个表单对应一个称为FID的唯一标识,为使该值唯一要用到一个计数器 。

  ⑵ 每当一个表单 顺利提交,必须在一个Dictionary对象中存储它的FID 。

  我们用一个专用的过程来初始化上述数据 。 固然以后各个子程序都要调用它,但实际上每一个会话期间它只执行一次:

Sub InitializeFID()
  If Not IsObject(Session("FIDList")) Then
  Set Session("FIDList")=Server.CreateObject("Scripting.Dictionary")
  Session("FID")=0
  End If
  End Sub

  (二)生成表单的唯一标识符

  下面这个函数GenerateFID()用于生成表单的唯一 标记 。该函数首先将FID值加1, 而后返回它:


  Function GenerateFID()
  InitializeFID
  Session("FID") = Session("FID") + 1
  GenerateFID = Session("FID")
  End Function

  (三) 注销已提交表单

  当表单 顺利地提交时,在Dictionary对象中 注销它的唯一标识:


  Sub RegisterFID()
  Dim strFID
  InitializeFID
  strFID = Request("FID")
  Session("FIDlist").Add strFID, now()
  End Sub

  (四) 审查表单是不是 反复提交

  在正式 解决消费者提交的表单之前,应该在Dictionary对象中 审查它的FID是不是已经 注销 。下面的CheckFID()函数用来 实现这个工作,如已经 注销,它返回FALSE,不然返回TRUE:

Function CheckFID()
  Dim strFID
  InitializeFID
  strFID = Request("FID")
  CheckFID = not Session("FIDlist").Exists(strFID)
  End Function

  二、如何 使用

  有两个地方要用到上述函数,即表单生成时与 后果 解决时 。 假如上述四个子程序已经放入包括文件Forms.inc中,下面的代码依据FID值来决定生成表单还是 解决表单 后果,它所 形容的 解决过程 合适于大多数ASP 利用:


  < %Option Explicit%>
  < !--#include file="forms.inc"-->
  < HTML>
  < HEAD>
  < TITLE>表单提交测试< /TITLE>
  < /HEAD
  < BODY>
  < %
  If Request("FID") = "" Then
  GenerateForm
  Else
  ProcessForm
  End If
  %>
  < /BODY>
  < /HTML>

  GenerateForm负责生成表单,表单中应该含有一个 潜藏的FID,如:

< %
  Sub GenerateForm()
  %>
  < form action="< %=Request.ServerVariables("PATH_INFO")%>" method=GET>
  < input type=hidden name=FID value="< %=GenerateFID()%>">
  < input type=text name="param1" value="">
  < input type=submit value="OK">
  < /form>
  < %
  End Sub
  %>

  ProcessForm负责 解决通过表单提交的内容,但在 解决之前应该先调用CheckFID() 审查目前表单是不是已经提交,代码类如:


  < %
  Sub ProcessForm()
  If CheckFID() Then
  Response.Write "你输入的内容是" & Request.QueryString("param1")
  RegisterFID
  Else
  Response.Write "此表单不得不提交一次!"
  End If
  End Sub
  %>

  三、 制约与改良措施

  上面我们介绍了在目前会话期间 制约同一表单被 频繁提交的一种 步骤 。在实际 利用中可能需求从多方面加以改良,例如:

  ⑴ 在 注销表单ID之前 审查消费者输入数据的合法性,使得数据不合法时消费者 可以按“后退”按钮返回,在 修改后再次提交同一表单 。

  ⑵ 这种对表单提交的 制约最多不得不在目前会话期间有效 。假如要求这种 制约 可以 跨越多个会话,那么就要用到Cookeis或数据库来 保留 有关数据了 。

  ⑶ 这种 步骤是不安全的 。它仅用于 提防误操作,不能 预防娴熟消费者故意地 频繁提交同一表单 。