使用CGI实现MapSever交互

通过 Mapfile 配置文件来进行地图制图,已经了解了地图、图层和类的基本思想,知道一个 Mapfile 的各部分怎样结合在一起。现在继续进行到一个应用程序,将提供完整的平移和缩放功能,以及能够打开和关闭图层。

到目前为止,只能在创建地图查看地图。创建Web制图应用程序,通常的意义是创建能够由用户(应用程序的) 改变的地图。 也就是说,一个用户能够改变地图的内容(或者信息)。 要互动的完成这件事情,我们使用MapServer HTML模板。

MapServer CGI是基于模板的。 当首次执行以响应Web请求时,它会读取描述地图的图层和其他组件的配置文件(Mapfile)。然后它绘制并保存地图。 接下来,它读取 Mapfile 中标识的一个或多个HTML模板文件。每个模板由传统的HTML标记标记和特殊的MapServer替换字符串组成。例如,这些字符串用于指定MapServer创建的地图图像的路径,识别要渲染的图层,以及指定缩放级别和方向。MapServer替换这些字符串的当前值,然后将数据流发送到Web服务器,然后Web服务器将其转发到浏览器。当请求者更改页面上的任何表单元素(例如,通过更改缩放方向或缩放值)并单击提交按钮时,MapServer将从Web服务器接收具有这些新值的请求。 然后循环再次开始。

MapServer的网络访问技术说明

你最初的目的是在CGI环境中生成地图,在CGI环境中,用户通过网页浏览器可以连接到Apache网络服务器。在这种环境下,Apache会调用MapServer,可以从浏览器传递各种形式的变量。使用这些信息,MapServer生成地图和网页,Apache再把这些内容返还给浏览器。当然,MapServer要想生成地图仅仅需要浏览器的信息是不够的。

事实上,CGI MapServer网络应用有四个组分: 地图文件,HTML初始化的形式,一个或多个模板文件,以及空间数据(库)。

注意:Web应用程序可以提供静态页面的固定内容,也可以通过脚本对web表单的响应来提供动态内容,以及数据库查询和其他的功能。

决定这些脚本与Web服务器之间交互作用的标准被称为通用网关接口,通常缩写为CGI。

本章将讨论这四个组分。前提假设是用户的网络浏览器已经显示了初始化的文件。

MapServer,与所有的网络应用都相似,是基于无状态的协议——也就是在每次调用时,它仅知道浏览器传达给它的信息。无状态协议排除了使用程序对最后一个问题之外的内容进行回答。然而,一些聪明的代码可以提供有状态的环境,从而使得网络应用程序有能力开展更复杂的工作。例如,通过在隐藏形式的变量中存储状态的信息可以在调用之间维持状态,在URL或者cookie中就可以存储这样的信息。但是有些方法需要对程序进行引导,所以它包含了第一次调用所需的信息。

在MapServer中,通过初始化文件来完成这项内容。在CGI MapServer应用程序中,初始化文件是传统的HTML表单,它有着初始化的信息把硬编码转化为表单变量。几乎所有MapServer用到的值都可以在初始化文件中设置。

当Apache使用HTML的初始化表单第一次调用MapServer的时候,表单变量用来指定地图文件的名称(扩展名通常是 .map )。

它随后找出文件的字体、符号、模板以及空间数据。地图文件同样指定了最后地图的大小、地理范围,以及地图是否是GIF,JPEG或者是PNG格式。读取完地图文件后,MapServer会渲染一幅或多幅影像:地图本身,图例和比例尺,可能还会有参考地图。它会把这些影像存储在地图文件的指定位置中。

为了展现结果,MapServer需要设计地图格式并组织相关元素使之成为网络页面。程序本身并不会生成HTML,相反,它会扫描HTML模板来替代字符串。字符串替代可以参考文件、地图几何的细节信息、图层规范或者缩放因素等。它们也可以是CGI变量的常数,例如图像大小、地图文件的名称、地图范围等等。

MapServer用合适的值替代字符串并把修改的HTML 返还给请求信息的浏览器。

本章中,你将建立地图应用来阐明使用MpaServer的简易性以及各组分是怎样组合在一起工作的。

下面的章节会介绍MapServer的 特性(投影,瓦片检索,符号,查询等等),这会使得MapServer的功能更加明显。

通过CGI进行MapServer应用开发

MapServer提供两种开发接口:CGI和MapScript。CGI是进行MapServer应用开发最基本的方法。在CGI模式下,MapServer利用GD库将空间数据转化成地理图形再传回到用户的浏览器。用户不需要安装任何特定的浏览程序就可以通过浏览器对其进行操作。

用户可以通过类似下面的URL直接向MapServer服务器发出请求,MapServer根据请求的参数创建合适的地图图片,并将结果返回给用户的浏览器:

http://hostname/cgi-bin/mapserv?map=/ms4w/apps/txitorial/htdocs/example1-1.map&layer=states&mode=map

其中 /cgi-bin/mapserv 是MapServer CGI程序。? 后面是由 maplayermode 等MapServer CGI参数组成的查询字符串。其中 map 参数指明MapServer进行处理的地图文件,layer 参数告诉 mapserv 显示的图层, mode 参数告诉 mapserv 生成静态的地图图片。

另外,可以通过指定 mode 参数的值为浏览器来生成动态的、可交互的地图。这时当用户点击地图时,MapServer会以用户点击的位置为中心生成一个放大、缩小或重新定位的地图。

生成动态地图需要一个HTML模板,该模板中有一个表单用来与用户进行交互。

一个简单的表单如下:

<!-START OF MAPSERVER FORM->
<form name=mapserv method=GET" action="/cgi-bin/mapserv.exe">
<!-HIDDENMAPSERVERCGIVARIABLES->
<input type=Mhidden"name="map"value=n[map]">
<input type="hidden"name="imgext"value="[mapext]n>
<input type="hidden"name="imgxy"value="199.5149.5">
<input type="hidden"name="zoom"value=,T'>
<input type="hidden"name="mode"value="browse">
<div align="center">
<table border='T'cellpadding="0"cellspacing=0">
<tr>
<td>
<!-THE INTERACTIVE,DYNAMICALLY CREATEDMAP->
<input type="image"name="img"src="[img]"
width=400height=300>
</td>
</tr>
</table>
</div>
</form>

MapServer HTML模板是一个带有MapServer标记(tag)的HTML格式的文件。MapServer标记是以方括号([])括起来的MapServer CGI变量,如 [map][img][mapext] 等,它们分别代表地图文件、地图图片URL和地图的范围。通过HTML模板,可以大量简化MapServer CGI编程。

当MapServer CGI程序接受到MapServer HTML模板传来的请求时,首先解析参数,处理请求并生成必要的输出,然后将这些输出中的一部分替换HTML模板中的相应的MapServer标记(变量),最后将带有输出结果的HTML(模板)文件返回给客户浏览器。由于模板中的地图是表单元素的形式返回的,所以用户可以与之进行交互。

MapServer提供了许多CGI变量用于Web制图,MapServer的地图文件中几乎所有的关键字都可以定义为一个变量,但是用于制图的核心的CGI变量并不多。另外,用户也可以自定义变量,如用户可以定义一个名为 root 的变量,用来代表应用程序的根目录。

地图浏览只能依靠MapServer提供Web制图服务的基本功能,除此之外,MapServer还提供了强大的空间和属性查询功能。在CGI模式下,广泛使用HTML模板来构建查询和组织查询返回的信息,这通常涉及与地图文件、模板和MapServerCGI程序间复杂的交互。

MapServer有许多模式( mode,浏览( browse )模式是MapServer默认的模式。其中有18种模式与查询相关。MapServer通过使用这些查询模式,可以实现诸如:根据鼠标位置进行点查询,根据输入坐标值进行点查询,通过输入一个表达式进行属性查询以及根据要素的序号进行查询等。

MapServer创建图例和比例尺(可在mapfile中配置)并生成参考图。参考地图显示当前显示的地图的上下文。缩放和平移由用户控制。

MapServer HTML模板

使用 MapServer HTML 模板,需要在每个 HTML模板文件中添加 MapServers模板声明。 不然,在使用 GetFeatureInfo (带有 info_format集合)作为 text/html 请求时,会得到下面的错误信息:

Content-type: text/xml isValidTemplate(): Web application error.
Missing magic string, template-file doesn't look like a MapServer template.

需要在每个模板的最开始添加:

<!-- MapServer Template -->

Example the exemplar template query footer.html is:

<!-- MapServer Template -->

一个MapServer HTML模板实际上是一个有几个特定MapServer的HTML文件-- 这些表标签是括在 [] 中的MapServer CGI 变量 。 当MapServer CGI程序处理应用时,它首先解析 query_string 和地图文件,并产生必要的输出 。 这些输出需要写 在 HTML 模板 文件中,必须在 Mapfile 中定义,通过使用网络模板关键字(或者在一个单独的HTML初始化文件中)。 CGI 程序将取代所有在 HTML 模板中的变量,用适当的值,在将它发送到 Web 浏览器之前。 如果直接在网页浏览器上查看HTML 模板的内容, 将不会有任何地图提供,反而会有空的图像和其它不明意义的字符。

MapServer的网络映射提供了一些变量-- img 变量, 前面已经有过例子,那里的几个常用的CGI 变量设计作为地图界面初始化的一个部分, 但是实际上所有 MapFile 参数都能够被定义为变量。

CGI变量的明确的参考在: http://www.mapserver.org/cgi/index.html

MapServer 使用的 CGI 变量也可以由开发者进行定义,MapServer将会把它传递到应用程序中。 例如,我们可以创建一个变量叫做 root 来代表我们的 代表本教程的根目录-- root 的值将会被 /tutorial 。 当MapServer CGI的值处理我们的HTML 模板,它将会代替每一个 [root] 标记以及 /tutorial 的实例。你将会看到这个在每一个如下例子中的动作中。