added iOS source code
[wl-app.git] / iOS / Pods / Realm / include / RLMAccessor.hpp
1 ////////////////////////////////////////////////////////////////////////////
2 //
3 // Copyright 2017 Realm Inc.
4 //
5 // Licensed under the Apache License, Version 2.0 (the "License");
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 // http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17 ////////////////////////////////////////////////////////////////////////////
18
19 #import "RLMAccessor.h"
20
21 #import "object_accessor.hpp"
22
23 #import "RLMUtil.hpp"
24
25 @class RLMRealm;
26 class RLMClassInfo;
27 class RLMObservationInfo;
28
29 // realm::util::Optional<id> doesn't work because Objective-C types can't
30 // be members of unions with ARC, so this covers the subset of Optional that we
31 // actually need.
32 struct RLMOptionalId {
33     id value;
34     RLMOptionalId(id value) : value(value) { }
35     explicit operator bool() const noexcept { return value; }
36     id operator*() const noexcept { return value; }
37 };
38
39 class RLMAccessorContext {
40 public:
41     // Accessor context interface
42     RLMAccessorContext(RLMAccessorContext& parent, realm::Property const& property);
43
44     id box(realm::List&&);
45     id box(realm::Results&&);
46     id box(realm::Object&&);
47     id box(realm::RowExpr);
48
49     id box(bool v) { return @(v); }
50     id box(double v) { return @(v); }
51     id box(float v) { return @(v); }
52     id box(long long v) { return @(v); }
53     id box(realm::StringData v) { return RLMStringDataToNSString(v) ?: NSNull.null; }
54     id box(realm::BinaryData v) { return RLMBinaryDataToNSData(v) ?: NSNull.null; }
55     id box(realm::Timestamp v) { return RLMTimestampToNSDate(v) ?: NSNull.null; }
56     id box(realm::Mixed v) { return RLMMixedToObjc(v); }
57
58     id box(realm::util::Optional<bool> v) { return v ? @(*v) : NSNull.null; }
59     id box(realm::util::Optional<double> v) { return v ? @(*v) : NSNull.null; }
60     id box(realm::util::Optional<float> v) { return v ? @(*v) : NSNull.null; }
61     id box(realm::util::Optional<int64_t> v) { return v ? @(*v) : NSNull.null; }
62
63     void will_change(realm::Row const&, realm::Property const&);
64     void will_change(realm::Object& obj, realm::Property const& prop) { will_change(obj.row(), prop); }
65     void did_change();
66
67     RLMOptionalId value_for_property(id dict, std::string const&, size_t prop_index);
68     RLMOptionalId default_value_for_property(realm::ObjectSchema const&,
69                                              std::string const& prop);
70
71     bool is_same_list(realm::List const& list, id v) const noexcept;
72
73     template<typename Func>
74     void enumerate_list(__unsafe_unretained const id v, Func&& func) {
75         for (id value in v) {
76             func(value);
77         }
78     }
79
80     template<typename T>
81     T unbox(id v, bool create = false, bool update = false);
82
83     bool is_null(id v) { return v == NSNull.null; }
84     id null_value() { return NSNull.null; }
85     id no_value() { return nil; }
86     bool allow_missing(id v) { return [v isKindOfClass:[NSArray class]]; }
87
88     std::string print(id obj) { return [obj description].UTF8String; }
89
90     // Internal API
91     RLMAccessorContext(RLMObjectBase *parentObject, const realm::Property *property = nullptr);
92     RLMAccessorContext(RLMRealm *realm, RLMClassInfo& info, bool promote=true);
93
94     // The property currently being accessed; needed for KVO things for boxing
95     // List and Results
96     RLMProperty *currentProperty;
97
98 private:
99     __unsafe_unretained RLMRealm *const _realm;
100     RLMClassInfo& _info;
101     // If true, promote unmanaged RLMObjects passed to box() with create=true
102     // rather than copying them
103     bool _promote_existing = true;
104     // Parent object of the thing currently being processed, for KVO purposes
105     __unsafe_unretained RLMObjectBase *const _parentObject = nil;
106
107     // Cached default values dictionary to avoid having to call the class method
108     // for every property
109     NSDictionary *_defaultValues;
110
111     RLMObservationInfo *_observationInfo = nullptr;
112     NSString *_kvoPropertyName = nil;
113
114     id defaultValue(NSString *key);
115     id propertyValue(id obj, size_t propIndex, __unsafe_unretained RLMProperty *const prop);
116 };