Parse Local Datastore

Parse Local Datastore

  • 简介
  • 翻译
    • Pinning
    • Retrieving Objects
    • Querying
    • Security
    • Unpinning
    • Pinning with Labels
    • Caching Query Results
    • Syncing Local Changes
  • 说明

简介

本文翻译了Parse关于本地存储的部分,链接如下:Parse Local Datastore

翻译

The Parse iOS/OSX SDK provides a local datastore which can be used to store and retrieve PFObjects, even when the network is unavailable. To enable this functionality, add libsqlite3.dylib and call [Parse enableLocalDatastore] before your call to setApplicationId:clientKey:.

Parse iOS/OSX SDK提供了一个本地数据存储用以存储和检索PFObjects,即使在无网络状态下也可以使用。为了开启这个功能,请先添加libsqlite3.dylib并且在你调用setApplicationId:clientKey:前先调用[Parse enableLocalDatastore]。

@implementation AppDelegate

- (void)application:(UIApplication *)application didFinishLaunchWithOptions:(NSDictionary *)options {
  [Parse enableLocalDatastore];
  [Parse setApplicationId:@"parseAppId" clientKey:@"parseClientKey"];
}

@end

There are a couple of side effects of enabling the local datastore that you should be aware of. When enabled, there will only be one instance of any given PFObject. For example, imagine you have an instance of the "GameScore" class with an objectId of "xWMyZ4YEGZ", and then you issue a PFQuery for all instances of "GameScore" with that objectId. The result will be the same instance of the object you already have in memory.

开启这个功能后有几个方面的影响是你需要注意的。当开启时,只有一个PFObject。例如,假设你有一个objectId为"xWMyZ4YEGZ"的“GameScore”类的实例,然后你用这个objectId来查询“GameScore”的所有实例。结果将是已经在你内存中的那个实例。

Another side effect is that the current user and current installation will be stored in the local datastore, so you can persist unsaved changes to these objects between runs of your app using the methods below.

另一个影响就是当前用户和当前安装表已经存在了本地数据库,所以在你运行你的应用期间,你可以用以下方法来保存这些对象没有保存的内容。

Calling the saveEventually method on a PFObject will cause the object to be pinned in the local datastore until the save completes. So now, if you change the current PFUser and call [[PFUser currentUser] saveEventually], your app will always see the changes that you have made.

在一个PVObject上调用saveEventually方法将会使得对象与本地的数据库相连,直到完全保存。因此如果你修改当前的PFUser并且调用[[PFUser currentUser] saveEventually],你的应用总会看到你所做的修改。

Pinning

You can store a PFObject in the local datastore by pinning it. Pinning a PFObject is recursive, just like saving, so any objects that are pointed to by the one you are pinning will also be pinned. When an object is pinned, every time you update it by fetching or saving new data, the copy in the local datastore will be updated automatically. You don‘t need to worry about it at all.

你可以通过连接本地数据库来存储一个PFObject。连接一个PFObject是递归的,就像保存那样,因此所有对象都会被另一个对象所指向,你所连接的对象同样被别的对象连接。当一个对象被连接,每一次你通过读取后更新或者是保存一个新数据,它在本地数据库中的备份也将会被自动更新。你完全不需要担心。

PFObject *gameScore = [PFObject objectWithClassName:@"GameScore"];
gameScore[@"score"] = @1337;
gameScore[@"playerName"] = @"Sean Plott";
gameScore[@"cheatMode"] = @NO;
[gameScore pinInBackground];

If you have multiple objects, you can pin them all at once with the pinAllInBackground convenience method.

假如你有多个对象,你可以使用简便方法pinAllInBackground来一次性连接全部对象。

[PFObject pinAllInBackground:listOfObjects];

Retrieving Objects

Storing objects is great, but it‘s only useful if you can then get the objects back out later. Retrieving an object from the local datastore works just like retrieving one over the network. The only difference is calling the fromLocalDatastore method to tell the PFQuery where to look for its results.

保存数据是好的,但只有在保存后你可以重新取出数据这种好处才能体现出来。从本地数据库中检索一个对象跟从网络中检索是相似的。唯一不现的是需要调用 fromLocalDatastore 方法来告诉PFQuery该从哪里获取结果。

PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query fromLocalDatastore];
[[query getObjectInBackgroundWithId:@"xWMyZ4YE"] continueWithBlock:^id(BFTask *task) {
  if (task.error) {
    // Something went wrong.
    return task;
  }

  // task.result will be your game score
  return task;
}];

Querying

Often, you‘ll want to find a whole list of objects that match certain criteria, instead of getting a single object by id. To do that, you can use a PFQuery. Any PFQuery can be used with the local datastore just as with the network. The results will include any object you have pinned that matches the query. Any unsaved changes you have made to the object will be considered when evaluating the query. So you can find a local object that matches, even if it was never returned from the server for this particular query.

有时你会想要找到符合某个标准的所有对象的列表,而不是通过id找到的一个单独对象。你可以使用PFQuery来完成这个。任意的PFQuery都可以用于本地存储,使用方法和网络一样。结果会包含所有符合标准的已经被连接的对象。当评估查询时任意你做的没有保存的修改都会被考虑进去。所以即使这个查询你从来没有从服务器上获取过你也可以在本地对象中找到。

PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query fromLocalDatastore];
[query whereKey:@"playerName" equalTo:@"Joe Bob"];
[[query findObjectsInBackground] continueWithBlock:^id(BFTask *task) {
  if (task.error) {
    NSLog(@"Error: %@", task.error);
    return task;
  }

  NSLog(@"Retrieved %d", task.result.count);
  return task;
}];

Security

The same security model that applies to objects in Parse applies to objects in the Local Datastore. Read-write permissions are defined by PFACLs and a user cannot access or modify anything they don‘t have permission to.

被用于Parsec对象的安全模式同样被用于本地数据存储。读写权限定义在PFACL中,并且一个用户在没有权限的情况下无法读取和修改任何的内容。

The only difference is that you won‘t be able to access any data protected by Role based ACLs due to the fact that the Roles are stored on the server. To access this data protected by Role based ACLs, you will need to ignore ACLs when executing a Local Datastore query:

唯一不同的是,你无法访问任何基于ACL的Role表所保护的数据,因为Role数据是存储在服务器上的。为了访问基于ACL的Role表,你需要在执行本地存储查询时忽略ACL:

PFQuery *query = [[[PFQuery queryWithClassName:@"Note"]
                   fromLocalDatastore]
                  ignoreACLs];

Unpinning

When you are done with an object and no longer need it to be in the local datastore, you can simply unpin it. This will free up disk space on the device and keep your queries on the local datastore running quickly.

当你使用完一个对象并且无需它还存留在本地数据存储中时,你可以简单地解除连接。这可以释放你设备的磁盘空间以及让你在本地存储的查询运行得更快。

[gameScore unpinInBackground];

There‘s also a method to unpin several objects at once.

这里还有一个方法可以一次性将多个对象解除连接。

[PFObject unpinAllInBackground:listOfObjects];

Pinning with Labels

Manually pinning and unpinning each object individual is a bit like using malloc and free. It is a very powerful tool, but it can be difficult to manage what objects get stored in complex scenarios. For example, imagine you are making a game with separate high score lists for global high scores and your friends‘ high scores. If one of your friends happens to have a globally high score, you need to make sure you don‘t unpin them completely when you remove them from one of the cached queries. To make these scenarios easier, you can also pin with a label. Labels indicate a group of objects that should be stored together.

手动地连接和解除连接每一个可用的对象有点类似于使用malloc和free。这是一个非常强大的工具,但是在复杂的场景管理这些对象非常困难。例如,假设你正在做一个游戏,游戏中有两个分开的列表分别用来列举全球的高分榜和你的朋友的高分榜。如果你有一个朋友刚好有一个全球性的高分,你需要确保当你从一个缓存查询中移除时没有完全的解除连接。为了使这些场景变得简单,你可以使用标签来进行连接。标签表象一组应该存储在一些的对象。

// Add several objects with a label.
[PFObject pinAllInBackground:someGameScores withName:@"MyScores"];

// Add another object with the same label.
[anotherGameScore pinInBackgroundWithName:@"MyScores"];

To unpin all of the objects with the same label at the same time, you can pass a label to the unpin methods. This saves you from having to manually track which objects are in each group you care about.

为了在同一时间解除所有具有相同标签的对象,你可以传递标签给解除连接的方法。这可以让你从你需要关心的每一组对象中释放出来,无需追踪它们。

[PFObject unpinAllObjectsInBackgroundWithName:@"MyScores"];

Any object will stay in the datastore as long as it is pinned with any label. In other words, if you pin an object with two different labels, and then unpin it with one label, the object will stay in the datastore until you also unpin it with the other label.

不管连接时携带什么标签,这些对象都会一直保存在数据存储中。换句话说,如果你用两个不同的标签去连接同一个对象,然后用其中一个标签解除,对象还会存在于数据存储中,除非你使用另外一个标签去解除连接。

Caching Query Results

Pinning with labels makes it easy to cache the results of queries. You can use one label to pin the results of each different query. To get new results from the network, just do a query and update the pinned objects.

用标签来连接可以使得缓存查询结果变得容易。你可以一个标签来连接每一个不同的查询结果。要从网络上获取新的结果,只需要查询和更新连接的对象即可。

PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query orderByDescending:@"score"];

// Query for new results from the network
[[query findObjectsInBackground] continueWithSuccessBlock:^id(BFTask *task) {
  return [[PFObject unpinAllObjectsInBackgroundWithName:@"HighScores"] continueWithSuccessBlock:^id(BFTask *ignored) {
    // Cache the new results.
    NSArray *scores = task.result;
    return [PFObject pinAllInBackground:scores withName:@"HighScores"];
  }];
}];

When you want to get the cached results for the query, you can then run the same query against the local datastore.

当你想要从查询中获得缓存结果时,你可以在本地存储使用相同的查询语句。

PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query fromLocalDatastore];
[query orderByDescending:@"score"];

[[query findObjectsInBackground] continueWithBlock:^id(BFTask *task) {
  if (task.error) {
    // Something went wrong.
    return task;
  }

  // Yay! Cached scores!
  return task;
}];

Syncing Local Changes

Once you‘ve saved some changes locally, there are a few different ways you can save those changes back to Parse over the network. The easiest way to do this is with saveEventually. When you call saveEventually on a PFObject, it will be pinned until it can be saved. The SDK will make sure to save the object the next time the network is available.

一旦你在本地作了一些修改,你有几种不同的方法存储这些修改至Parse的服务器上。最简单的方法是使用saveEventually。当你调用使用PFObject发送saveEventually消息时,它将会被连接直到被保存。SDK会确保在下次网络可用时保存对象。

[gameScore saveEventually];

If you‘d like to have more control over the way objects are synced, you can keep them in the local datastore until you are ready to save them yourself using saveInBackground. To manage the set of objects that need to be saved, you can again use a label. The fromPinWithName: method on PFQuery makes it easy to fetch just the objects you care about.

如果你想通过同步对象方法进行更多的控制,你可以保持它们在本地存储上直接你使用svaeInBackground保存它们。为了管理需要被保存的对象集合,你可以再次使用标签。PFQuery上的fromPinWithName:方法可以方便地抓取你关心的对象。

PFQuery *query = [PFQuery queryWithClassName:@"GameScore"];
[query fromPinWithName:@"MyChanges"];
[[query findObjectsInBackground] continueWithBlock:^id(BFTask *task) {
  NSArray *scores = task.result;
  for (PFObject *score in scores) {
    [[score saveInBackground] continueWithSuccessBlock:^id(BFTask *task) {
      return [score unpinInBackground];
    }];
  }
  return task;
}];

说明

该篇翻译在很多地方可能都不准确,如果有读者有好的翻译,非常希望可以给个链接让我学习。

时间: 2024-08-04 15:04:30

Parse Local Datastore的相关文章

streamsets http client && json parse && local fs 使用

streamsets 包含了丰富的组件,origin processer destination 测试例子为集成了http client 以及json 处理 启动服务 使用docker 创建pipeline 添加http client 组件 配置http client http 服务地址: https://raw.githubusercontent.com/rongfengliang/json-learning/master/user3.json 添加json parse 配置json pars

Java UNIX时间转换

public static String toLocalTime(String unix) { Long timestamp = Long.parseLong(unix) * 1000; String date = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new java.util.Date(tmestamp)); return date; }http://www.huiyi8.com/jiaoben/ 网页特效代码 pub

libwebsockets 运行问题

/****************************************************************************** * libwebsockets 运行问题 * 说明: * 编译发现libwebsockets运行出问题,解决一下. * * 2017-6-28 深圳 龙华樟坑村 曾剑锋 *****************************************************************************/ 一.错误现象

Performance Snapshot and collect VMware support log bundle by command

From VMware: 1st Command: Normal Support Bundle #vm-support –w/vmfs/volumes/storage_location 2nd Command: Performance Snapshot #vm-support –p -aPerformanceSnapshot:vsi -d 600 -i 5 –w/vmfs/volumes/storage_location Remark: -d:Duration (Second) -i:Inter

Unity3d 开发之 lua 在 IOS 上坑的总结

相同的 lua 代码在安卓上能正常运行,但在 IOS 上可能不会正常运行而导致报红,崩溃等,我在使用 lua 编程时遇到的一些坑总结如下: 1. File.ReadAllText, 诸如以下代码在 ios 上会崩: local path="C:/1.txt"; local file=luanet.import_type("System.IO.File"); local text=file.ReadAllText(path); 正确写法如下: local path=&

csv表格处理(下)--纯JS解析导入csv

多日前的上篇介绍了csv表格,以及JS结合后端PHP解析表格填充表单的方法.其中csv转换成二维数组的时候逻辑比较复杂多坑,幸好PHP有丰富的库函数来处理,而现在用JS解析的话就没有那么幸运了,一切都要自己撸一个出来 或者 →_→ 引入一个库. JS导入CSV--读取文本 JS能前端读取文件吗?以前只有通过 IE的ActiveXObject或者Flash才能本地读取文件.随着H5的出现,这个问题有普遍解了.Talk is cheap,show you the code $.fn.csv2arr

VMware vSphere常见问题汇总(二十四)

220.如果查看hostd和vpxa的状态 有些时候ESXi主机出现故障,我们无法从vSphere client直接连入ESXi主机,这时可以通过DUCI查看状态. a.打开DUCI的Local ESXi Shell,然后Alt+F1进入到命令界面: b.执行如下命令查看hostd服务是否正常运行: /etc/init.d/hostd status 输出类似如下结果: hostd is running c.如果ESXi主机有连接到vCenter Server则还可以查看vCenter Serve

How to Copy files between ESXi hosts using SCP Command

How to Copy files between ESXi hosts using SCP command Enable SSH and allow SSH in ESXi firewall Only prerequisite to copy files between ESXi host using SCP command is that both source and destination ESXi host should have SSH enabled and SSH allowed

使用lua graphql 模块让openresty 支持graphql api

graphql 是一个很不错的api 查询标准语言,已经有一个lua 的版本支持graphql 项目使用docker&&docker-compose 运行 环境准备 模块安装 luarocks install graphql docker镜像准备 模块使用luarocks 安装,默认alpine 镜像是没有安装这个包,我们使用alpine-fat的 FROM openresty/openresty:alpine-fat RUN /usr/local/openresty/luajit/bin