在2011年为iOS / Android开发HTML5离线存储解决方案


74

问题:

我需要一个与设备无关的解决方案(例如HTML5),用于在电话或平板电脑类型的设备(例如iOS / Android)上离线存储和查询250,000多行数据。我的想法是让人们在没有任何蜂窝数据连接的情况下在偏远地区工作,他们需要对此数据运行查询并在脱机时对其进行编辑。部分将基于地理位置,因此,如果资产所在的区域中有资产(使用GPS),则它将显示这些资产并进行编辑。当他们返回办公室时,他们可以将数据同步回办公室服务器。

我从Web标准的角度来解决这个问题的原因基本上是为了节省金钱和时间,方法是在HTML5中编写一次,然后在多个平台上工作,而不是在Objective C和Java中编写两次。同样,如果您编写的内容与平台无关,那么您就不会被锁定,并且当每个人都迁移到更新的版本时,都不会陷入困境。我们有一个为Windows Mobile 5编写的类似应用程序,但由于该平台已失效,它已无用。

设备上的离线数据库必须为:

  • 快速(响应时间少于2秒)
  • 可能执行联接并与能够查询数据库的其他表有关系
  • 根据GPS读数,通过x和y坐标选择某个范围或标准内的数据。

选项:

HTML5本地存储:

对于少量<5,000个键/值的数据,如果将其转换为JSON,您甚至可以在其中存储数组/对象。

缺点:

  • 即使在高端计算机上,超过10,000行的浏览器也会缓慢爬行。
  • 无法对数据进行复杂的查询以提取所需的数据,因为您必须遍历整个存储并手动搜索它。
  • 可以存储的存储空间的限制

Web SQL数据库:

  • 符合要求。
  • 快速在250,000行上运行查询(1-2秒)
  • 可以创建复杂的查询,联接等
  • 受Safari,Android和Opera支持,因此可在iOS和Android设备上使用

缺点:

  • 自2010年11月起弃用
  • 跨目录攻击的安全漏洞。并不是真正的问题,因为我们不会共享托管

IndexedDB:

键/值对象存储与本地存储类似,但带有索引。

缺点:

  • 缓慢地对200,000行执行查询(15-18秒)
  • 无法运行复杂的查询
  • 不能与其他表联接
  • 主要电话或平板电脑设备(例如iPad / Android)不支持
  • 标准不完整

这就留下了实现不推荐使用的Web SQL方法的唯一选择,该方法只能再使用一年左右。目前,IndexedDB和本地存储不可用。

我不确定Mozilla和Microsoft如何弃用Web SQL数据库标准,以及W3C为何允许它发生。据推测,它们之间拥有台式机浏览器市场的77%。在先进的移动设备上,Mozilla和Microsoft的影响力几乎为零,因为Safari,Opera和Android占据了90%以上的市场份额。Mozilla和Microsoft如何决定应该在移动市场中使用哪个标准,而在哪个市场中最有可能使用脱机存储,这没有任何意义。

Mozilla在关于为什么要使用IndexedDB的评论中,主要是关于“开发者审美”的,他们不喜欢在JavaScript中运行SQL的想法。我不买。

  1. 目前,提出的标准还很差,并且是一个极其基本的NoSQL实现,该实现很慢,甚至不支持人们在数据库中所需的高级功能。建立数据库和获取数据有很多样板代码,但他们声称人们会在其顶部编写一些不错的抽象库,这些库将提供更多高级功能。截至2011年10月,它们无处可寻。

  2. 他们已经弃用了现有的Web SQL标准,该标准实际上有效并已在主要的移动/平板电脑浏览器中实现。而在主要的移动浏览器中没有它们的“新”和“更好”标准。

  3. 在接下来的3-5年中,作为IndexedDB规范可能逐步标准化,具有更多功能,在主要的移动/平板电脑浏览器中实现的功能以及一些易于使用的好的库,开发人员应该使用什么?

W3C应该保持Web SQL数据库标准并行运行,并解决问题。它已经支持主要的移动平台,并且运行良好。Mozilla和Microsoft作为拥有最多桌面浏览器份额的两个播放器能够取消此标准的事实是相当可疑的,并且可以被视为试图阻止移动Web平台上的进展,直到他们能够赶上并提供该标准。与iOS / Safari和Android竞争的解决方案。

总之,没有人能解决我的问题,该解决方案适用于适用于手机/平板电脑设备的iOS / Android。也许是一个不错的包装器API,它可以在后台使用具有查询功能的多个数据库实现,并允许您选择哪个数据库具有优先级。我见过草椅之类的东西,但我敢肯定,它默认只允许您使用本地存储,而后退到其他位置。我想我宁愿使用Web SQL(默认情况下),然后使用较慢的选项。

任何帮助解决方案的帮助,谢谢!


5
写得好文章!这是本机应用程序赢得本机vs Web应用程序争论的情况之一,但我知道您不想听到这种情况。在我所知的情况下,Web SQL是最好的选择-我还会强迫用户下载与他们要去的位置相关的行,而不是整个数据库-如果您认为他们可能需要在某个地方进行更新,连接,更不用说通过1/5大小的数据库(不确定数据库的规模)搜索的速度提高了
amcc

2
他们无法使用WebSQL来“解决问题”,因为向W3C推荐标准发展的标准的要求之一是必须有“独立且可互操作的实现”。由于规范基本上是“做SQLite要做的事情”,所以这永远不会发生。
robertc 2011年

2
嘿,您刚刚描述了我的期末考试项目:)正如我所看到的,如果您需要脱机和下降性能,则有两种选择;1.使用本地存储并将数据精简为绝对基础。或2.构建一个本机应用程序(具有可伸缩的UI?),然后将其克隆到另一个平台(您已经在第一个平台上设置了规范,因此可以更快地为其他平台开发它。)缺点是您必须维持多个)
Michael Olesen

2
因为在他们要求我们拥有的是W3C建议之前,实际上还没有浏览器实现。三种浏览器都使用SQLite。没有SQLite规范,这就是为什么它不是标准的良好基础的原因之一。
robertc 2011年

1
@robertc您如何表示没有任何规格?它基于SQL92标准,并略有遗漏。我发现此页面似乎是一个规范。另外,SQLite网站上的所有其他文档又如何呢?这实际上是规范的一部分吗?它还需要什么有效?
zuallauz 2011年

Answers:


18

我建议您检出JayData库,该库实际上具有为移动设备创建与存储无关的数据访问层的确切目的。JayData提供了一个具有JavaScript语言查询(JSLQ)和JavaScript CRUD支持的抽象层,让您以完全相同的方式处理不同的离线和在线数据存储类型。JayData支持处理复杂实体以及本地或远程实体关系。

在撰写本文时,JayData支持以下存储或协议:webSQL(sqLite)/ IndexedDB / OData / YQL / FBQL。

您可以通过JayData的提供程序后备功能轻松解决您的不同系统提供不同存储引擎的特定问题:JayData会使用它可以找到的任何存储层,同时仍然为消费者代码提供相同的API。

关于WebSQL在2012年之前已过时:在撰写本文时,WebSQL仍具有95%的设备覆盖率,包括三星SmartTV和亚马逊Kindle。检出使用JayData执行WebSQL单元测试的kindle


我同意,JavaScript语言查询的支持和提供程序模型使JayData库成为HTML5离线存储解决方案的不错选择。

更新:JayData现在也支持HTML5 localStorage。JayData库执行JSON字符串化/解析工作,并提供干净,统一的数据管理API和概念。
罗伯斯(Robesz)

1
我很高兴为您提供答案,因为这听起来确实很必要,但是对于大型数据库(例如250,000行),您是否有任何性能基准?我很想知道它是否可以同时使用IndexedDB和WebSQL基础存储来处理这么多行(取决于设备),然后花时间进行一次基本的“ where”类型查询以根据某些条件查找某一行需要花费多长时间。
zuallauz

2
@zuallauz我刚刚制定了这样的基准。使用Android nexus 2从25万个项目中获取5-10个项目在websql上花费了我60毫秒,而在装有Windows Phone的Lumia 920上花费了25毫秒。(IndexedDB肯定更快)。
彼得·阿隆·曾泰

1
@zuallauz您对此非常正确,我们会的。通常,IndexedDB在各个方面都快得多-除了复杂的多字段查询。但是,在WebSQL上插入数据可能会很慢。开放进行写入的事务可能会很昂贵(60-120ms)。
Peter Aron Zentai

13

我会结帐CouchBase Lite。它是CouchDB的近全功能实现,可在Android和iOS上运行。

的iOS

安卓

如果将您的应用程序包装在诸如PhoneGap之类的东西中,则可以为两个平台创建本机HTML 5应用程序,而只需执行少量Android / iOS特定程序即可实现CouchDB。

优点:

  • 快速查看引擎,用于查询多行数据。
  • 简单而强大的污垢复制支持。

缺点:

  • 键值存储-需要一段时间才能习惯。

谢谢,听起来像它可以工作,但是您需要一个我认为可以为其开发并产生密钥等的Mac系统吗?我们没有任何Mac。
zuallauz 2011年

CouchDB非常有趣,但是我不相信其使索引(“视图”)更新延迟(由查询或批处理触发)的模型确实运行良好。我见过的大多数应用程序都假定一旦添加了一些数据,就可以有效地查询它,并且大多数其他NoSQL数据库将更多工作推入写入事务中,从而使读取事务更快。
RichVel 2012年

@RichVel:以我的经验,视图更新从未在移动设备上成为问题。这就是说使用CouchDB或TouchDB的最大原因之一是超级强大但易于使用的复制。
rwilliams

1
我开始考虑将CouchDB复制到移动设备,但是我并不是真的想将服务器数据库公开给移动设备,或者我不想在服务器上使用CouchDB来进行复制。因此,我现在正在研究一种称为Simperium的数据同步云服务,请参见simperium.comsimperium
RichVel 2012年

6

我在为自己的项目寻找解决方案的同时进行了更多研究。看起来这个库很有前途:http : //nparashuram.com/IndexedDBShim/

它允许使用在后台具有WebSQL的IndexedDB API。

测试通过了最新的iPad,iPhone 5,Android 4.2.2。

希望这对某人有帮助。


晚会,但我也建议indexeddbshim.js。它可以在Cordova / PhoneGap环境中正常运行,从而为IOS和Android提供单一解决方案。
道格拉斯·蒂姆斯

2

我会告诉你使用电晕。这是用于跨移动应用程序的私有平台,该平台支持SQLite。

优点

  • 这很容易,并且对SQLite具有强大的支持,并且不需要使用Html5存储做奇怪的事情

缺点

  • 如果您想在Android Market或iOS Market中使用它,则必须付费。

我在这里粘贴他们对此的评价:

Corona包括所有平台上对SQLite数据库的支持。这基于iPhone上内置的sqlite支持,以及Android上SQLite的编译版本。请注意,这会将Android二进制文件的大小增加300K。

SQLite在所有版本的Android,iPhone和iPad以及Corona Simulator中均可用。


2

“我见过草椅之类的东西,但是我敢肯定,它默认情况下只能让您使用本地存储,而其他用户则可以使用它。我想我宁愿它使用Web SQL(默认情况下),然后使用速度较慢的选项。”

这是可配置的,存储引擎的每个“适配器”都是自包含的,您可以将适配器传递给Lawnchair构造函数,或者通过在不同时串联javascript文件来更改其回退到其他存储选项的顺序创建库。例如,对于index-db,然后回退到sqlite,然后调整sqlite:

git clone https://github.com/brianleroux/lawnchair.git  
cd lawnchair  
cat src/Lawnchair.js src/adapters/indexed-db.js src/adapters/webkit-sqlite.js src/adapters/gears-sqlite.js > my_lawnchair.js

当然,正如其他答案所建议的那样,您可以使用phonegap等将html5包装到本地应用程序中。然后,您将有很多选择,但是如果您要遵循网络标准,那么这可能是一个不错的选择我们已经广泛采用了IndexedDB。


1

为什么不使用javascript(涵盖“基于标准”的部分)编写一个简单的存储引擎?显然,您不需要任何花哨的东西,因此它不需要花费太多的精力即可工作。

我将执行以下操作:

  • 将所有内容存储为bson或类似的二进制格式。
  • 解析并在文件中创建索引,并在启动时读取。
  • 使用javascript查询并从您的(显然是脱机的)Web应用程序中读取大文件。
  • 分开存储更新的对象。

仅当数据库足够简单时,此解决方案才可行。但我认为这可能会起作用-在移动设备上javascript支持很好。

为了激发灵感,这里是用javascript实现的Btree +实现。

要读取本地文件,您将需要文件API,该文件API可用于访问本地文件。大多数现代浏览器甚至Safari 6都支持它。我无法确定当前的iPhone浏览器是否支持此API。


手机上的JavaScript如何访问设备上的文件系统或从文件系统读取/写入文件?
zuallauz 2011年

1
好点子。显然,File API并不像它看起来的那样远,但是我的回答可能有点过于乐观。CouchBase看起来更安全。
alexfernandez

1

值得检查我的开源库https://bitbucket.org/ytkyaw/ydn-db/wiki/Home

用于Indexeddb,WebDatabase(WebSQL)和WebStorage(localStorage)存储机制的Javascript数据库模块,支持版本迁移,高级查询和事务。

作为NoSQL库,join是手动的,但并非没有可能。库中已经内置了关键的加入算法。


如果在代码中我需要执行SQL查询以检索一些数据并对其进行排序,但是我的设备正在运行IndexedDB,那么您的库是否可以转换该SQL查询,以便从IndexedDB数据库中获取数据?
zuallauz

不。我的库中的SQL支持非常基础。请在此处查看它的功能。dev.yathit.com/ydn
Kyaw Tun
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.