Portable Basemap Server简单介绍

使用现在流行的Web地图API的第一件事情,就是往地图控件中添加一个底图(Basemap)图层,做为我们整个GIS应用的可视化基础。而这个底图图层通常有两个特点,一是经过了缓存,即服务器端提供已经预先缓存好或动态提供固定大小(比如256*256)地图切片,加快客户端的访问速度;二是该图层由一个REST风格的网络服务暴露出来。对于它的访问,客户端一般会发起若干个包含有三个关键参数的请求,比如http://hostaddress/servicename/LEVEL/ROW/COLUMN,将请求的结果(若干切片)拼接成我们所看到的地图。
  目前来讲,要使用这些底图服务的前提是,我们必须使用特定的客户端才能加载特定的底图服务,比如利用Google Maps API加载Google的底图;如果要加载自己地理数据,还需要有专门的GIS软件,比如ArcGIS Server来发布Map Service。
  为了解决这一问题,使得开发人员能够更加方便地加载各种底图服务,从而将更多的精力投入到做出更有用的系统中去,我做了这个称作Portable Basemap Server(简称PBS)的小程序供大家免费使用。它的目的是通过一个可以拷贝到U盘里的,免安装的WPF程序,来加载各种数据源作为底图图层,直接为更多的客户端API提供一致风格的REST底图服务,从而使开发人员免去为每个应用程序自定义图层的麻烦。

Untitled-1

关于PBS的功能

  使用起来很简单,大致分四个步骤。1、选择数据源类型,2、设置数据源路径,3、设置将要发布的服务端口号和服务名,4、启动服务。程序界面如下:
image

一、选择数据源类型:

image

  • MobileAtlasCreator:MAC是一个开源的Java程序,可将在线地图切片保存到本地,比如Sqlite数据库中,供移动设备离线使用。介绍看这里。很多朋友都喜欢使用Google地图作为底图,以前的方法是,用第三方程序(MAC还是比较厚道的,不加水印没有任何功能限制)去下载切片,保存到本地,然后按照ArcGIS缓存的组织规则重新组织这些切片,再将其发布成缓存地图服务。最后一步比较麻烦。利用PBS,就可以直接读取MAC保存的Sqlite数据库,将其中的切片直接发布成可供多种客户端API使用的底图服务;
  • MBTile:类似于MAC,但它有更严格的规范,比如在特定位置存储全图范围(MAC没有),具体规范查看这里。MBTile切片存储遵循的是TMS规范,虽然这中规范已被WMTS逐步取代,但PBS依然支持这种数据源,可直接读取该数据源作为多种客户端的底图服务。可在这里下载一个海地的地形图进行试验;
  • ArcGISCache:这个不用多说了,ArcGIS Server生成的地图缓存,指定包含Conf.xml和Conf.cdi文件的文件夹作为数据源即可,PBS会自动读取Tiling Scheme;Exploded和Compact两种存储格式均可识别。如果是ArcGIS 10之前的切片,需要自己手动创建Conf.cdi文件(仿照现有的文件即可,里面存储的是全图范围);
  • ArcGISTilePackage:Tile Package是ArcGIS 10.1推出的便于分发,可将地图服务缓存文件(compact或exploded)打包成单一文件的文件格式,文件后缀名为.tpk。以前为了分发地图数据,需要将样式配置信息(针对所有图层的地图文档.mxd,针对单个图层的图层样式.lyer)和实际地理数据(.mdb/.gdb/.shp等)一起拷贝。自9.3.1的开始,为了便于地图数据的分发,ArcGIS推出了Layer Package格式(.lpk),它包括了图层样式(.lyr)以及引用到的实际地理数据。这样其他用户拿到一个文件,就可完全还原数据本身和显示样式。ArcGIS10开始推出Map Package(.mpk)格式,10.1开始推出Tile Package(.tpk),Locator Package(.apk)和Geoprocessing Package(.gpk)格式;
  • RasterImage:1.0.1版本开始支持。文件形式的影像数据。在项目过程中,可能需要加入高分辨率的影像文件做为底图服务,但对这些影像文件切图、保存需要耗费极大的时间、空间。利用PBS可将影像文件直接发布为动态缓存地图服务,无需切图即可达到缓存地图服务的效果。对栅格数据的读取是利用GDAL完成的,支持的影像格式见这里。发布的影像数据必须具有正确的空间参考信息(不支持动态投影);需要选择ArcGIS Server生成的TilingScheme(Conf.xml和Conf.cdi文件)以确定缓存服务的级别; 
    1.0.2版本开始支持.ecw和.vrt影像格式。
    ecw是ERDAS公司持有的高压缩比影像格式,压缩率可达1:2~1:100。比如1m大小的ecw文件可包含3波段3000*3000(行/列)大小的影像数据;
    .vrt格式类似于ArcGIS中的Raster Catalog,具有对多张影像动态镶嵌的功能。比如你有很多空间连续的小的影像文件,它们加起来可能有上百G。通过构建后缀名为vrt的xml文件,直接将它们通过动态镶嵌,发布为一个完整的动态缓存地图服务。vrt文件可利用gdalbuildvrt.exe工具来自动创建,发布时PBS中数据源直接选择.vrt文件即可。vrt格式介绍一文,供参考。
    1.0.3版本开始支持.sid影像格式。
    MrSID是LizardTech公司持有的高压缩比影像存储格式,根据GDAL的解释,最初被FBI用于指纹存储。我对遥感知识知之甚少,做遥感的mm同事告诉我,MrSID格式压缩率通常比ecw格式要高,并且使用更广泛;
    image
  • ArcGISDynamicMapService:此数据源是指利用ArcGIS Server发布的,没有创建过缓存的动态地图服务。动态地图服务如何作为缓存地图服务的数据源呢?这就是所谓的动态缓存服务,没有预先创建过缓存,但能够提供缓存服务效果,并且支持动态投影的服务,也可查看超图的在线帮助。通过PBS,也能够提供动态缓存服务了,并且不需要在客户端再去自定义图层,因为PBS已经为你做好,直接使用即可。还可以输入多个动态服务地址,通过多个服务实例来达到加速动态缓存地图服务的目的,原理说明可查看这篇文章。输入服务地址后,还需要选择Tiling Scheme。可以选择Google/Bing/ArcGISOnline采用的Tiling Scheme,也可指定ArcGIS Server创建的Tiling Scheme(Conf.xml和Conf.cdi文件),如果数据源的坐标系与指定的Tiling Scheme坐标系不一致,可以自动进行动态投影;
  • ArcGISImageService:ArcGIS Server发布的影像服务(ImageService)。10.1版本之前的ArcGIS,不支持ImageService的切图。类似于上面的动态地图服务数据源,PBS可将动态的ImageService转成动态缓存地图服务,既大大改善了ImageService的显示效果和速度,又省去了切图所需的时间和硬盘空间。支持输入多个影像服务地址,通过多个服务实例来达到加速动态缓存地图服务的目的。选择此数据源,默认填入Esri发布的全球Landsat数据影像服务地址,可通过观察原动态影像服务,对比PBS转换后的动态缓存地图服务的效果;
  • 各种在线地图:这个也不用多说了。目前支持OpenStreetMap,Google Maps街道图,Google Maps影像图,Bing Maps街道图,Bing Maps影像图,天地图(文字注记和地图是两个服务,可叠加)这几种在线地图作为数据源,天地图Tiling Scheme是WGS 1984坐标系的,其他几种均是WGS 1984 Web Mercator坐标系的。需要说明一点,如果你打算使用PBS为公网用户提供服务,选用在线数据源时可能会有延迟,因为PBS首先会下载切片到本机(内存中),然后公网用户在下载这些结果,局域网应用可忽略此问题(2.0版本开始提供内存缓存功能,可解决此问题);如果确实慢,可考虑使用MAC数据源(Bing Maps服务最好输入一个合法的API KEY,以用达到最快的下载速度)。还要郑重声明一点,这些数据源只能做试验使用,不能直接用于商业目的,没有技术手段限制,但大家要自觉。如需商用,还请联系最终服务提供商


二、设置数据源:

  为选择的数据源类型设置相应的数据源位置即可。MAC和MBTile直接选去本地的Sqlite文件;ArcGISCache选择包含有Conf.xml和Conf.cdi的文件夹;ArcGISDynamicMapService直接输入一个或多个REST服务的地址;所有在线地图不需要设置数据源位置,PBS已为你做好。

三、设置端口号和服务名

  PBS是通过.NET Framework的WCF框架完成的。在启动服务之前需要选择将服务发布到本机的哪个端口上。一个端口上可以发布多个服务,也可将服务发布在多个端口上。但同一端口上不能有同名的服务。
  DisableClientCache:默认情况下,PBS输出的图片可以被缓存在客户端,下次访问时会直接使用客户端的缓存而不需要重新绘制切片。勾选此选项后,PBS输出的图片响应会指明不允许客户端进行缓存,从而方便客户端每次都请求道最新的数据。
  Display”NoData”Tile:勾选此项后,在Tiling Scheme范围内,如果某些范围或某些比例尺没有创建缓存,则会显示一个NoData的图片;如果打算用此服务与其它服务叠加(保持此服务背景透明),请不要勾选。

四、启动服务

  设置好上面参数后,点击“Start New Service”,即可启动该服务。启动好的服务会出现在下方的服务列表中:
image

五、服务管理

  程序下方的服务列表内会列出所有正在运行的底图服务,会显示服务名,所在端口号,数据源类型,服务启动后输出的切片数量,平均成功输出一张切片所需时间,以及最后一次被请求的客户端ip地址做为服务情况的大致预览。可在服务列表中双击某个服务,会弹出一个对话框,调用ArcGIS API for WPF查看该服务,并显示该服务的详细信息。如果该服务缺少全图范围参数,比如MAC数据源,则会新弹出的WPF对话框会额外添加一个ArcGIS Online底图,以便方便浏览到该服务的范围。

image

  如果加载某个切片失败,比如下载在线数据源时网络连接出现问题,会显示失败的图片:

image
  若要删除某个服务,请在服务列表中选中,然后点击“DeleteService”即可。
  此外,还可将已发布的全部服务保存成配置文件(v1.0.4版本以上),下回程序启动时可载入配置文件以启动相应的服务。配置文件保存在程序根目录下的Config.db文件中(sqlite文件格式)。

image

  2.0.3版本开始,PBS增加REST Admin API。任何程序可通过发送HTTP(POST)请求,对PBS的服务进行管理。PBS的REST Admin API使用HTTP基本认证,即HTTP请求头(request header)中必须含有“Authorization”项,该项内容为Base64编码字符串,格式为“用户名:密码”。请求认证信息中的用户(包含正确的密码),必须为PBS运行机器上Administrators组中的成员,所发送的请求才会被正确处理,否则将返回包含详细错误描述的响应信息。
  为了保证PBS能够正确响应请求的操作,请求中的端口必须提前打开。2.0.3版本开始,PBS默认使用7080端口,该端口会在PBS启动时自动开启。可修改配置文件中的DefaultPort值来更改PBS使用的默认端口号。
  每项管理操作都需要相应的参数,参数提交格式为标准JSON对象,对象中每一个键值对即为一个参数(键应为string类型,值应为string/int/bool/null类型)。参数应存放于HTTP请求体(request body)内。
  ~添加服务(addService):v2.0.3,该操作的地址为“http://serverip:port/PBS/rest/admin/addService”,参数列表如下:

  • name:(必须)需要添加的服务名称;
  • port:(必须)需要添加的服务端口号;
  • dataSourceType:(必须)需要添加的服务数据源类型,例如“ArcGISTilePackage”。可选值:MobileAtlasCreator|MBTile|ArcGISCache|ArcGISTilePackage|RasterImage|
    ArcGISDynamicMapService|ArcGISImageService|OpenStreetMap|BingMapsRoad|
    BingMapsImagery|GoogleMapsRoad|GoogleMapsImagery|TianDiTuAnnotation|
    TianDiTuMap。区分大小写;
  • dataSourcePath:(必须)需要添加的服务数据源路径。文件数据源类型可用本地路径或UNC路径,比如“D:\\arcgisserver\\arcgiscache\\CharlotteRaster.tpk”或“\\192.168.0.100\\arcgisserver\\arcgiscache\\CharlotteRaster.tpk”;ArcGIS动态地图服务或影像服务填服务地址;其余在线服务不需要此参数,填“”即可。注:RasterImage数据源路径中不能有中文字符;
  • allowMemoryCache:(可选)需要添加的服务是否允许支持内存缓存,默认为true。可选值:true|false;
  • disableClientCache:(可选)需要添加的服务是否禁止客户端缓存,默认为false。可选值:true|false;
  • displayNodataTile:(可选)需要添加的服务是否显示“Nodata”的切片,默认为false。如需要和其它服务叠加,此项需为false。可选值:true|false;
  • visualStyle:(可选)需要添加的服务的视觉效果,默认为None。可选值:None|Gray|Invert|Tint|Embossed。区分大小写;
  • tilingSchemePath:(可选)需要添加的服务使用的tiling scheme(缓存策略)文件路径。默认为null;

  比如,在fiddler中发送如下请求:
image[7]

  或用C#发送如下请求:

   1: byte[] postData = Encoding.UTF8.GetBytes(@"{""port"":7080, ""disableClientCache"":false, ""dataSourcePath"":""D:\\arcgisserver\\arcgiscache\\CharlotteRaster.tpk"",""dataSourceType"":""ArcGISTilePackage"", ""tilingSchemePath"":null, ""allowMemoryCache"":true, ""visualStyle"":""None"", ""name"":""ServiceName1"", ""displayNodataTile"":false}");

   2:             HttpWebRequest myReq = WebRequest.Create("http://localhost:7080/PBS/rest/admin/addService") as HttpWebRequest;

   3:             myReq.Method = "POST";

   4:             string username = "Administrator";

   5:             string password = "123456";

   6:             string usernamePassword = username + ":" + password;

   7:             //注意格式 “用户名:密码”,之后Base64编码

   8:             myReq.Headers.Add("Authorization", Convert.ToBase64String(Encoding.UTF8.GetBytes(usernamePassword)));

   9:             myReq.ContentLength = postData.Length;

  10:             using (System.IO.Stream requestStream = myReq.GetRequestStream())

  11:             {

  12:                 requestStream.Write(postData, 0, postData.Length);

  13:             }            

  14:             WebResponse wr = myReq.GetResponse();

  15:             System.IO.Stream receiveStream = wr.GetResponseStream();

  16:             System.IO.StreamReader reader = new System.IO.StreamReader(receiveStream, Encoding.UTF8);

  17:             string content = reader.ReadToEnd();

  18:             receiveStream.Close();

  19:             reader.Close();

  响应内容:JSON字符串,格式:{“success”": [ture|false],”message”: [detail message]}。如果操作成功,detail message将返回PBS服务信息的JSON字符串,如果失败,将返回详细错误原因。
  ~删除服务(deleteService):v2.0.3,该操作地址为“http://serverip:port/PBS/rest/admin/deleteService”,参数列表如下:

  • name:(必须)需要删除的服务名称;
  • port:(必须)需要删除的服务所在端口号;

  响应内容:JSON字符串,格式:{“success”": [ture|false],”message”: [detail message]}。
  ~开启内存缓存(enable):v2.0.4,该操作地址为“http://serverip:port/PBS/rest/admin/memCache/enable”,参数列表如下:

  • memSize:(可选)内存缓存功能占用的内存大小,默认为64(M)。

  如果内存缓存功能已经开启,返回结果依然为true,但会有额外提示。
  响应内容:JSON字符串,格式:{“success”": [ture|false],”message”: [detail message]}。
  ~关闭内存缓存(disable):v2.0.4,该操作地址为“http://serverip:port/PBS/rest/admin/memCache/disable”,此操作不需要参数(请求体为空即可,如有则忽略)。如果内存缓存功能已经关闭,返回结果依然为true,但会有额外提示。
  响应内容:JSON字符串,格式:{“success”": [ture|false],”message”: [detail message]}。
  ~清除某个服务的内存缓存(clearByService):v2.0.4,该操作地址为“http://serverip:port/PBS/rest/admin/memCache/clearByService”,参数列表如下:

  • name:(必须)需要清除内存缓存的服务名称;
  • port:(必须)需要清除内存缓存服务所在端口号;

  响应内容:JSON字符串,格式:{“success”": [ture|false],”message”: [detail message]}。
  后续版本将增加更多操作…

六、服务使用

  启动好的服务都会暴露出来一个REST服务地址,
image

  目前仅支持ArcGIS缓存服务规范,可供所有ArcGIS客户端API,包括Javascript/Flex/Silverlight/iOS/Windows Phone/Android,以及即将推出的ArcGIS Runtime直接使用;由于OpenLayer中可通过ArcGIS93REST图层直接加载ArcGIS的服务,因此PBS服务也可直接被OpenLayers客户端使用。
  比如在ArcGIS API for Javascript中,我们在地图中添加一个底图图层,Url地址指向PBS发布的某个服务:
image

  这样就能直接通过PBS为我们提供的,类似于原生ArcGIS缓存地图服务的Url地址,访问到第三方的底图数据了。开发人员从此免去了在客户端自定义图层,去加载第三方切片的麻烦。比如通过PBS提供的服务,分别在ArcGIS API for Javascript/Flex/Silverlight中调用Google Maps地图。

image

image

image

  除此之外,从1.0.6版本开始,PBS增加了风格化的选项,可以在不需要重新切图的情况下(动态地图服务则无需切图),直接改变所有底图服务的视觉呈现效果。目前提供视觉风格选项:灰度图(Gray)和反色图(Invert),用于特殊目的。比如使用灰度图可突出显示业务内容,详见这里
  2.0.3版本新增泛黄(tint)与浮雕(embossed)两种效果。
VisualSytle


关于PBS的性能

  PBS利用WCF REST框架开发,支持多用户,多并发请求,性能仅受机器硬件限制。初步用Apache JMeter做了测试,在我的笔记本上,通过PBS的REST服务,请求Sqlite数据库中一张22kb的图片,500个并发请求的响应时间在10ms以下:
image

  在磁盘性能更好的服务器上测试,1000个并发请求的相应时间可以在10ms以下。
  而实际使用中,单个底图服务达到上千个并发请求的情况还是比较少见的,所以PBS可以满足大多数需求。
  从2.0版本开始,PBS增加了内存缓存功能。可将已生成过的切片数据自动缓存在机器内存中,之后可从内存中直接返回该切片,而不是动态生成。
image_thumb[3]
  2.0.1版本增加对单个服务是否启用内存缓存的控制,并增加输出动态生成切片数量和内存缓存切片数量的信息。
image_thumb[3]
  2.0.2版本增加对单一服务清除内存缓存的功能。
  只需在Memory Cache菜单下,勾选Enable选项,即可启用内存缓存功能。该特性可显著提高PBS性能,尤其对于动态缓存地图服务功能(影像数据或动态地图服务作为数据源),在几乎不占用cpu资源的情况下,支持的并发数可提高数十倍。该功能利用Memcached完成,它是一个免费的高性能分布式缓存系统(http://memcached.org/)。
  默认情况下,Memory Cache会使用64M机器内存来缓存切片数据,达到64M后,会自动替换掉最早的缓存数据。使用机器内存的大小可通过PortableBasemapServer.exe.config配置文件进行配置,只需修改其中MemcachedSize节点的数值即可。
  比如对于影像数据作为数据源的动态缓存地图服务功能,在服务器机器上,可配置更多的物理内存(比如4G)供PBS使用。这样一来,只需在第一个客户端访问时生成一次切片数据,后续的请求就可直接从内存中获得切片。以内存方式替代cpu的工作和硬盘的存储空间,使得PBS投入实际生产运行成为可能。
  经测试(笔记本环境),对于PBS转发的在线地图服务(Google Maps)中的一张切片,没有使用内存缓存功能时,100个并发请求响应时间平均为10秒左右(和我的网速慢也有很大关系),因为每次请求都需要在线下载该切片;使用了内存缓存功能后,对于同样的一个切片,100个并发请求响应时间平均为2毫秒(该切片已在内存中的情况,下同),500个并发平均响应时间为6毫秒,1000个并发平均响应时间为200毫秒左右。在内存更好的服务器上测试,可获得更理想的结果

总结

  对于ArcGIS用户来说,通过PBS,可直接加载第三方的离线数据源(MAC/MBTile),而不需要按照ArcGIS的切图规则重新组织切片;可将动态地图服务转换成动态缓存地图服务,无需自己在客户端API中自定义图层;可使用多种数据源;
  对于OpenLayers用户,可使用更多的,内容更丰富的底图数据;
  Portable Basemap Server可装入U盘带走,在任何具有.NET Framework 4.0环境的机器上直接运行,无需安装。一个U盘即可提供多种底图,方便开发者使用;
  后续计划加入更多数据源,比如本地影像数据(已加入),以及为更多客户端提供支持。

下载地址

http://www.arcgis.com/home/item.html?id=48bf53da123e442ab8ac9aed52747552
如果大家对于软件有任何意见或建议,欢迎在此篇博客中留言回复。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值