Objective-C++ Preprocessor  5.0 with ARC & GC
C++ classes to enhance syntax and manage reference counting.
objsql.h
Go to the documentation of this file.
1 /*
2  * objsql.h - simple persistence layer for Objective-C classes
3  * ========
4  *
5  * Created by John Holdsworth on 01/04/2009.
6  * Copyright 2009 © John Holdsworth. All Rights Reserved.
7  *
8  * $Id: //depot/ObjCpp/objsql.h#41 $
9  * $DateTime: 2012/09/05 00:02:49 $
10  *
11  * C++ classes to wrap up XCode classes for operator overload of
12  * useful operations such as access to NSArrays and NSDictionary
13  * by subscript or NSString operators such as + for concatenation.
14  *
15  * This works as the Apple Objective-C compiler supports source
16  * which mixes C++ with objective C. To enable this: for each
17  * source file which will include/import this header file, select
18  * it in Xcode and open it's "Info". To enable mixed compilation,
19  * for the file's "File Type" select: "sourcecode.cpp.objcpp".
20  *
21  * For bugs or ommisions please email objcpp@johnholdsworth.com
22  *
23  * Home page for updates and docs: http://objcpp.johnholdsworth.com
24  *
25  * If you find it useful please send a donation via paypal to account
26  * objcpp@johnholdsworth.com. Thanks.
27  *
28  * License
29  * =======
30  *
31  * You may make commercial use of this source in applications without
32  * charge but not sell it as source nor can you remove this notice from
33  * this source if you redistribute. You can make any changes you like
34  * to this code before redistribution but you must annotate them below.
35  *
36  * For further details http://objcpp.johnholdsworth.com/license.html
37  *
38  * THIS CODE IS PROVIDED “AS IS” WITHOUT WARRANTY OF ANY KIND EITHER
39  * EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
40  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
41  *
42  * IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
43  * WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS
44  * THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING
45  * ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT
46  * OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
47  * TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED
48  * BY YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH
49  * ANY OTHER PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN
50  * ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
51  *
52  */
53 
54 #ifndef _objsql_h_
55 #define _objsql_h_
56 #ifdef __cplusplus
57 #import "objcpp.h"
58 
59 #ifdef __IPHONE_OS_VERSION_MIN_REQUIRED
60 #define OOView UIView
61 #else
62 #define OOView NSView
63 #endif
64 
65 @class OOView;
66 
67 #define OOValueDictionary OODictionary<NSValue *>
68 #define cOOValueDictionary const OOValueDictionary &
69 
70 #pragma mark OORecord abstract superclass for records
71 
72 /**
73  Superclass which can be used for all record classes to simplify interface to
74  sqlite database. Any class can be a record class but subclasses of this class
75  can use methods such as insert, update etc and be automatically registered
76  using [registerSubclassesOf:[OORecord class]].
77  */
78 
79 @interface OORecord : NSObject {
80 }
81 
82 + (id)insert OO_AUTORETURNS;
83 + (id)insertWithParent:(id)parent OO_AUTORETURNS;
84 
85 - (id)insert OO_RETURNS;
86 - (id)delete OO_RETURNS;
87 - (void)update;
88 
89 - (void)indate;
90 - (void)upsert;
91 
92 - (int)commit;
93 - (int)rollback;
94 
95 + (OOArray<id>)select;
96 + (OOArray<id>)select:(cOOString)sql;
97 + (OOArray<id>)selectRecordsRelatedTo:(id)record;
98 
99 + (id)record OO_AUTORETURNS;
100 - (OOArray<id>)select;
101 
102 + (int)importFrom:(OOFile &)file delimiter:(cOOString)delim;
103 + (BOOL)exportTo:(OOFile &)file delimiter:(cOOString)delim;
104 
105 - (void)bindToView:(OOView *)view delegate:(id)delegate;
106 - (void)updateFromView:(OOView *)view;
107 
108 @end
109 
110 #pragma mark OOMetaData instances represent a table in the database and it's record class
111 
112 /**
113  Internal class storing meta data about a class and its instance variables for
114  constructing and binding data to an associated "sqlite" table.
115  */
116 
117 @interface OOMetaData : OORecord {
118 @public
124  Class recordClass;
125 }
126 
127 + (OOMetaData *)metaDataForClass:(Class)recordClass OO_RETURNS;
128 - initClass:(Class)aClass;
129 
130 - (OOStringArray)naturalJoinTo:(cOOStringArray)to;
131 - (cOOValueDictionary)encode:(cOOValueDictionary)values;
132 - (cOOValueDictionary)decode:(cOOValueDictionary)values;
133 
134 + (OOArray<id>)import:(const OOArray<OODictionary<OOString> > &)nodes intoClass:(Class)recordClass;
135 + (OOArray<id>)import:(cOOString)string intoClass:(Class)recordClass delimiter:(cOOString)delim;
136 + (OOString)export:(const OOArray<id> &)array delimiter:(cOOString)delim;
137 
138 + (void)bindRecord:(id)record toView:(OOView *)view delegate:(id)delegate;
139 + (void)updateRecord:(id)value fromView:(OOView *)view;
140 
141 @end
142 
143 #pragma mark OOTableCustomization method to alter relatoinship betweeh classes and database objects
144 
145 /**
146  Protocol which can be used to control aspects of the table associated with a particular class.
147  */
148 
150 
151 + (NSString *)ooTableKey;
152 + (NSString *)ooTableSql;
153 + (NSString *)ooTableName;
154 + (NSString *)ooTableTitle;
155 + (NSString *)ooOrderBy;
156 
157 + (NSString *)ooConstraints;
158 
159 - (void)awakeFromDB;
160 
161 @end
162 
163 @class OOAdaptor;
164 
165 #pragma mark OODatabase is the low level interface to a particular database
166 
167 /**
168  Simple persistence class for Objective-C objects using a "sqlite" database. Instances a
169  class are automatically bound to a table with the class name for insert, update and delete.
170 
171  A table with the same name as the class is created automatically when you perform any
172  operation on instances of that class with columns corresponding to the instance variables
173  of the class except those which begin with the character "_". If an instance variable
174  starts with an upper case letter it will be indexed.
175 
176  To update a record, fetch it and call the update: method passing it in as the argument to
177  save it's preious values. You can then modify it and call commit to update it's record.
178  Delete operations on objects also accumulate and need to be commited to take effect.
179  */
180 
181 @interface OODatabase : NSObject {
184 @public
187  char *errmsg;
189 }
190 
191 + (OODatabase *)sharedInstance;
192 + (OODatabase *)sharedInstanceForPath:(cOOString)path;
193 
194 + (BOOL)exec:(cOOString)sql, ...;
195 + (OOArray<id>)select:(cOOString)select intoClass:(Class)recordClass joinFrom:(id)parent;
196 + (OOArray<id>)select:(cOOString)select intoClass:(Class)recordClass;
197 + (OOArray<id>)select:(cOOString)select;
198 
199 + (int)insertArray:(const OOArray<id> &)objects;
200 + (int)deleteArray:(const OOArray<id> &)objects;
201 
202 + (int)insert:(id)object;
203 + (int)delete:(id)object;
204 + (int)update:(id)object;
205 
206 + (int)indate:(id)object;
207 + (int)upsert:(id)object;
208 
209 + (int)commit;
210 + (int)rollback;
211 + (int)commitTransaction;
212 
213 - initPath:(cOOString)path;// __attribute__((objc_method_family(int)));
214 
215 - (OOStringArray)registerSubclassesOf:(Class)recordSuperClass;
216 - (void)registerTableClassesNamed:(cOOStringArray)classes;
217 
218 - (OOArray<OOMetaData *>)tablesRelatedByNaturalJoinFrom:(id)recordClass;
219 - (OOMetaData *)tableMetaDataForClass:(Class)recordClass OO_RETURNS;
220 
221 - (BOOL)exec:(cOOString)sql, ...;
222 - (OOString)stringForSql:(cOOString)fmt, ...;
223 - (id)copyJoinKeysFrom:(id)parent to:(id)newChild;
224 
225 - (OOArray<id>)select:(cOOString)select intoClass:(Class)recordClass joinFrom:(id)parent;
226 - (OOArray<id>)select:(cOOString)select intoClass:(Class)recordClass;
227 - (OOArray<id>)select:(cOOString)select;
228 
229 - (long long)rowIDForRecord:(id)record;
230 - (long long)lastInsertRowID;
231 
232 // all record modifications must be commited
233 - (int)insertArray:(const OOArray<id> &)objects;
234 - (int)deleteArray:(const OOArray<id> &)objects;
235 
236 - (int)insert:(id)object;
237 - (int)delete:(id)object;
238 - (int)update:(id)object;
239 
240 - (int)indate:(id)object;
241 - (int)upsert:(id)object;
242 
243 - (int)commit;
244 - (int)commitTransaction;
245 - (int)rollback;
246 
247 @end
248 
249 #pragma mark OOTable records represent database object
250 
251 /**
252  record class for sqlite3's master table of database objects
253  */
254 
255 @interface OOTable {
257  int rootpage;
259 }
260 @end
261 
262 /**
263  implementation of -[UIView copy] for UITableViewCells
264  */
266 - copyView;
267 @end
268 
269 #pragma mark C++ interface to OODB
270 
271 template <typename ETYPE>
273  return *this = [[OODatabase sharedInstance] select:sql intoClass:[typeof *(ETYPE)0 class] joinFrom:parent];
274 }
275 
276 /**
277  Experimental even more operator overloaded interface to OODatabase.
278  */
279 
280 extern class OOOODatabase {
281 public:
282  BOOL autocommit, autorelease;
284  autocommit = YES;
285  autorelease = NO;
286  }
288  return [OODatabase commit];
289  }
290  oo_inline id autowhatever( id record ) {
291  if ( autocommit )
292  commit();
293  if ( autorelease )
294  OO_RELEASE( record );
295  return autorelease ? nil : record;
296  }
297  oo_inline id operator += ( id record ) {
298  [[OODatabase sharedInstance] insert:record];
299  return autowhatever( record );
300  }
301  oo_inline id operator -= ( id record ) {
302  [[OODatabase sharedInstance] delete:record];
303  return autowhatever( record );
304  }
305  oo_inline id operator *= ( id record ) {
306  [[OODatabase sharedInstance] update:record];
307  return record;
308  }
309  oo_inline OOArray<id> operator >> ( Class recordClass ) {
310  return [recordClass select];
311  }
312 /// oo_inline OOArray<id> operator >> ( id filter ) {
313 // return [[filter class] selectRecordsRelatedTo:filter];
314 // }
315 } OODB;
316 
317 template <typename ETYPE>
319  return arr.fetch();
320 }
321 
322 #endif
323 #endif