rest_kat 0.0.9 → 0.0.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/VERSION +1 -1
- data/lib/model.h.erb +14 -4
- data/lib/model.m.erb +231 -30
- data/lib/rest_kat.rb +202 -56
- data/rest_kat.gemspec +2 -2
- data/src/MSRestSerializable.h +12 -50
- data/src/MSRestSerializable.m +15 -189
- metadata +3 -3
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.0.
|
1
|
+
0.0.10
|
data/lib/model.h.erb
CHANGED
@@ -31,14 +31,17 @@
|
|
31
31
|
//// <%= klass.objc_class %>
|
32
32
|
//////////////////////////////////////////////////////////////////////////////
|
33
33
|
<%end%>
|
34
|
-
@interface <%= klass.objc_class %> :
|
34
|
+
@interface <%= klass.objc_class %> : NSObject<<%=klass.objc_protocols%>>
|
35
|
+
|
36
|
+
|
37
|
+
|
35
38
|
<%klass.properties.each do |property|%>
|
36
|
-
<%if property.klass.
|
37
|
-
// <%=property.name%> :
|
39
|
+
<%if property.klass.is_a? ObjCSequenceOfMap %>
|
40
|
+
// <%=property.name%> : sequence of <%=property.klass.item_class.objc_class%>
|
38
41
|
<%else%>
|
39
42
|
// <%=property.name%> : <%=property.klass.json_type%>
|
40
43
|
<%end%>
|
41
|
-
<%if property.klass.enum?%>
|
44
|
+
<%if property.klass.is_a? ObjCPrimitiveType and property.klass.enum?%>
|
42
45
|
// Enumeration of
|
43
46
|
<%property.klass.enum.each do |e|%>
|
44
47
|
// - <%=e%>
|
@@ -49,6 +52,9 @@
|
|
49
52
|
|
50
53
|
// Initialize all the methods. Called by +initialize ( don't call manually )
|
51
54
|
+ (void)initializeMapping;
|
55
|
+
<%if klass.cached?%>
|
56
|
+
+ (NSEntityDescription *)initializeCoreData;
|
57
|
+
<%end%>
|
52
58
|
|
53
59
|
// Static initializer ( don't call manually )
|
54
60
|
+ (void)initialize;
|
@@ -58,3 +64,7 @@
|
|
58
64
|
@end
|
59
65
|
|
60
66
|
<%end%>
|
67
|
+
|
68
|
+
extern NSMutableArray * entities();
|
69
|
+
|
70
|
+
extern NSManagedObjectModel * managedObjectModel();
|
data/lib/model.m.erb
CHANGED
@@ -1,4 +1,6 @@
|
|
1
1
|
#import "<%=header%>"
|
2
|
+
#import <objc/runtime.h>
|
3
|
+
|
2
4
|
|
3
5
|
<%classes.each do |klass|%>
|
4
6
|
//////////////////////////////////////////////////////////////////////////////
|
@@ -6,41 +8,149 @@
|
|
6
8
|
//////////////////////////////////////////////////////////////////////////////
|
7
9
|
@implementation <%= klass.objc_class %>
|
8
10
|
|
11
|
+
+ (RKObjectMapping *) mapperForParsing
|
12
|
+
{
|
13
|
+
return [[RKObjectManager sharedManager].mappingProvider objectMappingForClass:self];
|
14
|
+
}
|
15
|
+
|
16
|
+
+ (RKObjectMapping *) mapperForSerializing
|
17
|
+
{
|
18
|
+
return [[RKObjectManager sharedManager].mappingProvider serializationMappingForClass:self];
|
19
|
+
}
|
20
|
+
|
9
21
|
<%klass.properties.each do |property|%>
|
10
22
|
@synthesize <%= property.name %>;
|
11
23
|
<%end%>
|
12
24
|
|
13
25
|
+ (void)initialize{
|
26
|
+
[self initializeMapping];
|
14
27
|
<%if klass.resource%>
|
15
28
|
[self initializeRouting];
|
16
29
|
<%end%>
|
17
|
-
|
30
|
+
<%if klass.cached?%>
|
31
|
+
(void)[self initializeCoreData];
|
32
|
+
<%end%>
|
18
33
|
}
|
19
34
|
|
35
|
+
- (NSString*)description
|
36
|
+
{
|
37
|
+
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider serializationMappingForClass:[self class]];
|
38
|
+
RKObjectSerializer * serializer = [RKObjectSerializer serializerWithObject:self mapping:mapper];
|
39
|
+
|
40
|
+
NSError * error;
|
41
|
+
NSString * description = (NSString *)[serializer serializedObjectForMIMEType:RKMIMETypeJSON error: &error];
|
42
|
+
return [description stringByReplacingOccurrencesOfString:@"\"" withString:@"'"];
|
43
|
+
}
|
44
|
+
|
45
|
+
<%if klass.cached? %>
|
46
|
+
+ (NSEntityDescription * )initializeCoreData
|
47
|
+
{
|
48
|
+
static NSEntityDescription * entity;
|
49
|
+
if(entity){
|
50
|
+
return entity;
|
51
|
+
}
|
52
|
+
entity = [[NSEntityDescription alloc] init];
|
53
|
+
entity.name = @"<%=klass.objc_class%>";
|
54
|
+
entity.managedObjectClassName = @"<%=klass.objc_class%>";
|
55
|
+
|
56
|
+
// -------------------------------------------
|
57
|
+
// Define the properties mappings
|
58
|
+
NSMutableArray * properties = [NSMutableArray array];
|
59
|
+
<%klass.primitive_properties.each do |property|%>
|
60
|
+
{
|
61
|
+
// <%= property.name %>
|
62
|
+
NSAttributeDescription * attrDesc = [[NSAttributeDescription alloc] init];
|
63
|
+
attrDesc.name = @"<%= property.name %>";
|
64
|
+
[attrDesc setAttributeType:<%= property.ns_attribute_type %>];
|
65
|
+
[attrDesc setOptional:NO];
|
66
|
+
[properties addObject:attrDesc];
|
67
|
+
}
|
68
|
+
<%end%>
|
69
|
+
|
70
|
+
// ----------------------------------------------
|
71
|
+
// Define 'has one' relationships
|
72
|
+
// ----------------------------------------------
|
73
|
+
<%klass.has_one_properties.each do |property|%>
|
74
|
+
{
|
75
|
+
// <%= property.name %>
|
76
|
+
NSRelationshipDescription * relDesc = [[NSRelationshipDescription alloc] init];
|
77
|
+
[relDesc setDestinationEntity:[<%=property.klass.objc_class%> initializeCoreData]];
|
78
|
+
relDesc.name = @"<%= property.name %>";
|
79
|
+
relDesc.minCount = 1;
|
80
|
+
relDesc.maxCount = 1;
|
81
|
+
relDesc.deleteRule = NSCascadeDeleteRule;
|
82
|
+
[properties addObject:relDesc];
|
83
|
+
}
|
84
|
+
<%end%>
|
85
|
+
|
86
|
+
// ----------------------------------------------
|
87
|
+
// Define 'has many' objects relationships
|
88
|
+
// ----------------------------------------------
|
89
|
+
<%klass.has_many_maps_properties.each do |property|%>
|
90
|
+
{
|
91
|
+
// <%= property.name %>
|
92
|
+
NSRelationshipDescription * relDesc = [[NSRelationshipDescription alloc] init];
|
93
|
+
relDesc.name = @"<%= property.name %>";
|
94
|
+
// Sequence of core data objects
|
95
|
+
[relDesc setDestinationEntity:[<%=property.klass.item_class.objc_class%> initializeCoreData]];
|
96
|
+
relDesc.deleteRule = NSCascadeDeleteRule;
|
97
|
+
[properties addObject:relDesc];
|
98
|
+
}
|
99
|
+
<%end%>
|
100
|
+
|
101
|
+
// ----------------------------------------------
|
102
|
+
// Define 'has many' primitves relationships
|
103
|
+
// ----------------------------------------------
|
104
|
+
<%klass.has_many_maps_properties.each do |property|%>
|
105
|
+
{
|
106
|
+
// Sequence of primitives
|
107
|
+
// This is really a sequence of primitive
|
108
|
+
#warning <%= property.name %> is a sequence of primitive
|
109
|
+
}
|
110
|
+
<%end%>
|
111
|
+
|
112
|
+
[entity setProperties:properties];
|
113
|
+
return entity;
|
114
|
+
}
|
115
|
+
<%end%>
|
116
|
+
|
117
|
+
|
20
118
|
+ (void)initializeMapping{
|
21
119
|
RKObjectMapping* mapping = [RKObjectMapping mappingForClass:[<%=klass.objc_class%> class]];
|
22
120
|
|
23
121
|
// -------------------------------------------
|
24
|
-
// Define
|
25
|
-
|
122
|
+
// Define 'primitive' properties mappings
|
123
|
+
// ----------------------------------------------
|
124
|
+
<%klass.primitive_properties.each do |property|%>
|
26
125
|
[mapping mapKeyPath:@"<%=property.name%>" toAttribute:@"<%=property.name%>"];
|
27
|
-
|
126
|
+
<%end%>
|
127
|
+
<%klass.has_many_primitives_properties.each do |property|%>
|
128
|
+
// NSArray of <%= property.klass.item_class.objc_class %>
|
129
|
+
[mapping mapKeyPath:@"<%=property.name%>" toAttribute:@"<%=property.name%>"];
|
130
|
+
<%end%>
|
28
131
|
|
29
|
-
//
|
30
|
-
// Define
|
31
|
-
|
32
|
-
|
132
|
+
// ----------------------------------------------
|
133
|
+
// Define 'has one' relationships
|
134
|
+
// ----------------------------------------------
|
135
|
+
<%klass.has_one_properties.each do |property|%>
|
33
136
|
{
|
34
|
-
|
35
|
-
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider
|
137
|
+
// <%= property.name %>
|
138
|
+
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider
|
139
|
+
objectMappingForClass:[<%=property.klass.objc_class%> class]];
|
36
140
|
[mapping hasOne:@"<%=property.name%>" withMapping:mapper];
|
37
|
-
|
38
|
-
|
141
|
+
}
|
142
|
+
<%end%>
|
143
|
+
|
144
|
+
// ----------------------------------------------
|
145
|
+
// Define 'has many' relationships
|
146
|
+
// ----------------------------------------------
|
147
|
+
<%klass.has_many_maps_properties.each do |property|%>
|
148
|
+
{
|
149
|
+
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider
|
150
|
+
objectMappingForClass:[<%=property.klass.item_class.objc_class%> class]];
|
39
151
|
[mapping hasMany:@"<%=property.name%>" withMapping:mapper];
|
40
|
-
<%end%>
|
41
152
|
}
|
42
|
-
|
43
|
-
<%end%>
|
153
|
+
<%end%>
|
44
154
|
|
45
155
|
// -------------------------------------------
|
46
156
|
// Register the mapper for the class
|
@@ -56,34 +166,94 @@
|
|
56
166
|
return @"<%= klass.resource.hash[:resource] %>";
|
57
167
|
}
|
58
168
|
|
169
|
+
+ (void)initializeRouting{
|
170
|
+
RKObjectRouter * router = [RKObjectManager sharedManager].router;
|
171
|
+
|
172
|
+
NSString * collectionResource = [self resourcePath];
|
173
|
+
NSString * objectResource = [NSString stringWithFormat:@"%@/(id)", collectionResource];
|
174
|
+
|
175
|
+
<%if klass.resource.create?%>
|
176
|
+
[router routeClass:self toResourcePath:collectionResource forMethod:RKRequestMethodPOST];
|
177
|
+
<%end%>
|
178
|
+
<%if klass.resource.read?%>
|
179
|
+
[router routeClass:self toResourcePath:objectResource forMethod:RKRequestMethodGET];
|
180
|
+
<%end%>
|
181
|
+
<%if klass.resource.update?%>
|
182
|
+
[router routeClass:self toResourcePath:objectResource forMethod:RKRequestMethodPUT];
|
183
|
+
<%end%>
|
184
|
+
<%if klass.resource.delete?%>
|
185
|
+
[router routeClass:self toResourcePath:objectResource forMethod:RKRequestMethodDELETE];
|
186
|
+
<%end%>
|
59
187
|
|
60
|
-
+ (Class) classForResource{
|
61
|
-
return [ <%=klass.resource.objc_resource_type%> class];
|
62
188
|
}
|
63
189
|
|
64
|
-
|
190
|
+
- (BOOL)isNew
|
65
191
|
{
|
66
|
-
|
192
|
+
BOOL hasId = class_getProperty([self class], [@"id" UTF8String]) != NULL;
|
193
|
+
return ([self valueForKey:@"id"] == NULL || !hasId);
|
194
|
+
}
|
195
|
+
|
196
|
+
-(void) saveWithDelegate:(id<RKObjectLoaderDelegate>)delegate
|
197
|
+
{
|
198
|
+
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider objectMappingForClass:[self class]];
|
199
|
+
|
200
|
+
if ([self isNew])
|
201
|
+
{
|
202
|
+
[[RKObjectManager sharedManager] postObject:self mapResponseWith:mapper delegate:delegate];
|
203
|
+
}else{
|
204
|
+
[[RKObjectManager sharedManager] putObject:self mapResponseWith:mapper delegate:delegate];
|
205
|
+
}
|
206
|
+
|
67
207
|
}
|
68
208
|
|
69
|
-
|
209
|
+
- (void)deleteWithDelegate:(id<RKObjectLoaderDelegate>)delegate
|
70
210
|
{
|
71
|
-
|
211
|
+
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider objectMappingForClass:[self class]];
|
212
|
+
[[RKObjectManager sharedManager] deleteObject:self mapResponseWith:mapper delegate:delegate];
|
72
213
|
}
|
73
214
|
|
74
|
-
+ (
|
215
|
+
+ (void) loadItem:(NSNumber *)id
|
216
|
+
withDelegate:(id<RKObjectLoaderDelegate>)delegate;
|
75
217
|
{
|
76
|
-
|
218
|
+
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider objectMappingForClass:[self class]];
|
219
|
+
|
220
|
+
<%= klass.objc_class%> * instance = [[self alloc] init];
|
221
|
+
[instance setValue:id forKey:@"id"];
|
222
|
+
[[RKObjectManager sharedManager] getObject:instance
|
223
|
+
mapResponseWith:mapper
|
224
|
+
delegate:delegate];
|
77
225
|
}
|
78
226
|
|
79
|
-
|
227
|
+
// Load collection
|
228
|
+
+ (void) loadCollectionWithDelegate:(id<RKObjectLoaderDelegate>)delegate
|
80
229
|
{
|
81
|
-
|
230
|
+
RKObjectManager * objectManager = [RKObjectManager sharedManager];
|
231
|
+
RKObjectMapping * mapping = [objectManager.mappingProvider
|
232
|
+
objectMappingForClass:self ];
|
233
|
+
|
234
|
+
[objectManager loadObjectsAtResourcePath:[self resourcePath]
|
235
|
+
objectMapping:mapping
|
236
|
+
delegate:delegate];
|
82
237
|
}
|
83
238
|
|
84
|
-
|
239
|
+
|
240
|
+
// Load collection with query
|
241
|
+
+ (void) loadCollectionThroughQuery:(NSObject *)mappableQueryObject
|
242
|
+
withDelegate:(id<RKObjectLoaderDelegate>)delegate
|
85
243
|
{
|
86
|
-
|
244
|
+
|
245
|
+
RKObjectManager * objectManager = [RKObjectManager sharedManager];
|
246
|
+
RKObjectMapping * mapping = [objectManager.mappingProvider
|
247
|
+
objectMappingForClass:self ];
|
248
|
+
|
249
|
+
|
250
|
+
// Append the dictionary to the resource as query parameters
|
251
|
+
NSString * resourcePath = RKPathAppendQueryParams([self resourcePath], convertToDictionary(mappableQueryObject));
|
252
|
+
|
253
|
+
// Load the objects at the query
|
254
|
+
[objectManager loadObjectsAtResourcePath:resourcePath
|
255
|
+
objectMapping:mapping
|
256
|
+
delegate:delegate];
|
87
257
|
}
|
88
258
|
<%end%>
|
89
259
|
|
@@ -104,12 +274,43 @@ return object;
|
|
104
274
|
- (id) copyWithZone : (NSZone * ) zone
|
105
275
|
{
|
106
276
|
<%=klass.objc_class%> * object = [[<%=klass.objc_class%> allocWithZone:zone] init];
|
107
|
-
|
108
|
-
|
109
|
-
|
277
|
+
<%klass.properties.each do |property|%>
|
278
|
+
object.<%=property.name%> = [self.<%=property.name%> copy];
|
279
|
+
<%end%>
|
110
280
|
return object;
|
111
281
|
}
|
112
282
|
|
283
|
+
|
113
284
|
@end
|
114
285
|
|
115
286
|
<%end%>
|
287
|
+
|
288
|
+
|
289
|
+
|
290
|
+
|
291
|
+
NSMutableArray * entities(){
|
292
|
+
static NSMutableArray * _entities = nil;
|
293
|
+
if(!_entities){
|
294
|
+
_entities = [[NSMutableArray alloc] init];
|
295
|
+
<%classes.each do |klass|%>
|
296
|
+
<%if klass.cached? %>
|
297
|
+
[_entities addObject:[<%=klass.objc_class%> initializeCoreData]];
|
298
|
+
<%end%>
|
299
|
+
<%end%>
|
300
|
+
}
|
301
|
+
return _entities;
|
302
|
+
}
|
303
|
+
|
304
|
+
NSManagedObjectModel * managedObjectModel(){
|
305
|
+
static NSManagedObjectModel *mom = nil;
|
306
|
+
|
307
|
+
if (mom != nil) {
|
308
|
+
return mom;
|
309
|
+
}
|
310
|
+
|
311
|
+
mom = [[NSManagedObjectModel alloc] init];
|
312
|
+
[mom setEntities:entities()];
|
313
|
+
|
314
|
+
return mom;
|
315
|
+
|
316
|
+
}
|
data/lib/rest_kat.rb
CHANGED
@@ -5,6 +5,10 @@ module RestKat
|
|
5
5
|
self.hash = resource
|
6
6
|
end
|
7
7
|
|
8
|
+
def cached?
|
9
|
+
self.hash[:cached]
|
10
|
+
end
|
11
|
+
|
8
12
|
def objc_resource_type
|
9
13
|
hash[:type][:name]
|
10
14
|
end
|
@@ -76,39 +80,115 @@ module RestKat
|
|
76
80
|
self.klass = klass
|
77
81
|
self.name = name
|
78
82
|
end
|
83
|
+
|
84
|
+
def ns_attribute_type
|
85
|
+
# typedef enum {
|
86
|
+
# NSUndefinedAttributeType = 0,
|
87
|
+
# NSInteger16AttributeType = 100,
|
88
|
+
# NSInteger32AttributeType = 200,
|
89
|
+
# NSInteger64AttributeType = 300,
|
90
|
+
# NSDecimalAttributeType = 400,
|
91
|
+
# NSDoubleAttributeType = 500,
|
92
|
+
# NSFloatAttributeType = 600,
|
93
|
+
# NSStringAttributeType = 700,
|
94
|
+
# NSBooleanAttributeType = 800,
|
95
|
+
# NSDateAttributeType = 900,
|
96
|
+
# NSBinaryDataAttributeType = 1000,
|
97
|
+
# NSTransformableAttributeType = 1800,
|
98
|
+
# NSObjectIDAttributeType = 2000
|
99
|
+
# } NSAttributeType;
|
100
|
+
case self.klass.objc_class
|
101
|
+
when "NSNumber"
|
102
|
+
case self.klass.json_type
|
103
|
+
when "int"
|
104
|
+
"NSInteger32AttributeType"
|
105
|
+
when "float"
|
106
|
+
"NSFloatAttributeType"
|
107
|
+
when "bool"
|
108
|
+
"NSBooleanAttributeType"
|
109
|
+
end
|
110
|
+
when "NSDate"
|
111
|
+
"NSDateAttributeType"
|
112
|
+
when "NSString"
|
113
|
+
"NSStringAttributeType"
|
114
|
+
else
|
115
|
+
raise Exception.new("Unknown type #{self.klass.objc_class} for NSAttributeType to be handled for property #{self.name}" )
|
116
|
+
end
|
117
|
+
|
118
|
+
end
|
79
119
|
end
|
80
120
|
|
81
|
-
class
|
82
|
-
|
83
|
-
attr_accessor :sequence_of
|
84
|
-
attr_accessor :type
|
85
|
-
attr_accessor :parent
|
86
|
-
attr_accessor :json_type
|
87
|
-
attr_accessor :node
|
88
|
-
attr_accessor :resource
|
121
|
+
class ObjCSequence
|
122
|
+
attr_accessor :item_class
|
89
123
|
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
124
|
+
def cached
|
125
|
+
item_class.cached
|
126
|
+
end
|
127
|
+
|
128
|
+
def cached=val
|
129
|
+
item_class.cached = val
|
130
|
+
end
|
131
|
+
|
132
|
+
def initialize klass
|
133
|
+
self.item_class = klass
|
134
|
+
end
|
135
|
+
|
136
|
+
def objc_property_decl name
|
137
|
+
"@property (nonatomic, strong) NSArray * #{name}"
|
138
|
+
end
|
139
|
+
|
140
|
+
def objc_property_arg_decl name
|
141
|
+
"#{name}: (NSArray *) #{name}"
|
95
142
|
end
|
143
|
+
|
144
|
+
def json_type
|
145
|
+
"seq"
|
146
|
+
end
|
147
|
+
|
148
|
+
def objc_class
|
149
|
+
"NSArray *"
|
150
|
+
end
|
151
|
+
end
|
152
|
+
|
153
|
+
class ObjCSequenceOfMap < ObjCSequence
|
154
|
+
def initialize klass
|
155
|
+
super klass
|
96
156
|
end
|
157
|
+
end
|
158
|
+
|
159
|
+
class ObjCSequenceOfPrimitve < ObjCSequence
|
160
|
+
def initialize klass
|
161
|
+
super klass
|
162
|
+
end
|
163
|
+
end
|
164
|
+
|
165
|
+
class ObjCType
|
166
|
+
attr_accessor :objc_class
|
167
|
+
attr_accessor :json_type
|
168
|
+
attr_accessor :node
|
169
|
+
attr_accessor :cached
|
97
170
|
|
98
|
-
def
|
99
|
-
|
171
|
+
def objc_property_decl name
|
172
|
+
"@property (nonatomic, strong) #{objc_class} * #{name}"
|
100
173
|
end
|
101
174
|
|
102
|
-
def
|
103
|
-
|
175
|
+
def objc_property_arg_decl name
|
176
|
+
"#{name}: (#{objc_class} *) #{name}"
|
104
177
|
end
|
105
178
|
|
106
|
-
def
|
107
|
-
|
179
|
+
def initialize objc_class, json_type, node
|
180
|
+
self.objc_class = objc_class
|
181
|
+
self.json_type = json_type
|
182
|
+
self.node = node
|
108
183
|
end
|
184
|
+
end
|
109
185
|
|
110
|
-
|
111
|
-
|
186
|
+
class ObjCPrimitiveType < ObjCType
|
187
|
+
attr_accessor :objc_class
|
188
|
+
attr_accessor :json_type
|
189
|
+
attr_accessor :node
|
190
|
+
def initialize objc_class, json_type, node
|
191
|
+
super objc_class, json_type, node
|
112
192
|
end
|
113
193
|
|
114
194
|
def enum?
|
@@ -118,13 +198,68 @@ module RestKat
|
|
118
198
|
def enum
|
119
199
|
node["enum"]
|
120
200
|
end
|
201
|
+
end
|
121
202
|
|
122
|
-
|
123
|
-
|
203
|
+
class ObjCMapType < ObjCType
|
204
|
+
attr_accessor :properties
|
205
|
+
attr_accessor :sequence_of
|
206
|
+
attr_accessor :resource
|
207
|
+
|
208
|
+
def cached?
|
209
|
+
cached
|
124
210
|
end
|
125
211
|
|
126
|
-
def
|
127
|
-
|
212
|
+
def cached=val
|
213
|
+
@cached = val
|
214
|
+
if properties
|
215
|
+
properties.each do |property|
|
216
|
+
property.klass.cached = val
|
217
|
+
end
|
218
|
+
end
|
219
|
+
end
|
220
|
+
|
221
|
+
def primitive_properties
|
222
|
+
properties.select do |p|
|
223
|
+
p.klass.is_a? ObjCPrimitiveType
|
224
|
+
end
|
225
|
+
end
|
226
|
+
|
227
|
+
def has_one_properties
|
228
|
+
properties.select do |p|
|
229
|
+
p.klass.is_a? ObjCMapType
|
230
|
+
end
|
231
|
+
end
|
232
|
+
|
233
|
+
def has_many_properties
|
234
|
+
properties.select do |p|
|
235
|
+
p.klass.is_a? ObjCSequence
|
236
|
+
end
|
237
|
+
end
|
238
|
+
|
239
|
+
def has_many_primitives_properties
|
240
|
+
properties.select do |p|
|
241
|
+
p.klass.is_a? ObjCSequenceOfPrimitve
|
242
|
+
end
|
243
|
+
end
|
244
|
+
|
245
|
+
def has_many_maps_properties
|
246
|
+
properties.select do |p|
|
247
|
+
p.klass.is_a? ObjCSequenceOfMap
|
248
|
+
end
|
249
|
+
end
|
250
|
+
|
251
|
+
def objc_super_class
|
252
|
+
if resource
|
253
|
+
"MSRestSerializableResource"
|
254
|
+
else
|
255
|
+
"MSRestSerializable"
|
256
|
+
end
|
257
|
+
end
|
258
|
+
|
259
|
+
def objc_protocols
|
260
|
+
["NSCopying"].tap do |p|
|
261
|
+
p << "MSRestResource" if resource
|
262
|
+
end.join ', '
|
128
263
|
end
|
129
264
|
|
130
265
|
def objc_properites_arg_list_decl
|
@@ -133,11 +268,10 @@ module RestKat
|
|
133
268
|
end.join "\n "
|
134
269
|
end
|
135
270
|
|
136
|
-
def initialize
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
self.node = node
|
271
|
+
def initialize objc_class, json_type, node
|
272
|
+
super objc_class, json_type, node
|
273
|
+
self.properties = nil
|
274
|
+
self.cached = false
|
141
275
|
end
|
142
276
|
|
143
277
|
end
|
@@ -188,10 +322,11 @@ module RestKat
|
|
188
322
|
Resource.new(resource_hash).tap do |resource|
|
189
323
|
# Generate the query classes first
|
190
324
|
resource.queries.each do |query|
|
191
|
-
|
325
|
+
# Query objects do not get cached in core data
|
326
|
+
to_objective_c_class node:query["type"], cached:false
|
192
327
|
end
|
193
328
|
# Generate the resource classes next
|
194
|
-
klass = to_objective_c_class resource.hash[:type]
|
329
|
+
klass = to_objective_c_class node:resource.hash[:type], cached:resource.cached?
|
195
330
|
# Mark this class as being a REST resource
|
196
331
|
klass.resource = resource
|
197
332
|
end
|
@@ -218,7 +353,7 @@ module RestKat
|
|
218
353
|
end
|
219
354
|
|
220
355
|
def find_processed_class node
|
221
|
-
classes.find{|c| c.
|
356
|
+
classes.find{|c| c.objc_class == node[:name]}
|
222
357
|
end
|
223
358
|
|
224
359
|
# Perform a depth first traversal of the type tree. The resulting
|
@@ -226,49 +361,47 @@ module RestKat
|
|
226
361
|
# the code generation phase this classes will be injected last into
|
227
362
|
# the code making sure the dependencies are define in the correct
|
228
363
|
# order.
|
229
|
-
def to_objective_c_class
|
364
|
+
def to_objective_c_class options
|
365
|
+
|
366
|
+
node = options[:node]
|
367
|
+
cached = options[:cached]
|
368
|
+
|
230
369
|
unless node
|
231
|
-
raise Exception.new("node is nil
|
370
|
+
raise Exception.new("node is nil")
|
232
371
|
end
|
233
372
|
|
234
373
|
case node[:type]
|
235
374
|
when "map"
|
236
375
|
|
237
376
|
unless klass = find_processed_class(node)
|
238
|
-
klass =
|
377
|
+
klass = ObjCMapType.new(node[:name], node[:type], node)
|
239
378
|
|
240
379
|
klass.properties = node[:mapping].collect do |property_name, property_node|
|
241
380
|
if property_node[:type] == "map"
|
242
381
|
property_node[:name] ||= IosMapping.obj_c_type_for_property(node, property_name)
|
243
382
|
end
|
244
|
-
ObjCProperty.new(to_objective_c_class(property_node), property_name)
|
383
|
+
ObjCProperty.new(to_objective_c_class(node:property_node, cached:cached), property_name)
|
245
384
|
end
|
246
385
|
|
247
386
|
self.classes << klass
|
248
387
|
end
|
249
388
|
|
389
|
+
# Inherit caching from parent as the whole object graph
|
390
|
+
# of cached objects needs to go into Core Data
|
391
|
+
klass.cached = cached
|
392
|
+
|
250
393
|
when "seq"
|
251
|
-
klass =
|
252
|
-
if node[:sequence].length != 1
|
253
|
-
raise "Only support sequence of map with one map type"
|
254
|
-
end
|
255
|
-
sequence_node = node[:sequence].first
|
256
|
-
if sequence_node["type"] == "map"
|
257
|
-
if not sequence_node["name"]
|
258
|
-
raise Exception.new ("sequence of map nodes must have a :name to generate the objective C types")
|
259
|
-
end
|
260
|
-
klass.sequence_of = to_objective_c_class sequence_node
|
261
|
-
end
|
394
|
+
klass = create_sequence(node, cached)
|
262
395
|
when "str", "text"
|
263
|
-
klass =
|
396
|
+
klass = ObjCPrimitiveType.new(node[:name] || "NSString", node[:type], node)
|
264
397
|
when "int"
|
265
|
-
klass =
|
398
|
+
klass = ObjCPrimitiveType.new(node[:name] || "NSNumber", node[:type], node)
|
266
399
|
when "float"
|
267
|
-
klass =
|
400
|
+
klass = ObjCPrimitiveType.new(node[:name] || "NSNumber", node[:type], node)
|
268
401
|
when "bool"
|
269
|
-
klass =
|
402
|
+
klass = ObjCPrimitiveType.new(node[:name] || "NSNumber", node[:type], node)
|
270
403
|
when "any"
|
271
|
-
klass =
|
404
|
+
klass = ObjCPrimitiveType.new(node[:name] || "NSObject", node[:type], node)
|
272
405
|
else
|
273
406
|
raise Exception.new("Unhandled type '#{node[:type]} for node with name #{node[:name]}")
|
274
407
|
end
|
@@ -278,6 +411,20 @@ module RestKat
|
|
278
411
|
klass
|
279
412
|
|
280
413
|
end
|
414
|
+
|
415
|
+
def create_sequence node, cached
|
416
|
+
if node[:sequence].length != 1
|
417
|
+
raise "Only support sequence of map with one map type"
|
418
|
+
end
|
419
|
+
item_class = to_objective_c_class node:node[:sequence].first, cached:cached
|
420
|
+
if item_class.is_a? ObjCMapType
|
421
|
+
ObjCSequenceOfMap.new(item_class)
|
422
|
+
elsif item_class.is_a? ObjCPrimitiveType
|
423
|
+
ObjCSequenceOfPrimitve.new(item_class)
|
424
|
+
else
|
425
|
+
raise Exception.new "#{item_class.class} cannot be handled here"
|
426
|
+
end
|
427
|
+
end
|
281
428
|
end
|
282
429
|
end
|
283
430
|
|
@@ -296,7 +443,6 @@ module RestKat
|
|
296
443
|
model.h.erb
|
297
444
|
model.m.erb
|
298
445
|
rest_kat.rb
|
299
|
-
validator.rb
|
300
446
|
].collect do |d|
|
301
447
|
File.expand_path "../#{d}", __FILE__
|
302
448
|
end
|
@@ -328,11 +474,11 @@ module RestKat
|
|
328
474
|
tgt_m = File.join api_location, "MSRestSerializable.m"
|
329
475
|
|
330
476
|
|
331
|
-
t0 = file tgt_h
|
477
|
+
t0 = file tgt_h => src_h do
|
332
478
|
cp src_h, tgt_h, :verbose => true
|
333
479
|
end
|
334
480
|
|
335
|
-
t1 = file tgt_m
|
481
|
+
t1 = file tgt_m => src_m do
|
336
482
|
cp src_m, tgt_m, :verbose => true
|
337
483
|
end
|
338
484
|
|
data/rest_kat.gemspec
CHANGED
@@ -5,11 +5,11 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{rest_kat}
|
8
|
-
s.version = "0.0.
|
8
|
+
s.version = "0.0.10"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = [%q{Brad Phelan}]
|
12
|
-
s.date = %q{2011-11-
|
12
|
+
s.date = %q{2011-11-28}
|
13
13
|
s.description = %q{The generated source code is a layer on top of the iOS REST framework http://restkit.org/}
|
14
14
|
s.email = %q{brad.phelan@mysugr.com}
|
15
15
|
s.extra_rdoc_files = [
|
data/src/MSRestSerializable.h
CHANGED
@@ -10,73 +10,35 @@
|
|
10
10
|
#import "NSDate+APIDate.h"
|
11
11
|
#import <RestKit/RestKit.h>
|
12
12
|
|
13
|
-
|
14
|
-
// The mapper for this instance
|
15
|
-
- (RKObjectMapping *) _mapper;
|
13
|
+
extern NSDictionary * convertToDictionary( NSObject * object);
|
16
14
|
|
17
|
-
|
18
|
-
- (RKObjectMapping *) _serializer;
|
15
|
+
extern NSString * convertToFormURLEncoded( NSObject * object);
|
19
16
|
|
20
|
-
|
17
|
+
extern NSString * convertToJSON( NSObject * object);
|
21
18
|
|
22
|
-
- (NSString *)convertToFormURLEncoded;
|
23
19
|
|
24
|
-
|
20
|
+
@protocol MSRestResource
|
25
21
|
|
22
|
+
// Is the object new or not
|
26
23
|
- (BOOL)isNew;
|
27
|
-
@end
|
28
|
-
|
29
|
-
@interface MSRestSerializableResource : MSRestSerializable
|
30
|
-
|
31
|
-
#pragma mark methods to be overridden
|
32
|
-
|
33
|
-
+ (Class) classForResource;
|
34
|
-
|
35
|
-
// The resource path. If this
|
36
|
-
+ (NSString *) resourcePath;
|
37
|
-
|
38
|
-
// Is the resource a singleton or a collection
|
39
|
-
+ (bool) isSingleton;
|
40
|
-
|
41
|
-
// Can the client create resources
|
42
|
-
+ (bool) canCreate;
|
43
|
-
|
44
|
-
// Can the client read resources
|
45
|
-
+ (bool) canRead;
|
46
|
-
|
47
|
-
// Can the client update resources
|
48
|
-
+ (bool) canUpdate;
|
49
|
-
|
50
|
-
// Can the client delete resources
|
51
|
-
+ (bool) canDelete;
|
52
|
-
|
53
|
-
#pragma mark helpers
|
54
|
-
|
55
|
-
// The router for this class
|
56
|
-
+ (RKObjectRouter *) router;
|
57
|
-
|
58
|
-
// Intialize the routing module. Must
|
59
|
-
// be called from +initialize in a
|
60
|
-
// subclass or the logic will not
|
61
|
-
// work.
|
62
|
-
+ (void) initializeRouting;
|
63
24
|
|
25
|
+
+ (void)initializeRouting;
|
64
26
|
|
65
|
-
//
|
27
|
+
// Save a single record
|
66
28
|
-(void) saveWithDelegate:(id<RKObjectLoaderDelegate>)delegate;
|
67
29
|
|
68
|
-
//
|
30
|
+
// Delete a single record
|
69
31
|
- (void)deleteWithDelegate:(id<RKObjectLoaderDelegate>)delegate;
|
70
32
|
|
71
|
-
//
|
72
|
-
+ (void)
|
73
|
-
|
33
|
+
// Load a single record
|
34
|
+
+ (void) loadItem:(NSNumber *)id
|
35
|
+
withDelegate:(id<RKObjectLoaderDelegate>)delegate;
|
74
36
|
|
75
37
|
// Load collection
|
76
38
|
+ (void) loadCollectionWithDelegate:(id<RKObjectLoaderDelegate>)delegate;
|
77
39
|
|
78
40
|
// Load collection with query
|
79
|
-
+ (void) loadCollectionThroughQuery:(
|
41
|
+
+ (void) loadCollectionThroughQuery:(NSObject *)mappableQueryObject
|
80
42
|
withDelegate:(id<RKObjectLoaderDelegate>)delegate;
|
81
43
|
|
82
44
|
@end
|
data/src/MSRestSerializable.m
CHANGED
@@ -10,210 +10,36 @@
|
|
10
10
|
#import <RestKit/RestKit.h>
|
11
11
|
#import <objc/runtime.h>
|
12
12
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
- (RKObjectMapping *) _mapper
|
17
|
-
{
|
18
|
-
RKObjectMappingProvider * provider = [RKObjectManager sharedManager].mappingProvider;
|
19
|
-
RKObjectMapping * mapping = [provider objectMappingForClass:[self class]];
|
20
|
-
return mapping;
|
21
|
-
|
22
|
-
|
23
|
-
}
|
24
|
-
|
25
|
-
- (RKObjectMapping *) _serializer
|
13
|
+
static RKObjectSerializer * serializerFor(NSObject * serializable)
|
26
14
|
{
|
27
|
-
|
28
|
-
|
29
|
-
return mapping;
|
30
|
-
}
|
15
|
+
RKObjectMapping * mapper = [[RKObjectManager sharedManager].mappingProvider
|
16
|
+
serializationMappingForClass:serializable.class];
|
31
17
|
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
{
|
36
|
-
BOOL hasId = class_getProperty([self class], [@"id" UTF8String]) != NULL;
|
37
|
-
return ([self valueForKey:@"id"] == NULL || !hasId);
|
18
|
+
return [RKObjectSerializer
|
19
|
+
serializerWithObject:serializable
|
20
|
+
mapping:mapper];
|
38
21
|
}
|
39
22
|
|
40
|
-
|
41
|
-
- (NSDictionary *)convertToDictionary
|
23
|
+
NSDictionary * convertToDictionary(NSObject * serializable)
|
42
24
|
{
|
43
25
|
NSError * error;
|
44
|
-
|
45
|
-
|
46
|
-
return [querySerializer serializedObject:&error];
|
26
|
+
return [serializerFor(serializable)
|
27
|
+
serializedObject:&error];
|
47
28
|
}
|
48
29
|
|
49
30
|
|
50
|
-
|
31
|
+
NSString * convertToJSON(NSObject * serializable)
|
51
32
|
{
|
52
|
-
RKObjectSerializer * serializer = [RKObjectSerializer serializerWithObject:self mapping:[self _serializer]];
|
53
33
|
NSError * error;
|
54
|
-
|
55
|
-
|
34
|
+
return (NSString *)[serializerFor(serializable)
|
35
|
+
serializedObjectForMIMEType:RKMIMETypeJSON error:&error];
|
56
36
|
}
|
57
37
|
|
58
|
-
|
38
|
+
NSString * convertToFormURLEncoded(NSObject * serializable)
|
59
39
|
{
|
60
|
-
RKObjectSerializer * serializer = [RKObjectSerializer serializerWithObject:self mapping:[self _serializer]];
|
61
|
-
|
62
40
|
NSError * error;
|
63
|
-
|
64
|
-
|
65
|
-
}
|
66
|
-
|
67
|
-
- (NSString*)description
|
68
|
-
{
|
69
|
-
|
70
|
-
|
71
|
-
RKObjectSerializer * serializer = [RKObjectSerializer serializerWithObject:self mapping:[self _serializer]];
|
72
|
-
|
73
|
-
NSError * error;
|
74
|
-
NSString * description = (NSString *)[serializer serializedObjectForMIMEType:RKMIMETypeJSON error: &error];
|
75
|
-
return [description stringByReplacingOccurrencesOfString:@"\"" withString:@"'"];
|
76
|
-
}
|
77
|
-
|
78
|
-
- (id)copyWithZone:(NSZone *)zone
|
79
|
-
{
|
80
|
-
return [[MSRestSerializable allocWithZone:zone] init];
|
81
|
-
}
|
82
|
-
|
83
|
-
@end
|
84
|
-
|
85
|
-
@implementation MSRestSerializableResource
|
86
|
-
|
87
|
-
+ (RKObjectRouter *) router
|
88
|
-
{
|
89
|
-
return [RKObjectManager sharedManager].router;
|
90
|
-
}
|
91
|
-
|
92
|
-
+ (Class) classForResource
|
93
|
-
{
|
94
|
-
NSAssert(NO, @"Stub implementation. Must be implemented in subclass");
|
95
|
-
return NULL;
|
96
|
-
}
|
97
|
-
|
98
|
-
|
99
|
-
+ (void) initializeRouting
|
100
|
-
{
|
101
|
-
RKObjectRouter * router = [self router];
|
102
|
-
|
103
|
-
NSString * collectionResource = [self resourcePath];
|
104
|
-
NSString * objectResource = [NSString stringWithFormat:@"%@/:id", collectionResource];
|
105
|
-
|
106
|
-
if([self isSingleton])
|
107
|
-
{
|
108
|
-
objectResource = collectionResource;
|
109
|
-
}
|
110
|
-
|
111
|
-
if ([self canCreate]){
|
112
|
-
[router routeClass:self toResourcePath:collectionResource forMethod:RKRequestMethodPOST];
|
113
|
-
}
|
114
|
-
|
115
|
-
if ([self canRead]){
|
116
|
-
[router routeClass:self toResourcePath:objectResource forMethod:RKRequestMethodGET];
|
117
|
-
}
|
118
|
-
|
119
|
-
if ([self canUpdate])
|
120
|
-
{
|
121
|
-
[router routeClass:self toResourcePath:objectResource forMethod:RKRequestMethodPUT];
|
122
|
-
}
|
123
|
-
|
124
|
-
if ([self canDelete])
|
125
|
-
{
|
126
|
-
[router routeClass:self toResourcePath:objectResource forMethod:RKRequestMethodDELETE];
|
127
|
-
}
|
128
|
-
|
129
|
-
}
|
130
|
-
|
131
|
-
|
132
|
-
+ (NSString *) resourcePath{
|
133
|
-
NSAssert(NO, @"Not implemented");
|
134
|
-
return NULL;
|
135
|
-
}
|
136
|
-
|
137
|
-
+ (bool) isSingleton{
|
138
|
-
return true;
|
139
|
-
}
|
140
|
-
+ (bool) canCreate{
|
141
|
-
return true;
|
142
|
-
}
|
143
|
-
+ (bool) canRead{
|
144
|
-
return true;
|
145
|
-
}
|
146
|
-
+ (bool) canUpdate{
|
147
|
-
return true;
|
148
|
-
}
|
149
|
-
+ (bool) canDelete{
|
150
|
-
return true;
|
151
|
-
}
|
152
|
-
|
153
|
-
|
154
|
-
- (void) saveWithDelegate:(id<RKObjectLoaderDelegate>)delegate
|
155
|
-
{
|
156
|
-
if ([self isNew])
|
157
|
-
{
|
158
|
-
NSAssert(self.class.canCreate, @"Object must allow create to be created");
|
159
|
-
NSLog(@"Creating new object\n%@", self);
|
160
|
-
// Save a new object
|
161
|
-
[[RKObjectManager sharedManager] postObject:self mapResponseWith:[self _mapper] delegate:delegate];
|
162
|
-
}else{
|
163
|
-
NSAssert(self.class.canUpdate, @"Object must allow update to be updated");
|
164
|
-
NSLog(@"Updating object\n%@", self);
|
165
|
-
// Update the object as it allready has an id
|
166
|
-
[[RKObjectManager sharedManager] putObject:self mapResponseWith:[self _mapper] delegate:delegate];
|
167
|
-
}
|
168
|
-
}
|
169
|
-
|
170
|
-
- (void)deleteWithDelegate:(id<RKObjectLoaderDelegate>)delegate
|
171
|
-
{
|
172
|
-
NSAssert(self.class.canDelete, @"Object must allow delete to be deleted");
|
173
|
-
[[RKObjectManager sharedManager] deleteObject:self mapResponseWith:[self _mapper] delegate:delegate];
|
174
|
-
}
|
175
|
-
|
176
|
-
// Find an instance by id
|
177
|
-
+ (void) find:(NSNumber *)id withDelegate:(id<RKObjectLoaderDelegate>)delegate
|
178
|
-
{
|
179
|
-
MSRestSerializable * instance = [[self alloc] init];
|
180
|
-
[instance setValue:id forKey:@"id"];
|
181
|
-
[[RKObjectManager sharedManager] getObject:instance
|
182
|
-
mapResponseWith:[instance _mapper]
|
183
|
-
delegate:delegate];
|
184
|
-
}
|
185
|
-
|
186
|
-
// Load collection
|
187
|
-
+ (void) loadCollectionWithDelegate:(id<RKObjectLoaderDelegate>)delegate
|
188
|
-
{
|
189
|
-
RKObjectManager * objectManager = [RKObjectManager sharedManager];
|
190
|
-
RKObjectMapping * mapping = [objectManager.mappingProvider
|
191
|
-
objectMappingForClass:self ];
|
192
|
-
|
193
|
-
[objectManager loadObjectsAtResourcePath:[self resourcePath]
|
194
|
-
objectMapping:mapping
|
195
|
-
delegate:delegate];
|
196
|
-
}
|
197
|
-
|
198
|
-
|
199
|
-
// Load collection with query
|
200
|
-
+ (void) loadCollectionThroughQuery:(MSRestSerializable *)mappableQueryObject
|
201
|
-
withDelegate:(id<RKObjectLoaderDelegate>)delegate
|
202
|
-
{
|
203
|
-
|
204
|
-
RKObjectManager * objectManager = [RKObjectManager sharedManager];
|
205
|
-
RKObjectMapping * mapping = [objectManager.mappingProvider
|
206
|
-
objectMappingForClass:self ];
|
207
|
-
|
208
|
-
|
209
|
-
// Append the dictionary to the resource as query parameters
|
210
|
-
NSString * resourcePath = RKPathAppendQueryParams([self resourcePath], [mappableQueryObject convertToDictionary]);
|
211
|
-
|
212
|
-
// Load the objects at the query
|
213
|
-
[objectManager loadObjectsAtResourcePath:resourcePath
|
214
|
-
objectMapping:mapping
|
215
|
-
delegate:delegate];
|
41
|
+
return (NSString *)[serializerFor(serializable)
|
42
|
+
serializedObjectForMIMEType:RKMIMETypeFormURLEncoded error: &error];
|
216
43
|
}
|
217
44
|
|
218
45
|
|
219
|
-
@end
|
metadata
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
name: rest_kat
|
3
3
|
version: !ruby/object:Gem::Version
|
4
4
|
prerelease:
|
5
|
-
version: 0.0.
|
5
|
+
version: 0.0.10
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
8
8
|
- Brad Phelan
|
@@ -10,7 +10,7 @@ autorequire:
|
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
12
|
|
13
|
-
date: 2011-11-
|
13
|
+
date: 2011-11-28 00:00:00 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: kwalify
|
@@ -110,7 +110,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
110
110
|
requirements:
|
111
111
|
- - ">="
|
112
112
|
- !ruby/object:Gem::Version
|
113
|
-
hash: -
|
113
|
+
hash: -4151209479782223092
|
114
114
|
segments:
|
115
115
|
- 0
|
116
116
|
version: "0"
|