[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"project-6720":3},{"id":4,"name":5,"fullName":6,"owner":7,"repo":5,"description":8,"homepage":9,"htmlUrl":10,"language":11,"languages":10,"totalLinesOfCode":10,"stars":12,"forks":13,"watchers":14,"openIssues":15,"contributorsCount":16,"subscribersCount":16,"size":16,"stars1d":16,"stars7d":16,"stars30d":17,"stars90d":16,"forks30d":16,"starsTrendScore":16,"compositeScore":18,"rankGlobal":10,"rankLanguage":10,"license":19,"archived":20,"fork":20,"defaultBranch":21,"hasWiki":22,"hasPages":22,"topics":23,"createdAt":10,"pushedAt":10,"updatedAt":24,"readmeContent":25,"aiSummary":26,"trendingCount":16,"starSnapshotCount":16,"syncStatus":17,"lastSyncTime":27,"discoverSource":28},6720,"ObjectMapper","tristanhimmelman\u002FObjectMapper","tristanhimmelman","Simple JSON Object mapping written in Swift","",null,"Swift",9148,1029,210,57,0,2,65.24,"MIT License",false,"master",true,[],"2026-06-12 04:00:30","ObjectMapper\n============\n[![CocoaPods](https:\u002F\u002Fimg.shields.io\u002Fcocoapods\u002Fv\u002FObjectMapper.svg)](https:\u002F\u002Fgithub.com\u002Ftristanhimmelman\u002FObjectMapper)\n[![Carthage compatible](https:\u002F\u002Fimg.shields.io\u002Fbadge\u002FCarthage-compatible-4BC51D.svg?style=flat)](https:\u002F\u002Fgithub.com\u002FCarthage\u002FCarthage)\n[![Swift Package Manager](https:\u002F\u002Frawgit.com\u002Fjlyonsmith\u002Fartwork\u002Fmaster\u002FSwiftPackageManager\u002Fswiftpackagemanager-compatible.svg)](https:\u002F\u002Fswift.org\u002Fpackage-manager\u002F)\n[![Build Status](https:\u002F\u002Ftravis-ci.org\u002Ftristanhimmelman\u002FObjectMapper.svg?branch=master)](https:\u002F\u002Ftravis-ci.org\u002Ftristanhimmelman\u002FObjectMapper)\n\nObjectMapper is a framework written in Swift that makes it easy for you to convert your model objects (classes and structs) to and from JSON. \n\n- [Features](#features)\n- [The Basics](#the-basics)\n- [Mapping Nested Objects](#easy-mapping-of-nested-objects)\n- [Custom Transformations](#custom-transforms)\n- [Subclassing](#subclasses)\n- [Generic Objects](#generic-objects)\n- [Mapping Context](#mapping-context)\n- [ObjectMapper + Alamofire](#objectmapper--alamofire) \n- [ObjectMapper + Realm](#objectmapper--realm)\n- [Projects using ObjectMapper](#projects-using-objectmapper)\n- [To Do](#to-do)\n- [Contributing](#contributing)\n- [Installation](#installation)\n\n# Features:\n- Mapping JSON to objects\n- Mapping objects to JSON\n- Nested Objects (stand alone, in arrays or in dictionaries)\n- Custom transformations during mapping\n- Struct support\n- [Immutable support](#immutablemappable-protocol)\n\n# The Basics\nTo support mapping, a class or struct just needs to implement the ```Mappable``` protocol which includes the following functions:\n```swift\ninit?(map: Map)\nmutating func mapping(map: Map)\n```\nObjectMapper uses the ```\u003C-``` operator to define how each member variable maps to and from JSON.\n\n```swift\nclass User: Mappable {\n    var username: String?\n    var age: Int?\n    var weight: Double!\n    var array: [Any]?\n    var dictionary: [String : Any] = [:]\n    var bestFriend: User?                       \u002F\u002F Nested User object\n    var friends: [User]?                        \u002F\u002F Array of Users\n    var birthday: Date?\n\n    required init?(map: Map) {\n\n    }\n\n    \u002F\u002F Mappable\n    func mapping(map: Map) {\n        username    \u003C- map[\"username\"]\n        age         \u003C- map[\"age\"]\n        weight      \u003C- map[\"weight\"]\n        array       \u003C- map[\"arr\"]\n        dictionary  \u003C- map[\"dict\"]\n        bestFriend  \u003C- map[\"best_friend\"]\n        friends     \u003C- map[\"friends\"]\n        birthday    \u003C- (map[\"birthday\"], DateTransform())\n    }\n}\n\nstruct Temperature: Mappable {\n    var celsius: Double?\n    var fahrenheit: Double?\n\n    init?(map: Map) {\n\n    }\n\n    mutating func mapping(map: Map) {\n        celsius \t\u003C- map[\"celsius\"]\n        fahrenheit \t\u003C- map[\"fahrenheit\"]\n    }\n}\n```\n\nOnce your class implements `Mappable`, ObjectMapper allows you to easily convert to and from JSON. \n\nConvert a JSON string to a model object:\n```swift\nlet user = User(JSONString: JSONString)\n```\n\nConvert a model object to a JSON string:\n```swift\nlet JSONString = user.toJSONString(prettyPrint: true)\n```\n\nAlternatively, the `Mapper.swift` class can also be used to accomplish the above (it also provides extra functionality for other situations):\n```swift\n\u002F\u002F Convert JSON String to Model\nlet user = Mapper\u003CUser>().map(JSONString: JSONString)\n\u002F\u002F Create JSON String from Model\nlet JSONString = Mapper().toJSONString(user, prettyPrint: true)\n```\n\nObjectMapper can map classes composed of the following types:\n- `Int`\n- `Bool`\n- `Double`\n- `Float`\n- `String`\n- `RawRepresentable` (Enums)\n- `Array\u003CAny>`\n- `Dictionary\u003CString, Any>`\n- `Object\u003CT: Mappable>`\n- `Array\u003CT: Mappable>`\n- `Array\u003CArray\u003CT: Mappable>>`\n- `Set\u003CT: Mappable>` \n- `Dictionary\u003CString, T: Mappable>`\n- `Dictionary\u003CString, Array\u003CT: Mappable>>`\n- Optionals of all the above\n- Implicitly Unwrapped Optionals of the above\n\n## `Mappable` Protocol\n\n#### `mutating func mapping(map: Map)` \nThis function is where all mapping definitions should go. When parsing JSON, this function is executed after successful object creation. When generating JSON, it is the only function that is called on the object.\n\n#### `init?(map: Map)` \nThis failable initializer is used by ObjectMapper for object creation. It can be used by developers to validate JSON prior to object serialization. Returning nil within the function will prevent the mapping from occuring. You can inspect the JSON stored within the `Map` object to do your validation:\n```swift\nrequired init?(map: Map){\n\t\u002F\u002F check if a required \"name\" property exists within the JSON.\n\tif map.JSON[\"name\"] == nil {\n\t\treturn nil\n\t}\n}\n```\n\n## `StaticMappable` Protocol\n`StaticMappable` is an alternative to `Mappable`. It provides developers with a static function that is used by ObjectMapper for object initialization instead of `init?(map: Map)`. \n\nNote: `StaticMappable`, like `Mappable`, is a sub protocol of `BaseMappable` which is where the `mapping(map: Map)` function is defined.\n\n#### `static func objectForMapping(map: Map) -> BaseMappable?` \nObjectMapper uses this function to get objects to use for mapping. Developers should return an instance of an object that conforms to `BaseMappable` in this function. This function can also be used to:\n- validate JSON prior to object serialization\n- provide an existing cached object to be used for mapping\n- return an object of another type (which also conforms to `BaseMappable`) to be used for mapping. For instance, you may inspect the JSON to infer the type of object that should be used for mapping ([see examples in ClassClusterTests.swift](https:\u002F\u002Fgithub.com\u002FHearst-DD\u002FObjectMapper\u002Fblob\u002Fmaster\u002FTests\u002FObjectMapperTests\u002FClassClusterTests.swift#L67))\n\nIf you need to implement ObjectMapper in an extension, you will need to adopt this protocol instead of `Mappable`. \n\n## `ImmutableMappable` Protocol\n\n`ImmutableMappable` provides the ability to map immutable properties. This is how `ImmutableMappable` differs from `Mappable`:\n\n\u003Ctable>\n  \u003Ctr>\n    \u003Cth>ImmutableMappable\u003C\u002Fth>\n    \u003Cth>Mappable\u003C\u002Fth>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Cth colspan=\"2\">Properties\u003C\u002Fth>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Ctd>\n\u003Cpre>\n\u003Cstrong>let\u003C\u002Fstrong> id: Int\n\u003Cstrong>let\u003C\u002Fstrong> name: String?\n\u003C\u002Fpre>\n  \u003C\u002Ftd>\n    \u003Ctd>\n\u003Cpre>\nvar id: Int!\nvar name: String?\n\u003C\u002Fpre>\n    \u003C\u002Ftd>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Cth colspan=\"2\">JSON -> Model\u003C\u002Fth>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Ctd>\n\u003Cpre>\ninit(map: Map) \u003Cstrong>throws\u003C\u002Fstrong> {\n  id   = \u003Cstrong>try\u003C\u002Fstrong> map.value(\"id\")\n  name = \u003Cstrong>try?\u003C\u002Fstrong> map.value(\"name\")\n}\n\u003C\u002Fpre>\n  \u003C\u002Ftd>\n    \u003Ctd>\n\u003Cpre>\nmutating func mapping(map: Map) {\n  id   \u003C- map[\"id\"]\n  name \u003C- map[\"name\"]\n}\n\u003C\u002Fpre>\n    \u003C\u002Ftd>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Cth colspan=\"2\">Model -> JSON\u003C\u002Fth>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Ctd>\n\u003Cpre>\nfunc mapping(map: Map) {\n  id   \u003Cstrong>>>>\u003C\u002Fstrong> map[\"id\"]\n  name \u003Cstrong>>>>\u003C\u002Fstrong> map[\"name\"]\n}\n\u003C\u002Fpre>\n    \u003C\u002Ftd>\n    \u003Ctd>\n\u003Cpre>\nmutating func mapping(map: Map) {\n  id   \u003C- map[\"id\"]\n  name \u003C- map[\"name\"]\n}\n\u003C\u002Fpre>\n    \u003C\u002Ftd>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Cth colspan=\"2\">Initializing\u003C\u002Fth>\n  \u003C\u002Ftr>\n  \u003Ctr>\n    \u003Ctd>\n\u003Cpre>\n\u003Cstrong>try\u003C\u002Fstrong> User(JSONString: JSONString)\n\u003C\u002Fpre>\n    \u003C\u002Ftd>\n    \u003Ctd>\n\u003Cpre>\nUser(JSONString: JSONString)\n\u003C\u002Fpre>\n    \u003C\u002Ftd>\n  \u003C\u002Ftr>\n\u003C\u002Ftable>\n\n#### `init(map: Map) throws`\n\nThis throwable initializer is used to map immutable properties from the given `Map`. Every immutable property should be initialized in this initializer.\n\nThis initializer throws an error when:\n- `Map` fails to get a value for the given key\n- `Map` fails to transform a value using `Transform`\n\n`ImmutableMappable` uses `Map.value(_:using:)` method to get values from the `Map`. This method should be used with the `try` keyword as it is throwable. `Optional` properties can easily be handled using `try?`.\n\n```swift\ninit(map: Map) throws {\n    name      = try map.value(\"name\") \u002F\u002F throws an error when it fails\n    createdAt = try map.value(\"createdAt\", using: DateTransform()) \u002F\u002F throws an error when it fails\n    updatedAt = try? map.value(\"updatedAt\", using: DateTransform()) \u002F\u002F optional\n    posts     = (try? map.value(\"posts\")) ?? [] \u002F\u002F optional + default value\n    surname    = try? map.value(\"surname\", default: \"DefaultSurname\") \u002F\u002F optional + default value as an argument\n}\n```\n\n#### `mutating func mapping(map: Map)`\n\nThis method is where the reverse transform is performed (model to JSON). Since immutable properties cannot be mapped with the `\u003C-` operator, developers have to define the reverse transform using the `>>>` operator.\n\n```swift\nmutating func mapping(map: Map) {\n    name      >>> map[\"name\"]\n    createdAt >>> (map[\"createdAt\"], DateTransform())\n    updatedAt >>> (map[\"updatedAt\"], DateTransform())\n    posts     >>> map[\"posts\"]\n}\n```\n\n# Easy Mapping of Nested Objects\nObjectMapper supports dot notation within keys for easy mapping of nested objects. Given the following JSON String:\n```json\n\"distance\" : {\n     \"text\" : \"102 ft\",\n     \"value\" : 31\n}\n```\nYou can access the nested objects as follows:\n```swift\nfunc mapping(map: Map) {\n    distance \u003C- map[\"distance.value\"]\n}\n```\nNested keys also support accessing values from an array. Given a JSON response with an array of distances, the value could be accessed as follows:\n```swift\ndistance \u003C- map[\"distances.0.value\"]\n```\nIf you have a key that contains `.`, you can individually disable the above feature as follows:\n```swift\nfunc mapping(map: Map) {\n    identifier \u003C- map[\"app.identifier\", nested: false]\n}\n```\nWhen you have nested keys which contain `.`, you can pass the custom nested key delimiter as follows ([#629](https:\u002F\u002Fgithub.com\u002Ftristanhimmelman\u002FObjectMapper\u002Fpull\u002F629)):\n```swift\nfunc mapping(map: Map) {\n    appName \u003C- map[\"com.myapp.info->com.myapp.name\", delimiter: \"->\"]\n}\n```\n\n# Custom Transforms\nObjectMapper also supports custom transforms that convert values during the mapping process. To use a transform, simply create a tuple with `map[\"field_name\"]` and the transform of your choice on the right side of the `\u003C-` operator:\n```swift\nbirthday \u003C- (map[\"birthday\"], DateTransform())\n```\nThe above transform will convert the JSON Int value to an Date when reading JSON and will convert the Date to an Int when converting objects to JSON.\n\nYou can easily create your own custom transforms by adopting and implementing the methods in the `TransformType` protocol:\n```swift\npublic protocol TransformType {\n    associatedtype Object\n    associatedtype JSON\n\n    func transformFromJSON(_ value: Any?) -> Object?\n    func transformToJSON(_ value: Object?) -> JSON?\n}\n```\n\n### TransformOf\nIn a lot of situations you can use the built-in transform class `TransformOf` to quickly perform a desired transformation. `TransformOf` is initialized with two types and two closures. The types define what the transform is converting to and from and the closures perform the actual transformation. \n\nFor example, if you want to transform a JSON `String` value to an `Int` you could use `TransformOf` as follows:\n```swift\nlet transform = TransformOf\u003CInt, String>(fromJSON: { (value: String?) -> Int? in \n    \u002F\u002F transform value from String? to Int?\n    return Int(value!)\n}, toJSON: { (value: Int?) -> String? in\n    \u002F\u002F transform value from Int? to String?\n    if let value = value {\n        return String(value)\n    }\n    return nil\n})\n\nid \u003C- (map[\"id\"], transform)\n```\nHere is a more condensed version of the above:\n```swift\nid \u003C- (map[\"id\"], TransformOf\u003CInt, String>(fromJSON: { Int($0!) }, toJSON: { $0.map { String($0) } }))\n```\n\n# Subclasses\n\nClasses that implement the `Mappable` protocol can easily be subclassed. When subclassing mappable classes, follow the structure below:\n\n```swift\nclass Base: Mappable {\n    var base: String?\n    \n    required init?(map: Map) {\n\n    }\n\n    func mapping(map: Map) {\n        base \u003C- map[\"base\"]\n    }\n}\n\nclass Subclass: Base {\n    var sub: String?\n\n    required init?(map: Map) {\n        super.init(map)\n    }\n\n    override func mapping(map: Map) {\n        super.mapping(map)\n        \n        sub \u003C- map[\"sub\"]\n    }\n}\n```\n\nMake sure your subclass implementation calls the right initializers and mapping functions to also apply the mappings from your superclass.\n\n# Generic Objects\n\nObjectMapper can handle classes with generic types as long as the generic type also conforms to `Mappable`. See the following example:\n```swift\nclass Result\u003CT: Mappable>: Mappable {\n    var result: T?\n\n    required init?(map: Map){\n\n    }\n\n    func mapping(map: Map) {\n        result \u003C- map[\"result\"]\n    }\n}\n\nlet result = Mapper\u003CResult\u003CUser>>().map(JSON)\n```\n\n# Mapping Context\n\nThe `Map` object which is passed around during mapping, has an optional `MapContext` object that is available for developers to use if they need to pass information around during mapping. \n\nTo take advantage of this feature, simply create an object that implements `MapContext` (which is an empty protocol) and pass it into `Mapper` during initialization. \n```swift\nstruct Context: MapContext {\n\tvar importantMappingInfo = \"Info that I need during mapping\"\n}\n\nclass User: Mappable {\n\tvar name: String?\n\t\n\trequired init?(map: Map){\n\t\n\t}\n\t\n\tfunc mapping(map: Map){\n\t\tif let context = map.context as? Context {\n\t\t\t\u002F\u002F use context to make decisions about mapping\n\t\t}\n\t}\n}\n\nlet context = Context()\nlet user = Mapper\u003CUser>(context: context).map(JSONString)\n```\n\n# ObjectMapper + Alamofire\n\nIf you are using [Alamofire](https:\u002F\u002Fgithub.com\u002FAlamofire\u002FAlamofire) for networking and you want to convert your responses to Swift objects, you can use [AlamofireObjectMapper](https:\u002F\u002Fgithub.com\u002Ftristanhimmelman\u002FAlamofireObjectMapper). It is a simple Alamofire extension that uses ObjectMapper to automatically map JSON response data to Swift objects.\n\n\n# ObjectMapper + Realm\n\nObjectMapper and Realm can be used together. Simply follow the class structure below and you will be able to use ObjectMapper to generate your Realm models:\n\n```swift\nclass Model: Object, Mappable {\n    dynamic var name = \"\"\n\n    required convenience init?(map: Map) {\n        self.init()\n    }\n\n    func mapping(map: Map) {\n        name \u003C- map[\"name\"]\n    }\n}\n```\n\nIf you want to serialize associated RealmObjects, you can use [ObjectMapper+Realm](https:\u002F\u002Fgithub.com\u002Fjakenberg\u002FObjectMapper-Realm). It is a simple Realm extension that serializes arbitrary JSON into Realm's `List` class.\n\nTo serialize Swift `String`, `Int`, `Double` and `Bool` arrays you can use [ObjectMapperAdditions\u002FRealm](https:\u002F\u002Fgithub.com\u002FAPUtils\u002FObjectMapperAdditions#realm-features). It'll wrap Swift types into RealmValues that can be stored in Realm's `List` class.\n\nNote: Generating a JSON string of a Realm Object using ObjectMappers' `toJSON` function only works within a Realm write transaction. This is because ObjectMapper uses the `inout` flag in its mapping functions (`\u003C-`) which are used both for serializing and deserializing. Realm detects the flag and forces the `toJSON` function to be called within a write block even though the objects are not being modified.\n\n# Projects Using ObjectMapper\n- [Xcode Plugin for generating `Mappable` and `ImmutableMappable` code](https:\u002F\u002Fgithub.com\u002Fliyanhuadev\u002FObjectMapper-Plugin)\n\n- [Json4Swift - Supports generating `ImmutableMappable` structs online (no plugins needed)](http:\u002F\u002Fwww.json4swift.com)\n\n- [JSON to Model - Template based MacOS app which generates structs with customisation.](https:\u002F\u002Fgithub.com\u002Fchanonly123\u002FJson-Model-Generator)  [⬇️Download App](https:\u002F\u002Fgithub.com\u002Fchanonly123\u002FJson-Model-Generator\u002Fraw\u002Fmaster\u002FJsonToModel.zip)\n\nIf you have a project that utilizes, extends or provides tooling for ObjectMapper, please submit a PR with a link to your project in this section of the README.\n\n# To Do\n- Improve error handling. Perhaps using `throws`\n- Class cluster documentation\n\n# Contributing\n\nContributions are very welcome 👍😃. \n\nBefore submitting any pull request, please ensure you have run the included tests and they have passed. If you are including new functionality, please write test cases for it as well.\n\n# Installation\n### Cocoapods\nObjectMapper can be added to your project using [CocoaPods 0.36 or later](http:\u002F\u002Fblog.cocoapods.org\u002FPod-Authors-Guide-to-CocoaPods-Frameworks\u002F) by adding the following line to your `Podfile`:\n\n```ruby\npod 'ObjectMapper', '~> 3.5' (check releases to make sure this is the latest version)\n```\n\n### Carthage\nIf you're using [Carthage](https:\u002F\u002Fgithub.com\u002FCarthage\u002FCarthage) you can add a dependency on ObjectMapper by adding it to your `Cartfile`:\n\n```\ngithub \"tristanhimmelman\u002FObjectMapper\" ~> 3.5 (check releases to make sure this is the latest version)\n```\n\n### Swift Package Manager\nTo add ObjectMapper to a [Swift Package Manager](https:\u002F\u002Fswift.org\u002Fpackage-manager\u002F) based project, add:\n\n```swift\n.package(url: \"https:\u002F\u002Fgithub.com\u002Ftristanhimmelman\u002FObjectMapper.git\", .upToNextMajor(from: \"4.1.0\")),\n```\nto your `Package.swift` files `dependencies` array.\n\n### Submodule\nOtherwise, ObjectMapper can be added as a submodule:\n\n1. Add ObjectMapper as a [submodule](http:\u002F\u002Fgit-scm.com\u002Fdocs\u002Fgit-submodule) by opening the terminal, `cd`-ing into your top-level project directory, and entering the command `git submodule add https:\u002F\u002Fgithub.com\u002Ftristanhimmelman\u002FObjectMapper.git`\n2. Open the `ObjectMapper` folder, and drag `ObjectMapper.xcodeproj` into the file navigator of your app project.\n3. In Xcode, navigate to the target configuration window by clicking on the blue project icon, and selecting the application target under the \"Targets\" heading in the sidebar.\n4. Ensure that the deployment target of `ObjectMapper.framework` matches that of the application target.\n5. In the tab bar at the top of that window, open the \"Build Phases\" panel.\n6. Expand the \"Target Dependencies\" group, and add `ObjectMapper.framework`.\n7. Click on the `+` button at the top left of the panel and select \"New Copy Files Phase\". Rename this new phase to \"Copy Frameworks\", set the \"Destination\" to \"Frameworks\", and add `ObjectMapper.framework`.\n","ObjectMapper 是一个用 Swift 编写的框架，旨在简化模型对象与 JSON 之间的转换过程。它支持将 JSON 数据映射到类或结构体中，反之亦然，并且能够处理嵌套的对象、数组和字典，同时允许开发者自定义转换逻辑。该库还提供了对不可变对象的支持以及与其他流行库如 Alamofire 和 Realm 的集成能力。适用于需要频繁进行 JSON 序列化和反序列化的 iOS 或 macOS 应用开发场景，尤其是当应用涉及到复杂的数据模型时，使用 ObjectMapper 可以显著提高开发效率并减少错误。","2026-06-11 03:08:32","top_language"]