Realm framework

realm.io/cn/

Introduction:

  • Realm is a cross-platform mobile database engine that supports iOS, OS X (Objective-C and Swift), and Android

  • – realm. IO /cn/news/jp-…

  • Comments: the ORM

    • OBJECT/RELATIONALMAPPING (ORM)
    • ORM technology provides a bridge between objects and relationships
  • Better performance than sqlite and coredata

  • Easy to use compared to sqlite, coredata is much simpler to use and easier to get started

  • IO /docs/objc/l…

  • Auxiliary tool

    • Realm Browser Visually accesses the Realm database
    • IO /sync/realm-…
    • Xcode plug-in github.com/alcatraz/Al… Realms can be created quickly

Click release.zip to download the plugin. Model objects can be stored

Realm of actual combat

1. Simple data manipulation

  • 1.1 Preparation: Creating the data model that inherits from RLMObject is required
  • How objects are created
    1. Common create
    2. Quickly create initWithValue + dictionary key-value pairs + array with property order using methods in parent class RLMObject
    3. Pay attention to
    • Note that all required properties must be assigned before the object is added to a Realm
    • Since Realm has a good semantic interpretation system inside its own engine, many of Objective C’s attributes, such as nonatomic, atomic, strong, copy, and weak, are ignored. Therefore, to avoid misunderstanding, the official recommendation is not to use any attribute features when writing data models.
  • 1.2 Use the RLMRealm object to save the specified model
    1. RLMRealm *realm = [RLMRealm defaultRealm];
    2. Write mode 1 Enables write transactions[realm beginWriteTransaction];Adding model Objects[realm addObject:stu];Commit write transaction[realm commitWriteTransaction];
    3. Write Mode 2[realm transactionWithBlock:^{[realm addObject:stu];}];
    4. Write Mode 3[Stu createInRealm: realm withValue: @ {@ "stu_id" : @ 22, @ "name:" @ "dong-mei ma 2," @ "age" : @ 666}].
  • 1.3 Using RLMRealm objects, update the specified model
    • Approach 1 updates objects directly in a transaction
    [realm beginWriteTransaction]; Stu. Name = @" stu "; [realm commitWriteTransaction];Copy the code
    • Method 2 Update data based on the primary key
        1. Models requiring operations must implement method + (NSString *)primaryKey to return the primaryKey
        1. Call the method [realm addOrUpdateObject: STU2] in the transaction;
    • Method 3 Update data based on the primary key
        1. Models requiring operations must implement method + (NSString *)primaryKey to return the primaryKey
        1. Invoke a method in a transaction[Stu createInRealm: realm withValue: @ {@ "stu_id" : @ 22, @ "name:" @ "dong-mei ma 2," @ "age" : @ 666}].
  • 1.4 Delete data using RLMRealm objects
    • Deletes the specified object

      • In the transaction
        • [realm deleteObject:stu];
        • Note: Model objects must be fetched from the REALM database, not created yourself
        • RLMObject *obj = [realm objectWithClassName:@"Stu" forPrimaryKey:@2];
    • DeleteAllObjects in transaction [realm deleteAllObjects];

  • 1.5 Query data using RLMRealm objects
    • Matters needing attention
        1. All queries, including queries and property accesses, are lazy-loaded in Realm, and the corresponding data can only be read when the property is accessed
        1. The query result is not a copy of the data: modifying the query result (in a write transaction) directly modifies the data on the hard disk.
        1. RLMResults will be updated at any time once the retrieval has been performed
    • Query all[Stu allObjects]
    • Conditions of the queryRLMResults<Stu *> * STUS = [Stu objectsWhere:@"name = 'ma Di '"];
    • The sorting[stus sortedResultsUsingProperty:@"name" ascending:YES];
    • Chain query

    Meaning Performs a secondary query based on the query result[STUS objectsWhere:@"address beginswith 'Beijing '"];

    • paging
      • Note:
        • The result of the query object is lazy loading, only when the actual access, the corresponding object will be loaded, so, here paging, in fact, is from all the collection pages can be obtained
        • Code demo
        RLMResults<Dog *> *dogs = [Dog allObjects];  
            for (NSInteger i = 0; i < 5; i++) {
             Dog *dog = dogs[i];
          // ...
        }
        Copy the code
  • 2. Supported data types

BOOL, bool, int, NSInteger, long, long long, float, double, NSString, NSDate, NSData, And NSNumber – Note: set type is not supported – solution – serialized to NSData for storage – converted to RLMArray for storage – Case store image

  • 3. The relationship between
    • One-to-one relationship: when one object holds another object, such as a person who has a pet 🐶
    • The more relationship
        1. In Dog, follow the specified protocol method
        • RLM_ARRAY_TYPE(Dog)
        • The RLM_ARRAY_TYPE macro creates a protocol that allows the use of the RLMArray syntax.
        1. In Person, you define attributes
        • @property (nonatomic, strong) RLMArray<Dog *> *dogs;
        • Note: Although you can assign nil to the RLMArray property, this is only used to “empty” the array, not to remove it. This means that you can always add an object to an RLMArray property, even if it is set to nil.
    • Inverse relationship
      • Example: people have dogs, and dogs have corresponding owners?
      • To solve
          1. Dog defines @Property (readonly) RLMLinkingObjects *master;
          1. Implement protocol methods that indicate link relationships
        + (NSDictionary<NSString *,RLMPropertyDescriptor *> *)linkingObjectsProperties {
        return @{
        @"master": [RLMPropertyDescriptor descriptorWithClass:NSClassFromString(@"Stu") propertyName:@"dogs"]
            };
        }
        Copy the code
    1. Nullable attribute & default value & ignore attribute
    • By default, the value of an attribute can be null. If you force an attribute to be non-null, you can use the following method
    • Follow protocol approach
    + (NSArray *)requiredProperties {
        return @[@"name"];
    }
    Copy the code
    • Property If assigned to nil again, an exception error is thrown
    • You can also set the default value
    + (NSDictionary *)defaultPropertyValues {
        return @{@"name": @""};
    }
    Copy the code
    • Ignore the attribute
      • Some attributes that you don’t want to store
      • Implementation method+ (NSArray *)ignoredProperties
    • The development experience can be used to create computational properties by ignoring properties & read-only properties to complete the storage and acquisition of collections and UIImage objects
    1. notice
    • Realm instances will send notifications to Realm instances on other threads every time a write transaction commits
      1. Get Realm Notifications
    Token = [realm addNotificationBlock:^(NSString *notification, RLMRealm * realm) {// Received notification of change, need to do}];Copy the code
      1. Remove notification [token stop];

    Note: The returned token must be held

    1. Realm database
    • User mechanism
      • Different users use different database files
      • Implementation scheme
          1. Different users, using different databases
+ (void)setDefaultRealmForUser:(NSString *)username { RLMRealmConfiguration *config = [RLMRealmConfiguration defaultConfiguration]; // Use the default directory, FileURL = [[[config.fileurl = [[[config.fileurl URLByDeletingLastPathComponent]URLByAppendingPathComponent:username]URLByAppendingPathExtension:@"realm"]; / / apply this configuration to the default Realm of database RLMRealmConfiguration setDefaultConfiguration: config]; }Copy the code
- Open the database in read-only modeCopy the code
RLMRealmConfiguration *config = [RLMRealmConfiguration defaultConfiguration]; FileURL = [[NSBundle mainBundle] URLForResource:@"MyBundledData" withExtension:@"realm"]; Config. readOnly = YES; // Open the file in read-only mode because application packets are not writable. / / by configuring database Realm open RLMRealm * Realm = [RLMRealm realmWithConfiguration: config error: nil]; RLMResults<Dog *> *dogs = [Dog objectsInRealm: Realm where:@"age > 5"];Copy the code
- Database file deletion note :1. Need to delete database files and auxiliary file code combatCopy the code
NSFileManager *manager = [NSFileManager defaultManager]; RLMRealmConfiguration *config = [RLMRealmConfiguration defaultConfiguration]; NSArray<NSURL *> *realmFileURLs = @[ config.fileURL, [config.fileURL URLByAppendingPathExtension:@"lock"], [config.fileURL URLByAppendingPathExtension:@"log_a"], [config.fileURL URLByAppendingPathExtension:@"log_b"], [config.fileURL URLByAppendingPathExtension:@"note"] ]; for (NSURL *URL in realmFileURLs) { NSError *error = nil; [manager removeItemAtURL:URL error:&error]; If (error) {// Handle error}}Copy the code
    1. Database Migration
    • Applies when the data model has been modified
    • Data structure migration
    / / in [AppDelegate didFinishLaunchingWithOptions:] configured RLMRealmConfiguration * config = [RLMRealmConfiguration defaultConfiguration]; // Set the new schema version. This version number must be higher than the version number previously used (set to 0 if you have never set schemaVersion before) config.schemaversion = 1; // Set the closure, Config. migrationBlock = ^(RLMMigration *migration, Uint64_t oldSchemaVersion) {// If (oldSchemaVersion < 1) {// Do nothing! Realm detects new and removed properties and automatically updates the database schema on disk}}; / / tell Realm to use the new configuration for the default Realm database objects [RLMRealmConfiguration setDefaultConfiguration: config]; // Now that we've told Realm how to handle schema changes, opening the file will automatically migrate [RLMRealm defaultRealm];Copy the code
    • Data migration
    // enumerateObjects:block: Each file in method to traverse the stored in the Realm of a "Person" object [migration enumerateObjects: Person. The className block: ^ (RLMObject * oldObject, RLMObject *newObject) {// Merge the names, NewObject [@"fullName"] = [NSString stringWithFormat:@"%@ %@",oldObject[@"firstName"],oldObject[@"lastName"]]; }];Copy the code
    • Property renaming
    [migration renamePropertyForClass:Person.className oldName:@"yearsSinceBirth" newName:@"age"];
    Copy the code
    • Multi-version incremental migration
      • scenario
  • Version 0
 // v0
 // @interface Person : RLMObject
 // @property NSString *firstName;
 // @property NSString *lastName;
 // @property int age;
 @end
Copy the code
  • Version 1
// v1 // @interface Person : RLMObject // @property NSString *fullName; // @property int age; // @endCopy the code
  • Version 2
// v2 @interface Person : RLMObject @property NSString *fullName; @property NSString *email; // new property @property int age; @endCopy the code
  • Migrating core code
// enumerateObjects:block: Each file in traverse the stored in the Realm of a "Person" object [migration enumerateObjects: Person. The className block: ^ (RLMObject * oldObject, RLMObject *newObject) {// Only if schema version 0 of the Realm database, If (oldSchemName < 1) {newObject[@"fullName"] = [NSString stringWithFormat:@"%@ %@", OldObject [@"firstName"], oldObject[@"lastName"]];} If (oldSchemaVersion < 2) {newObject[@"email"] = @"";}}];Copy the code