Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/joshdholtz/jsonapi-ios
A library for loading data from a JSON API datasource.
https://github.com/joshdholtz/jsonapi-ios
Last synced: 4 days ago
JSON representation
A library for loading data from a JSON API datasource.
- Host: GitHub
- URL: https://github.com/joshdholtz/jsonapi-ios
- Owner: joshdholtz
- License: mit
- Created: 2013-12-23T20:49:45.000Z (almost 11 years ago)
- Default Branch: master
- Last Pushed: 2018-10-25T04:50:10.000Z (about 6 years ago)
- Last Synced: 2024-10-27T22:17:50.580Z (16 days ago)
- Language: Objective-C
- Homepage:
- Size: 284 KB
- Stars: 182
- Watchers: 11
- Forks: 33
- Open Issues: 14
-
Metadata Files:
- Readme: README.md
- Changelog: CHANGELOG.md
- License: LICENSE
Awesome Lists containing this project
README
# JSONAPI - iOS
[![Build Status](https://travis-ci.org/joshdholtz/jsonapi-ios.png?branch=master)](https://travis-ci.org/joshdholtz/jsonapi-ios)
![](https://cocoapod-badges.herokuapp.com/v/JSONAPI/badge.png)
[![Join the chat at https://gitter.im/joshdholtz/jsonapi-ios](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/joshdholtz/jsonapi-ios?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)A library for loading data from a [JSON API](http://jsonapi.org) datasource. Parses JSON API data into models with support for linking of properties and other resources.
### Quick Usage
```objc
NSDictionary *json = [self responseFromAPIRequest];
JSONAPI *jsonAPI = [JSONAPI jsonAPIWithDictionary:json];ArticleResource *article = jsonAPI.resource;
NSLog(@"Title: %@", article.title);
```For some full examples on how to use everything, please see the tests - https://github.com/joshdholtz/jsonapi-ios/blob/master/Project/JSONAPITests/JSONAPITests.m
### Updates
Version | Changes
--- | ---
**1.0.7** | Added `meta` and `setMeta` to `JSONAPIResource` and `JSONAPIResourceBase` (https://github.com/joshdholtz/jsonapi-ios/pull/43).
**1.0.6** | Improved resource parsing and added parsing of `selfLinks` (https://github.com/joshdholtz/jsonapi-ios/pull/35). Thanks to [ artcom](https://github.com/ artcom) for helping! Also removed the need to define `setIdProperty` and `setSelfLinkProperty` in every resource (automatically mapped in the init of `JSONAPIResourceDescriptor`)
**1.0.5** | Fix 1-to-many relationships serialization according to JSON API v1.0 (https://github.com/joshdholtz/jsonapi-ios/pull/34). Thanks to [RafaelKayumov](https://github.com/RafaelKayumov) for helping!
**1.0.4** | Add support for empty to-one relationship according to JSON API v1.0 (https://github.com/joshdholtz/jsonapi-ios/pull/33). Thanks to [RafaelKayumov](https://github.com/RafaelKayumov) for helping!
**1.0.3** | Add ability to map different types of objects (https://github.com/joshdholtz/jsonapi-ios/pull/32). Thanks to [ealeksandrov](https://github.com/ealeksandrov) for helping!
**1.0.2** | Just some bug fixes. Thanks to [christianklotz](https://github.com/christianklotz) for helping again!
**1.0.1** | Now safely checks for `NSNull` in the parsed JSON. Thanks to [christianklotz](https://github.com/christianklotz) for that fix!
**1.0.0** | We did it team! We are at the `JSON API 1.0 final` spec. Resources now use `JSONAPIResourceDescriptor` for more explicit definitions. **HUGE** thanks to [jkarmstr](https://github.com/jkarmstr) for doing all the dirty work. Also thanks to [edopelawi ](https://github.com/edopelawi ), [BenjaminDigeon](https://github.com/BenjaminDigeon), and [christianklotz](https://github.com/christianklotz) for some bug fixes!
**1.0.0-rc1** | Rewrote core of `JSONAPI` and `JSONAPIResource` and all unit tests to be up to spec with JSON API spec 1.0.0-rc3. Removed `JSONAPIResourceLinker`. Added `JSONAPIErrorResource`
**0.2.0** | Added `NSCopying` and `NSCoded` to `JSONAPIResource`; Added `JSONAPIResourceFormatter` to format values before getting mapped - [more info](#formatter)
**0.1.2** | `JSONAPIResource` IDs can either be numbers or strings (thanks [danylhebreux](https://github.com/danylhebreux)); `JSONAPIResource` subclass can have mappings defined to set JSON values into properties automatically - [more info](#resource-mappings)
**0.1.1** | Fixed linked resources with links so they actually link to other linked resources
**0.1.0** | Initial release### Features
- Allows resource types to be created into subclasses of `JSONAPIResource`
- Set mapping for `JSONAPIResource` subclass to set JSON values and relationships into properties## Installation
### Drop-in Classes
Clone the repository and drop in the .h and .m files from the "Classes" directory into your project.### CocoaPods
JSONAPI is available through [CocoaPods](http://cocoapods.org), to install
it simply add the following line to your Podfile:pod 'JSONAPI', '~> 1.0.7'
## Classes/protocols
For some full examples on how to use everything, please see the tests - https://github.com/joshdholtz/jsonapi-ios/blob/master/Project/JSONAPITests/JSONAPITests.m### JSONAPI
`JSONAPI` parses and validates a JSON API document into a usable object. This object holds the response as an NSDictionary but provides methods to accomdate the JSON API format such as `meta`, `errors`, `linked`, `resources`, and `includedResources`.### JSONAPIResource
Protocol of an object that is available for JSON API serialization. When developing model classes for use with JSON-API, it is suggested that classes be derived from `JSONAPIResourceBase`, but that is not required. An existing model class can be adapted for JSON-API by implementing this protocol.### JSONAPIResourceBase
`JSONAPIResourceBase` is an object (that gets subclassed) that holds data for each resource in a JSON API document. This objects holds the "id" as `ID` and link for self as `selfLink` as well as attributes and relationships defined by descriptors (see below)### JSONAPIResourceDescriptor
`+ (JSONAPIResourceDescriptor*)descriptor` should be overwritten to define descriptors for mapping of JSON keys and relationships into properties of a subclassed JSONAPIResource.## Full Example
### ViewController.m
```objc
NSDictionary *json = [self responseFromAPIRequest];
JSONAPI *jsonAPI = [JSONAPI jsonAPIWithDictionary:json];ArticleResource *article = jsonAPI.resource;
NSLog(@"Title: %@", article.title);
NSLog(@"Author: %@ %@", article.author.firstName, article.author.lastName);
NSLog(@"Comment Count: %ld", article.comments.count);
```### ArticleResource.h
```objc
@interface ArticleResource : JSONAPIResourceBase
@property (nonatomic, strong) NSString *title;
@property (nonatomic, strong) PeopleResource *author;
@property (nonatomic, strong) NSDate *date;
@property (nonatomic, strong) NSArray *comments;@end
```### ArticleResource.m
```objc
@implementation ArticleResourcestatic JSONAPIResourceDescriptor *__descriptor = nil;
+ (JSONAPIResourceDescriptor*)descriptor {
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
__descriptor = [[JSONAPIResourceDescriptor alloc] initWithClass:[self class] forLinkedType:@"articles"];[__descriptor addProperty:@"title"];
[__descriptor addProperty:@"date"
withDescription:[[JSONAPIPropertyDescriptor alloc] initWithJsonName:@"date" withFormat:[NSDateFormatter RFC3339DateFormatter]]];[__descriptor hasOne:[PeopleResource class] withName:@"author"];
[__descriptor hasMany:[CommentResource class] withName:@"comments"];
});return __descriptor;
}@end
```
### PeopleResource.h
```objc
@interface PeopleResource : JSONAPIResourceBase@property (nonatomic, strong) NSString *firstName;
@property (nonatomic, strong) NSString *lastName;
@property (nonatomic, strong) NSString *twitter;@end
```### PeopleResource.m
```objc
@implementation PeopleResourcestatic JSONAPIResourceDescriptor *__descriptor = nil;
+ (JSONAPIResourceDescriptor*)descriptor {
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
__descriptor = [[JSONAPIResourceDescriptor alloc] initWithClass:[self class] forLinkedType:@"people"];[__descriptor addProperty:@"firstName" withDescription:[[JSONAPIPropertyDescriptor alloc] initWithJsonName:@"first-name"]];
[__descriptor addProperty:@"lastName" withJsonName:@"last-name"];
[__descriptor addProperty:@"twitter"];
});return __descriptor;
}@end
```### CommentResource.h
```objc
@interface CommentResource : JSONAPIResourceBase@property (nonatomic, strong) NSString *text;
@property (nonatomic, strong) PeopleResource *author;@end
```### CommentResource.m
```objc
@implementation CommentResourcestatic JSONAPIResourceDescriptor *__descriptor = nil;
+ (JSONAPIResourceDescriptor*)descriptor {
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
__descriptor = [[JSONAPIResourceDescriptor alloc] initWithClass:[self class] forLinkedType:@"comments"];[__descriptor addProperty:@"text" withJsonName:@"body"];
[__descriptor hasOne:[PeopleResource class] withName:@"author"];
});return __descriptor;
}@end
```## Advanced
### How to do custom "sub-resources" mappings
Sometimes you may have parts of a resource that need to get mapped to something more specific than just an `NSDictionary`. Below is an example on how to map an `NSDictionary` to non-JSONAPIResource models.We are essentially creating a property descriptor that maps to a private property on the resource. We then override that properties setter and do our custom mapping there.
#### Resource part of JSON API Response
```js
"attributes":{
"title": "Something something blah blah blah"
"image": {
"large": "http://someimageurl.com/large",
"medium": "http://someimageurl.com/medium",
"small": "http://someimageurl.com/small"
}
}
```#### ArticleResource.h
```objc
@interface ArticleResource : JSONAPIResourceBase
@property (nonatomic, strong) NSString *title;
// The properties we are pulling out of a a "images" dictionary
@property (nonatomic, storng) NSString *largeImageUrl;
@property (nonatomic, storng) NSString *mediumImageUrl;
@property (nonatomic, storng) NSString *smallImageUrl;@end
```#### ArticleResource.m
```objc
@interface ArticleResource()// Private variable used to store raw NSDictionary
// We will override the setter and set our custom properties there
@property (nonatomic, strong) NSDictionary *rawImage;@end
@implementation ArticleResource
static JSONAPIResourceDescriptor *__descriptor = nil;
+ (JSONAPIResourceDescriptor*)descriptor {
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
__descriptor = [[JSONAPIResourceDescriptor alloc] initWithClass:[self class] forLinkedType:@"articles"];[__descriptor addProperty:@"title"];
[__descriptor addProperty:@"rawImage" withDescription:[[JSONAPIPropertyDescriptor alloc] initWithJsonName:@"image"]];});
return __descriptor;
}- (void)setRawImage:(NSDictionary*)rawImage {
_rawImage = rawImage;// Pulling the large, medium, and small urls out when
// this property gets set by the JSON API parser
_largeImageUrl = _rawImage[@"large"];
_mediumImageUrl = _rawImage[@"medium"];
_smallImageUrl = _rawImage[@"small"];
}@end
```
## Author
Josh Holtz, [email protected], [@joshdholtz](https://twitter.com/joshdholtz)
## License
JSONAPI is available under the MIT license. See the LICENSE file for more info.