added iOS source code
[wl-app.git] / iOS / Pods / Realm / include / object_store.hpp
1 ////////////////////////////////////////////////////////////////////////////
2 //
3 // Copyright 2015 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 #ifndef REALM_OBJECT_STORE_HPP
20 #define REALM_OBJECT_STORE_HPP
21
22 #include "property.hpp"
23
24 #include <realm/table_ref.hpp>
25 #include <realm/util/optional.hpp>
26
27 #include <functional>
28 #include <string>
29 #include <vector>
30 namespace realm {
31 class Group;
32 class Schema;
33 class SchemaChange;
34 class StringData;
35 enum class SchemaMode : uint8_t;
36
37 namespace util {
38 template<typename... Args>
39 std::string format(const char* fmt, Args&&... args);
40 }
41
42 class ObjectStore {
43 public:
44     // Schema version used for uninitialized Realms
45     static constexpr uint64_t NotVersioned = std::numeric_limits<uint64_t>::max();
46
47     // Column name used for subtables which store an array
48     static constexpr const char* const ArrayColumnName = "!ARRAY_VALUE";
49
50     // get the last set schema version
51     static uint64_t get_schema_version(Group const& group);
52
53     // set the schema version without any checks
54     // and the tables for the schema version and the primary key are created if they don't exist
55     // NOTE: must be performed within a write transaction
56     static void set_schema_version(Group& group, uint64_t version);
57
58     // check if all of the changes in the list can be applied automatically, or
59     // throw if any of them require a schema version bump and migration function
60     static void verify_no_migration_required(std::vector<SchemaChange> const& changes);
61
62     // Similar to above, but returns a bool rather than throwing/not throwing
63     static bool needs_migration(std::vector<SchemaChange> const& changes);
64
65     // check if any of the schema changes in the list are forbidden in
66     // additive-only mode, and if any are throw an exception
67     // returns true if any of the changes are not no-ops
68     static bool verify_valid_additive_changes(std::vector<SchemaChange> const& changes,
69                                               bool update_indexes=false);
70
71     // check if the schema changes made by a different process made any changes
72     // which will prevent us from being able to continue (such as removing a
73     // property we were relying on)
74     static void verify_valid_external_changes(std::vector<SchemaChange> const& changes);
75
76     static void verify_compatible_for_immutable_and_readonly(std::vector<SchemaChange> const& changes);
77
78     // check if changes is empty, and throw an exception if not
79     static void verify_no_changes_required(std::vector<SchemaChange> const& changes);
80
81     // updates a Realm from old_schema to the given target schema, creating and updating tables as needed
82     // passed in target schema is updated with the correct column mapping
83     // optionally runs migration function if schema is out of date
84     // NOTE: must be performed within a write transaction
85     static void apply_schema_changes(Group& group, uint64_t schema_version,
86                                      Schema& target_schema, uint64_t target_schema_version,
87                                      SchemaMode mode, std::vector<SchemaChange> const& changes,
88                                      std::function<void()> migration_function={});
89
90     static void apply_additive_changes(Group&, std::vector<SchemaChange> const&, bool update_indexes);
91
92     // get a table for an object type
93     static realm::TableRef table_for_object_type(Group& group, StringData object_type);
94     static realm::ConstTableRef table_for_object_type(Group const& group, StringData object_type);
95
96     // get existing Schema from a group
97     static Schema schema_from_group(Group const& group);
98
99     // get the property for a existing column in the given table. return none if the column is reserved internally.
100     // NOTE: is_primary won't be set for the returned property.
101     static util::Optional<Property> property_for_column_index(ConstTableRef& table, size_t column_index);
102
103     static void set_schema_columns(Group const& group, Schema& schema);
104
105     // deletes the table for the given type
106     static void delete_data_for_object(Group& group, StringData object_type);
107
108     // indicates if this group contains any objects
109     static bool is_empty(Group const& group);
110
111     // renames the object_type's column of the old_name to the new name
112     static void rename_property(Group& group, Schema& schema, StringData object_type, StringData old_name, StringData new_name);
113
114     // get primary key property name for object type
115     static StringData get_primary_key_for_object(Group const& group, StringData object_type);
116
117     // sets primary key property for object type
118     // must be in write transaction to set
119     static void set_primary_key_for_object(Group& group, StringData object_type, StringData primary_key);
120
121     static std::string table_name_for_object_type(StringData class_name);
122     static StringData object_type_for_table_name(StringData table_name);
123
124 private:
125     friend class ObjectSchema;
126 };
127
128 class InvalidSchemaVersionException : public std::logic_error {
129 public:
130     InvalidSchemaVersionException(uint64_t old_version, uint64_t new_version);
131     uint64_t old_version() const { return m_old_version; }
132     uint64_t new_version() const { return m_new_version; }
133 private:
134     uint64_t m_old_version, m_new_version;
135 };
136
137 class DuplicatePrimaryKeyValueException : public std::logic_error {
138 public:
139     DuplicatePrimaryKeyValueException(std::string object_type, std::string property);
140
141     std::string const& object_type() const { return m_object_type; }
142     std::string const& property() const { return m_property; }
143 private:
144     std::string m_object_type;
145     std::string m_property;
146 };
147
148 // Schema validation exceptions
149 struct ObjectSchemaValidationException : public std::logic_error {
150     ObjectSchemaValidationException(std::string message) : logic_error(std::move(message)) {}
151
152     template<typename... Args>
153     ObjectSchemaValidationException(const char* fmt, Args&&... args)
154     : std::logic_error(util::format(fmt, std::forward<Args>(args)...)) { }
155 };
156
157 struct SchemaValidationException : public std::logic_error {
158     SchemaValidationException(std::vector<ObjectSchemaValidationException> const& errors);
159 };
160
161 struct SchemaMismatchException : public std::logic_error {
162     SchemaMismatchException(std::vector<ObjectSchemaValidationException> const& errors);
163 };
164
165 struct InvalidSchemaChangeException : public std::logic_error {
166     InvalidSchemaChangeException(std::vector<ObjectSchemaValidationException> const& errors);
167 };
168 } // namespace realm
169
170 #endif /* defined(REALM_OBJECT_STORE_HPP) */