Compare commits
No commits in common. "master" and "gh-pages" have entirely different histories.
|
@ -1,43 +0,0 @@
|
|||
### Your JSON dictionary:
|
||||
|
||||
```json
|
||||
{
|
||||
"name": "ObjectMapper",
|
||||
"url": "https://github.com/Hearst-DD/ObjectMapper"
|
||||
}
|
||||
```
|
||||
|
||||
### Your model:
|
||||
|
||||
```swift
|
||||
struct Repo: Mappable {
|
||||
var name: String!
|
||||
var url: URL!
|
||||
|
||||
init(_ map: Map) {
|
||||
name <- map["name"]
|
||||
url <- map["url"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### What you did:
|
||||
|
||||
```swift
|
||||
let repo = Mapper<Repo>().map(myJSONDictionary)
|
||||
```
|
||||
|
||||
### What you expected:
|
||||
|
||||
I exepected something like:
|
||||
|
||||
```swift
|
||||
Repo(name: "ObjectMapper", url: "https://github.com/Hearst-DD/ObjectMapper")
|
||||
```
|
||||
|
||||
### What you got:
|
||||
|
||||
```swift
|
||||
Repo(name: "ObjectMapper", url: nil) // expected the url is mapped correctly
|
||||
```
|
||||
|
|
@ -1,5 +0,0 @@
|
|||
## Why <!-- Describe why you are making the change -->
|
||||
|
||||
|
||||
|
||||
## What <!-- Describe what changed -->
|
|
@ -1,26 +0,0 @@
|
|||
# Xcode
|
||||
build/
|
||||
*.pbxuser
|
||||
!default.pbxuser
|
||||
*.mode1v3
|
||||
!default.mode1v3
|
||||
*.mode2v3
|
||||
!default.mode2v3
|
||||
*.perspectivev3
|
||||
!default.perspectivev3
|
||||
xcuserdata
|
||||
*.xccheckout
|
||||
*.moved-aside
|
||||
DerivedData
|
||||
*.xcuserstate
|
||||
# AppCode etc.
|
||||
.idea/
|
||||
# Desktop Servies
|
||||
.DS_Store
|
||||
|
||||
# Carthage
|
||||
Carthage/Build
|
||||
|
||||
# Swift package manager
|
||||
.build/
|
||||
Packages/
|
45
.travis.yml
45
.travis.yml
|
@ -1,45 +0,0 @@
|
|||
language: objective-c
|
||||
osx_image: xcode11.3
|
||||
|
||||
env:
|
||||
global:
|
||||
- LANG=en_US.UTF-8
|
||||
- LC_ALL=en_US.UTF-8
|
||||
- WORKSPACE="ObjectMapper.xcworkspace"
|
||||
- IOS_FRAMEWORK_SCHEME="ObjectMapper-iOS"
|
||||
- OSX_FRAMEWORK_SCHEME="ObjectMapper-Mac"
|
||||
- TVOS_FRAMEWORK_SCHEME="ObjectMapper-tvOS"
|
||||
- WATCHOS_FRAMEWORK_SCHEME="ObjectMapper-watchOS"
|
||||
matrix:
|
||||
#iOS
|
||||
- DESTINATION="OS=11.4,name=iPhone X" SCHEME="$IOS_FRAMEWORK_SCHEME" RUN_TESTS="YES"
|
||||
- DESTINATION="OS=10.3.1,name=iPhone 7 Plus" SCHEME="$IOS_FRAMEWORK_SCHEME" RUN_TESTS="YES"
|
||||
#macOS
|
||||
- DESTINATION="arch=x86_64" SCHEME="$OSX_FRAMEWORK_SCHEME" RUN_TESTS="YES"
|
||||
#tvOS
|
||||
- DESTINATION="OS=11.4,name=Apple TV 4K" SCHEME="$TVOS_FRAMEWORK_SCHEME" RUN_TESTS="YES"
|
||||
|
||||
before_install:
|
||||
- gem install xcpretty --no-document --quiet
|
||||
|
||||
script:
|
||||
- set -o pipefail
|
||||
- xcodebuild -version
|
||||
- xcodebuild -showsdks
|
||||
|
||||
# Build Framework in Debug and Run Tests if specified
|
||||
- if [ $RUN_TESTS == "YES" ]; then
|
||||
travis_retry xcodebuild -workspace "$WORKSPACE" -scheme "$SCHEME" -destination "$DESTINATION" -configuration Debug ONLY_ACTIVE_ARCH=NO test | xcpretty -c;
|
||||
else
|
||||
travis_retry xcodebuild -workspace "$WORKSPACE" -scheme "$SCHEME" -destination "$DESTINATION" -configuration Debug ONLY_ACTIVE_ARCH=NO build | xcpretty -c;
|
||||
fi
|
||||
|
||||
# Build Framework in Release and Run Tests if specified
|
||||
- if [ $RUN_TESTS == "YES" ]; then
|
||||
travis_retry xcodebuild -workspace "$WORKSPACE" -scheme "$SCHEME" -destination "$DESTINATION" -configuration Release ONLY_ACTIVE_ARCH=NO test | xcpretty -c;
|
||||
else
|
||||
travis_retry xcodebuild -workspace "$WORKSPACE" -scheme "$SCHEME" -destination "$DESTINATION" -configuration Release ONLY_ACTIVE_ARCH=NO build | xcpretty -c;
|
||||
fi
|
||||
|
||||
notifications:
|
||||
email: false
|
8
LICENSE
8
LICENSE
|
@ -1,8 +0,0 @@
|
|||
The MIT License (MIT)
|
||||
Copyright (c) 2014 Hearst
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
@ -1,19 +0,0 @@
|
|||
Pod::Spec.new do |s|
|
||||
s.name = 'ObjectMapper'
|
||||
s.version = '4.2.0'
|
||||
s.license = 'MIT'
|
||||
s.summary = 'JSON Object mapping written in Swift'
|
||||
s.homepage = 'https://github.com/tristanhimmelman/ObjectMapper'
|
||||
s.authors = { 'Tristan Himmelman' => 'tristanhimmelman@gmail.com' }
|
||||
s.source = { :git => 'https://github.com/tristanhimmelman/ObjectMapper.git', :tag => s.version.to_s }
|
||||
|
||||
s.watchos.deployment_target = '2.0'
|
||||
s.ios.deployment_target = '10.0'
|
||||
s.osx.deployment_target = '10.9'
|
||||
s.tvos.deployment_target = '9.0'
|
||||
|
||||
s.swift_version = '5.0'
|
||||
|
||||
s.requires_arc = true
|
||||
s.source_files = 'Sources/**/*.swift'
|
||||
end
|
File diff suppressed because it is too large
Load Diff
|
@ -1,7 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Workspace
|
||||
version = "1.0">
|
||||
<FileRef
|
||||
location = "self:ObjectMapper.xcodeproj">
|
||||
</FileRef>
|
||||
</Workspace>
|
|
@ -1,8 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>IDEDidComputeMac32BitWarning</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
|
@ -1,113 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1020"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
<BuildActionEntries>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "YES"
|
||||
buildForArchiving = "YES"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "CD1602FE1AC023D5000CD69A"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-macOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "NO"
|
||||
buildForProfiling = "NO"
|
||||
buildForArchiving = "NO"
|
||||
buildForAnalyzing = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "CD1603081AC023D6000CD69A"
|
||||
BuildableName = "ObjectMapper-macOSTests.xctest"
|
||||
BlueprintName = "ObjectMapper-macOSTests"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Release"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "CD1603081AC023D6000CD69A"
|
||||
BuildableName = "ObjectMapper-macOSTests.xctest"
|
||||
BlueprintName = "ObjectMapper-macOSTests"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "CD1602FE1AC023D5000CD69A"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-macOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "CD1602FE1AC023D5000CD69A"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-macOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "CD1602FE1AC023D5000CD69A"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-macOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
|
@ -1,113 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1020"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
<BuildActionEntries>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "YES"
|
||||
buildForArchiving = "YES"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6AAC8F7519F03C2900E7A677"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-iOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "NO"
|
||||
buildForProfiling = "NO"
|
||||
buildForArchiving = "NO"
|
||||
buildForAnalyzing = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6AAC8F8019F03C2900E7A677"
|
||||
BuildableName = "ObjectMapper-iOSTests.xctest"
|
||||
BlueprintName = "ObjectMapper-iOSTests"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Release"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6AAC8F8019F03C2900E7A677"
|
||||
BuildableName = "ObjectMapper-iOSTests.xctest"
|
||||
BlueprintName = "ObjectMapper-iOSTests"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6AAC8F7519F03C2900E7A677"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-iOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6AAC8F7519F03C2900E7A677"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-iOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6AAC8F7519F03C2900E7A677"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-iOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
|
@ -1,99 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1020"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
<BuildActionEntries>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "YES"
|
||||
buildForArchiving = "YES"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A05B7A51BE274BE00F19B53"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-tvOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A05B7AE1BE274BE00F19B53"
|
||||
BuildableName = "ObjectMapper-tvOSTests.xctest"
|
||||
BlueprintName = "ObjectMapper-tvOSTests"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A05B7A51BE274BE00F19B53"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-tvOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A05B7A51BE274BE00F19B53"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-tvOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A05B7A51BE274BE00F19B53"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-tvOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
|
@ -1,99 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1020"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
<BuildActionEntries>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "YES"
|
||||
buildForArchiving = "YES"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A2AD03C1B2C78540097E150"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-watchOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A2098072193AA00009AB4DF"
|
||||
BuildableName = "ObjectMapper-watchOSTests.xctest"
|
||||
BlueprintName = "ObjectMapper-watchOSTests"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A2AD03C1B2C78540097E150"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-watchOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A2AD03C1B2C78540097E150"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-watchOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6A2AD03C1B2C78540097E150"
|
||||
BuildableName = "ObjectMapper.framework"
|
||||
BlueprintName = "ObjectMapper-watchOS"
|
||||
ReferencedContainer = "container:ObjectMapper.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
|
@ -1,7 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Workspace
|
||||
version = "1.0">
|
||||
<FileRef
|
||||
location = "group:ObjectMapper.xcodeproj">
|
||||
</FileRef>
|
||||
</Workspace>
|
|
@ -1,8 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>IDEDidComputeMac32BitWarning</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
|
@ -1,30 +0,0 @@
|
|||
{
|
||||
"DVTSourceControlWorkspaceBlueprintPrimaryRemoteRepositoryKey" : "58AAB0051E2B4EEDF1845A552012E6D0EBAD9127",
|
||||
"DVTSourceControlWorkspaceBlueprintWorkingCopyRepositoryLocationsKey" : {
|
||||
|
||||
},
|
||||
"DVTSourceControlWorkspaceBlueprintWorkingCopyStatesKey" : {
|
||||
"58AAB0051E2B4EEDF1845A552012E6D0EBAD9127" : 0,
|
||||
"95438028B10BBB846574013D29F154A00556A9D1" : 0
|
||||
},
|
||||
"DVTSourceControlWorkspaceBlueprintIdentifierKey" : "A42BB54B-7EE9-41B5-B851-0FC3BB5A9811",
|
||||
"DVTSourceControlWorkspaceBlueprintWorkingCopyPathsKey" : {
|
||||
"58AAB0051E2B4EEDF1845A552012E6D0EBAD9127" : "ObjectMapper\/",
|
||||
"95438028B10BBB846574013D29F154A00556A9D1" : "ObjectMapperCarthage\/Checkouts\/Nimble"
|
||||
},
|
||||
"DVTSourceControlWorkspaceBlueprintNameKey" : "ObjectMapper",
|
||||
"DVTSourceControlWorkspaceBlueprintVersion" : 204,
|
||||
"DVTSourceControlWorkspaceBlueprintRelativePathToProjectKey" : "ObjectMapper.xcworkspace",
|
||||
"DVTSourceControlWorkspaceBlueprintRemoteRepositoriesKey" : [
|
||||
{
|
||||
"DVTSourceControlWorkspaceBlueprintRemoteRepositoryURLKey" : "https:\/\/github.com\/Hearst-DD\/ObjectMapper.git",
|
||||
"DVTSourceControlWorkspaceBlueprintRemoteRepositorySystemKey" : "com.apple.dt.Xcode.sourcecontrol.Git",
|
||||
"DVTSourceControlWorkspaceBlueprintRemoteRepositoryIdentifierKey" : "58AAB0051E2B4EEDF1845A552012E6D0EBAD9127"
|
||||
},
|
||||
{
|
||||
"DVTSourceControlWorkspaceBlueprintRemoteRepositoryURLKey" : "https:\/\/github.com\/Quick\/Nimble.git",
|
||||
"DVTSourceControlWorkspaceBlueprintRemoteRepositorySystemKey" : "com.apple.dt.Xcode.sourcecontrol.Git",
|
||||
"DVTSourceControlWorkspaceBlueprintRemoteRepositoryIdentifierKey" : "95438028B10BBB846574013D29F154A00556A9D1"
|
||||
}
|
||||
]
|
||||
}
|
|
@ -1,17 +0,0 @@
|
|||
// swift-tools-version:5.0
|
||||
|
||||
import PackageDescription
|
||||
|
||||
let package = Package(name: "ObjectMapper",
|
||||
platforms: [.macOS(.v10_10),
|
||||
.iOS(.v10),
|
||||
.tvOS(.v9),
|
||||
.watchOS(.v2)],
|
||||
products: [.library(name: "ObjectMapper",
|
||||
targets: ["ObjectMapper"])],
|
||||
targets: [.target(name: "ObjectMapper",
|
||||
path: "Sources"),
|
||||
.testTarget(name: "ObjectMapperTests",
|
||||
dependencies: ["ObjectMapper"],
|
||||
path: "Tests")],
|
||||
swiftLanguageVersions: [.v5])
|
|
@ -1,18 +0,0 @@
|
|||
// swift-tools-version:4.2
|
||||
// The swift-tools-version declares the minimum version of Swift required to build this package.
|
||||
|
||||
import PackageDescription
|
||||
|
||||
let package = Package(
|
||||
name: "ObjectMapper",
|
||||
products: [
|
||||
.library(name: "ObjectMapper", targets: ["ObjectMapper"]),
|
||||
],
|
||||
targets: [
|
||||
.target(
|
||||
name: "ObjectMapper",
|
||||
path: "Sources"
|
||||
)
|
||||
],
|
||||
swiftLanguageVersions: [.v3, .v4, .v4_2]
|
||||
)
|
|
@ -1,18 +0,0 @@
|
|||
// swift-tools-version:4.0
|
||||
// The swift-tools-version declares the minimum version of Swift required to build this package.
|
||||
|
||||
import PackageDescription
|
||||
|
||||
let package = Package(
|
||||
name: "ObjectMapper",
|
||||
products: [
|
||||
.library(name: "ObjectMapper", targets: ["ObjectMapper"]),
|
||||
],
|
||||
targets: [
|
||||
.target(
|
||||
name: "ObjectMapper",
|
||||
path: "Sources"
|
||||
)
|
||||
],
|
||||
swiftLanguageVersions = [3, 4]
|
||||
)
|
500
README-CN.md
500
README-CN.md
|
@ -1,500 +0,0 @@
|
|||
# ObjectMapper-CN-Guide
|
||||
> 文档由Swift老司机活动中心负责翻译,欢迎关注[@SwiftOldDriver](http://weibo.com/6062089411)。翻译有问题可以到 [ObjectMapper-CN-Guide](https://github.com/SwiftOldDriver/ObjectMapper-CN-Guide) 提 PR。
|
||||
|
||||
[ObjectMapper](https://github.com/Hearst-DD/ObjectMapper) 是一个使用 Swift 编写的用于 model 对象(类和结构体)和 JSON 之间转换的框架。
|
||||
|
||||
- [特性](#特性)
|
||||
- [基础使用方法](#基础使用方法)
|
||||
- [映射嵌套对象](#映射嵌套对象)
|
||||
- [自定义转换规则](#自定义转换规则)
|
||||
- [继承](#继承)
|
||||
- [泛型对象](#泛型对象)
|
||||
- [映射时的上下文对象](#映射时的上下文对象)
|
||||
- [ObjectMapper + Alamofire](#objectmapper--alamofire)
|
||||
- [ObjectMapper + Realm](#objectmapper--realm)
|
||||
- [待完成](#待完成)
|
||||
- [安装](#安装)
|
||||
|
||||
# 特性:
|
||||
- 把 JSON 映射成对象
|
||||
- 把对象映射 JSON
|
||||
- 支持嵌套对象 (单独的成员变量、在数组或字典中都可以)
|
||||
- 在转换过程支持自定义规则
|
||||
- 支持结构体( Struct )
|
||||
- [Immutable support](#immutablemappable-protocol-beta) (目前还在 beta )
|
||||
|
||||
# 基础使用方法
|
||||
为了支持映射,类或者结构体只需要实现```Mappable```协议。这个协议包含以下方法:
|
||||
```swift
|
||||
init?(map: Map)
|
||||
mutating func mapping(map: Map)
|
||||
```
|
||||
ObjectMapper使用自定义的```<-``` 运算符来声明成员变量和 JSON 的映射关系。
|
||||
```swift
|
||||
class User: Mappable {
|
||||
var username: String?
|
||||
var age: Int?
|
||||
var weight: Double!
|
||||
var array: [AnyObject]?
|
||||
var dictionary: [String : AnyObject] = [:]
|
||||
var bestFriend: User? // 嵌套的 User 对象
|
||||
var friends: [User]? // Users 的数组
|
||||
var birthday: NSDate?
|
||||
|
||||
required init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
// Mappable
|
||||
func mapping(map: Map) {
|
||||
username <- map["username"]
|
||||
age <- map["age"]
|
||||
weight <- map["weight"]
|
||||
array <- map["arr"]
|
||||
dictionary <- map["dict"]
|
||||
bestFriend <- map["best_friend"]
|
||||
friends <- map["friends"]
|
||||
birthday <- (map["birthday"], DateTransform())
|
||||
}
|
||||
}
|
||||
|
||||
struct Temperature: Mappable {
|
||||
var celsius: Double?
|
||||
var fahrenheit: Double?
|
||||
|
||||
init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
celsius <- map["celsius"]
|
||||
fahrenheit <- map["fahrenheit"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
一旦你的对象实现了 `Mappable`, ObjectMapper就可以让你轻松的实现和 JSON 之间的转换。
|
||||
|
||||
把 JSON 字符串转成 model 对象:
|
||||
|
||||
```swift
|
||||
let user = User(JSONString: JSONString)
|
||||
```
|
||||
|
||||
把一个 model 转成 JSON 字符串:
|
||||
|
||||
```swift
|
||||
let JSONString = user.toJSONString(prettyPrint: true)
|
||||
```
|
||||
|
||||
也可以使用`Mapper.swift`类来完成转换(这个类还额外提供了一些函数来处理一些特殊的情况:
|
||||
|
||||
```swift
|
||||
// 把 JSON 字符串转成 Model
|
||||
let user = Mapper<User>().map(JSONString: JSONString)
|
||||
// 根据 Model 生成 JSON 字符串
|
||||
let JSONString = Mapper().toJSONString(user, prettyPrint: true)
|
||||
```
|
||||
|
||||
ObjectMapper支持以下的类型映射到对象中:
|
||||
|
||||
- `Int`
|
||||
- `Bool`
|
||||
- `Double`
|
||||
- `Float`
|
||||
- `String`
|
||||
- `RawRepresentable` (枚举)
|
||||
- `Array<AnyObject>`
|
||||
- `Dictionary<String, AnyObject>`
|
||||
- `Object<T: Mappable>`
|
||||
- `Array<T: Mappable>`
|
||||
- `Array<Array<T: Mappable>>`
|
||||
- `Set<T: Mappable>`
|
||||
- `Dictionary<String, T: Mappable>`
|
||||
- `Dictionary<String, Array<T: Mappable>>`
|
||||
- 以上所有的 Optional 类型
|
||||
- 以上所有的隐式强制解包类型(Implicitly Unwrapped Optional)
|
||||
|
||||
## `Mappable` 协议
|
||||
|
||||
#### `mutating func mapping(map: Map)`
|
||||
所有的映射最后都会调用到这个函数。当解析 JSON 时,这个函数会在对象创建成功后被执行。当生成 JSON 时就只有这个函数会被对象调用。
|
||||
|
||||
#### `init?(map: Map)`
|
||||
这个可失败的初始化函数是 ObjectMapper 创建对象的时候使用的。开发者可以通过这个函数在映射前校验 JSON 。如果在这个方法里返回 nil 就不会执行 `mapping` 函数。可以通过传入的保存着 JSON 的 `Map` 对象进行校验:
|
||||
|
||||
```swift
|
||||
required init?(map: Map){
|
||||
// 检查 JSON 里是否有一定要有的 "name" 属性
|
||||
if map.JSONDictionary["name"] == nil {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## `StaticMappable` 协议
|
||||
`StaticMappable` 是 `Mappable` 之外的另一种选择。 这个协议可以让开发者通过一个静态函数初始化对象而不是通过 `init?(map: Map)`。
|
||||
|
||||
注意: `StaticMappable` 和 `Mappable` 都继承了 `BaseMappable` 协议。 `BaseMappable` 协议声明了 `mapping(map: Map)` 函数。
|
||||
|
||||
#### `static func objectForMapping(map: Map) -> BaseMappable?`
|
||||
ObjectMapper 使用这个函数获取对象后进行映射。开发者需要在这个函数里返回一个实现 `BaseMappable` 对象的实例。这个函数也可以用于:
|
||||
|
||||
- 在对象进行映射前校验 JSON
|
||||
- 提供一个缓存过的对象用于映射
|
||||
- 返回另外一种类型的对象(当然是必须实现了 BaseMappable)用于映射。比如你可能通过检查 JSON 推断出用于映射的对象 ([看这个例子](https://github.com/Hearst-DD/ObjectMapper/blob/master/ObjectMapperTests/ClassClusterTests.swift#L62))。
|
||||
|
||||
如果你需要在 extension 里实现 ObjectMapper,你需要选择这个协议而不是 `Mappable` 。
|
||||
|
||||
## `ImmutableMappable` Protocol
|
||||
|
||||
使用 `ImmutableMappable` 可以映射不可变的属性。下面的表格展示了 `ImmutableMappable` 和 `Mappable` 的不同:
|
||||
|
||||
<table>
|
||||
<tr>
|
||||
<th>ImmutableMappable</th>
|
||||
<th>Mappable</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">Properties</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
<strong>let</strong> id: Int
|
||||
<strong>let</strong> name: String?
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
var id: Int!
|
||||
var name: String?
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">JSON -> Model</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
init(map: Map) <strong>throws</strong> {
|
||||
id = <strong>try</strong> map.value("id")
|
||||
name = <strong>try?</strong> map.value("name")
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
mutating func mapping(map: Map) {
|
||||
id <- map["id"]
|
||||
name <- map["name"]
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">Model -> JSON</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
mutating func mapping(map: Map) {
|
||||
id <strong>>>></strong> map["id"]
|
||||
name <strong>>>></strong> map["name"]
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
mutating func mapping(map: Map) {
|
||||
id <- map["id"]
|
||||
name <- map["name"]
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">Initializing</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
<strong>try</strong> User(JSONString: JSONString)
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
User(JSONString: JSONString)
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
#### `init(map: Map) throws`
|
||||
|
||||
这个可能抛出异常的初始化函数用于在提供的 `Map` 里映射不可变属性。每个不可变的初始化属性都要在这个初始化函数里初始化。
|
||||
|
||||
当发生下列情况时初始化函数会抛出一个错误:
|
||||
|
||||
- `Map` 根据提供的键名获取不到对应值
|
||||
- `Map` 使用 `Transform` 后没有得到值
|
||||
|
||||
`ImmutableMappable` 使用 `Map.value(_:using:)` 方法从 `Map` 中获取值。因为可能抛出异常,这个方法在使用时需要使用 `try` 关键字。 `Optional` 的属性可以简单的用 `try?` 处理。
|
||||
|
||||
```swift
|
||||
init(map: Map) throws {
|
||||
name = try map.value("name") // throws an error when it fails
|
||||
createdAt = try map.value("createdAt", using: DateTransform()) // throws an error when it fails
|
||||
updatedAt = try? map.value("updatedAt", using: DateTransform()) // optional
|
||||
posts = (try? map.value("posts")) ?? [] // optional + default value
|
||||
}
|
||||
```
|
||||
|
||||
#### `mutating func mapping(map: Map)`
|
||||
|
||||
这个方法是在 Model 转回 JSON 时调用的。因为不可变的属性不能被 `<-` 映射,所以映射回来时需要使用 `>>>` 。
|
||||
|
||||
```swift
|
||||
mutating func mapping(map: Map) {
|
||||
name >>> map["name"]
|
||||
createdAt >>> (map["createdAt"], DateTransform())
|
||||
updatedAt >>> (map["updatedAt"], DateTransform())
|
||||
posts >>> map["posts"]
|
||||
}
|
||||
```
|
||||
# 轻松映射嵌套对象
|
||||
|
||||
ObjectMapper 支持使用点语法来轻松实现嵌套对象的映射。比如有如下的 JSON 字符串:
|
||||
|
||||
```json
|
||||
"distance" : {
|
||||
"text" : "102 ft",
|
||||
"value" : 31
|
||||
}
|
||||
```
|
||||
你可以通过这种写法直接访问到嵌套对象:
|
||||
|
||||
```swift
|
||||
func mapping(map: Map) {
|
||||
distance <- map["distance.value"]
|
||||
}
|
||||
```
|
||||
嵌套的键名也支持访问数组中的值。如果有一个返回的 JSON 是一个包含 distance 的数组,可以通过这种写法访问:
|
||||
|
||||
```
|
||||
distance <- map["distances.0.value"]
|
||||
```
|
||||
如果你的键名刚好含有 `.` 符号,你需要特别声明关闭上面提到的获取嵌套对象功能:
|
||||
|
||||
```swift
|
||||
func mapping(map: Map) {
|
||||
identifier <- map["app.identifier", nested: false]
|
||||
}
|
||||
```
|
||||
如果刚好有嵌套的对象的键名还有 `.` ,可以在中间加入一个自定义的分割符([#629](https://github.com/Hearst-DD/ObjectMapper/pull/629)):
|
||||
```swift
|
||||
func mapping(map: Map) {
|
||||
appName <- map["com.myapp.info->com.myapp.name", delimiter: "->"]
|
||||
}
|
||||
```
|
||||
这种情况的 JSON 是这样的:
|
||||
|
||||
```json
|
||||
"com.myapp.info" : {
|
||||
"com.myapp.name" : "SwiftOldDriver"
|
||||
}
|
||||
```
|
||||
|
||||
# 自定义转换规则
|
||||
ObjectMapper 也支持在映射时自定义转换规则。如果要使用自定义转换,创建一个 tuple(元祖)包含 ```map["field_name"]``` 和你要使用的变换放在 ```<-``` 的右边:
|
||||
|
||||
```swift
|
||||
birthday <- (map["birthday"], DateTransform())
|
||||
```
|
||||
当解析 JSON 时上面的转换会把 JSON 里面的 Int 值转成一个 NSDate ,如果是对象转为 JSON 时,则会把 NSDate 对象转成 Int 值。
|
||||
|
||||
只要实现```TransformType``` 协议就可以轻松的创建自定义的转换规则:
|
||||
|
||||
```swift
|
||||
public protocol TransformType {
|
||||
associatedtype Object
|
||||
associatedtype JSON
|
||||
|
||||
func transformFromJSON(_ value: Any?) -> Object?
|
||||
func transformToJSON(_ value: Object?) -> JSON?
|
||||
}
|
||||
```
|
||||
|
||||
### TransformOf
|
||||
大多数情况下你都可以使用框架提供的转换类 ```TransformOf``` 来快速的实现一个期望的转换。 ```TransformOf``` 的初始化需要两个类型和两个闭包。两个类型声明了转换的目标类型和源类型,闭包则实现具体转换逻辑。
|
||||
|
||||
举个例子,如果你想要把一个 JSON 字符串转成 Int ,你可以像这样使用 ```TransformOf``` :
|
||||
|
||||
```swift
|
||||
let transform = TransformOf<Int, String>(fromJSON: { (value: String?) -> Int? in
|
||||
// 把值从 String? 转成 Int?
|
||||
return Int(value!)
|
||||
}, toJSON: { (value: Int?) -> String? in
|
||||
// 把值从 Int? 转成 String?
|
||||
if let value = value {
|
||||
return String(value)
|
||||
}
|
||||
return nil
|
||||
})
|
||||
|
||||
id <- (map["id"], transform)
|
||||
```
|
||||
这是一种更省略的写法:
|
||||
|
||||
```swift
|
||||
id <- (map["id"], TransformOf<Int, String>(fromJSON: { Int($0!) }, toJSON: { $0.map { String($0) } }))
|
||||
```
|
||||
# 继承
|
||||
|
||||
实现了 ```Mappable``` 协议的类可以容易的被继承。当继承一个 mappable 的类时,使用这样的结构:
|
||||
|
||||
```swift
|
||||
class Base: Mappable {
|
||||
var base: String?
|
||||
|
||||
required init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
base <- map["base"]
|
||||
}
|
||||
}
|
||||
|
||||
class Subclass: Base {
|
||||
var sub: String?
|
||||
|
||||
required init?(map: Map) {
|
||||
super.init(map)
|
||||
}
|
||||
|
||||
override func mapping(map: Map) {
|
||||
super.mapping(map)
|
||||
|
||||
sub <- map["sub"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
注意确认子类中的实现调用了父类中正确的初始化器和映射函数。
|
||||
|
||||
# 泛型对象
|
||||
|
||||
ObjectMapper 可以处理泛型只要这个泛型也实现了`Mappable`协议。看这个例子:
|
||||
|
||||
```swift
|
||||
class Result<T: Mappable>: Mappable {
|
||||
var result: T?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
result <- map["result"]
|
||||
}
|
||||
}
|
||||
|
||||
let result = Mapper<Result<User>>().map(JSON)
|
||||
```
|
||||
# 映射时的上下文对象
|
||||
|
||||
`Map` 是在映射时传入的对象,带有一个 optional `MapContext` 对象,开发者可以通过使用这个对象在映射时传入一些信息。
|
||||
|
||||
为了使用这个特性,需要先创建一个对象实现了 `MapContext` 协议(这个协议是空的),然后在初始化时传入 `Mapper` 中。
|
||||
|
||||
```swift
|
||||
struct Context: MapContext {
|
||||
var importantMappingInfo = "映射时需要知道的额外信息"
|
||||
}
|
||||
|
||||
class User: Mappable {
|
||||
var name: String?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map){
|
||||
if let context = map.context as? Context {
|
||||
// 获取到额外的信息
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let context = Context()
|
||||
let user = Mapper<User>(context: context).map(JSONString)
|
||||
```
|
||||
|
||||
# ObjectMapper + Alamofire
|
||||
|
||||
如果网络层你使用的是 [Alamofire](https://github.com/Alamofire/Alamofire) ,并且你希望把返回的结果转换成 Swift 对象,你可以使用 [AlamofireObjectMapper](https://github.com/tristanhimmelman/AlamofireObjectMapper) 。这是一个使用 ObjectMapper 实现的把返回的 JSON 自动转成 Swift 对象的 Alamofire 的扩展。
|
||||
|
||||
|
||||
# ObjectMapper + Realm
|
||||
|
||||
ObjectMapper 可以和 Realm 一起配合使用。使用下面的声明结构就可以使用 ObjectMapper 生成 Realm 对象:
|
||||
|
||||
```swift
|
||||
class Model: Object, Mappable {
|
||||
dynamic var name = ""
|
||||
|
||||
required convenience init?(map: Map) {
|
||||
self.init()
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
name <- map["name"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
如果你想要序列化相关联的 RealmObject,你可以使用 [ObjectMapper+Realm](https://github.com/jakenberg/ObjectMapper-Realm)。这是一个简单的 Realm 扩展,用于把任意的 JSON 序列化成 Realm 的类(ealm's List class。)
|
||||
|
||||
注意:使用 ObjectMappers 的 `toJSON` 函数来生成 JSON 字符串只在 Realm 的写事务中有效(write transaction)。这是因为 ObjectMapper 在解析和生成时在映射函数( `<-` )中使用 `inout` 作为标记( flag )。Realm 会检测到标记并且强制要求 `toJSON` 函数只能在一个写的事务中调用,即使这个对象并没有被修改。
|
||||
|
||||
# 待完成
|
||||
- 改善错误的处理。可能使用 `throws` 来处理。
|
||||
- 相关类的文档完善
|
||||
|
||||
# 安装
|
||||
### Cocoapods
|
||||
如果你的项目使用 [CocoaPods 0.36 及以上](http://blog.cocoapods.org/Pod-Authors-Guide-to-CocoaPods-Frameworks/) 的版本,你可以把下面内容添加到在 `Podfile` 中,将 ObjectMapper 添加到你的项目中:
|
||||
|
||||
```ruby
|
||||
pod 'ObjectMapper', '~> 2.2'
|
||||
```
|
||||
|
||||
### Carthage
|
||||
如果你的项目使用 [Carthage](https://github.com/Carthage/Carthage) ,你可以把下面的内容添加到 `Cartfile` 中,将 ObjectMapper 的依赖到你的项目中:
|
||||
|
||||
```
|
||||
github "Hearst-DD/ObjectMapper" ~> 2.2
|
||||
```
|
||||
|
||||
### Swift Package Manager
|
||||
如果你的项目使用 [Swift Package Manager](https://swift.org/package-manager/) ,那么你可以把下面内容添加到 `Package.swift` 中的 `dependencies` 数组中,将 ObjectMapper 的依赖到你的项目中:
|
||||
|
||||
```swift
|
||||
.Package(url: "https://github.com/Hearst-DD/ObjectMapper.git", majorVersion: 2, minor: 2),
|
||||
```
|
||||
|
||||
|
||||
### Submodule
|
||||
此外,ObjectMapper 也可以作为一个 submodule 添加到项目中:
|
||||
|
||||
1. 打开终端,使用 `cd` 命令进入项目文件的根目录下,然后在终端中输入 `git submodule add https://github.com/Hearst-DD/ObjectMapper.git` ,把 ObjectMapper 作为项目的一个 [submodule](http://git-scm.com/docs/git-submodule) 添加进来。
|
||||
2. 打开 `ObjectMapper` 文件,并将 `ObjectMapper.xcodeproj` 拖进你 app 项目的文件导航中。
|
||||
3. 在 Xcode 中,文件导航中点击蓝色项目图标进入到 target 配置界面,在侧边栏的 "TARGETS" 下选择主工程对应的target。
|
||||
4. 确保 `ObjectMapper.framework` 的部署版本( deployment target )和主工程的部署版本保持一致。
|
||||
5. 在配置界面的顶部选项栏中,打开 "Build Phases" 面板。
|
||||
6. 展开 "Target Dependencies" 组,并添加 `ObjectMapper.framework` 。
|
||||
7. 点击面板左上角的 `+` 按钮,选择 "New Copy Files Phase"。将这个阶段重命名为 "Copy Frameworks",设置 "Destination" 为 "Frameworks",最后添加 `ObjectMapper.framework` 。
|
||||
|
||||
|
501
README.md
501
README.md
|
@ -1,501 +0,0 @@
|
|||
ObjectMapper
|
||||
============
|
||||
[](https://github.com/tristanhimmelman/ObjectMapper)
|
||||
[](https://github.com/Carthage/Carthage)
|
||||
[](https://swift.org/package-manager/)
|
||||
[](https://travis-ci.org/tristanhimmelman/ObjectMapper)
|
||||
|
||||
ObjectMapper is a framework written in Swift that makes it easy for you to convert your model objects (classes and structs) to and from JSON.
|
||||
|
||||
- [Features](#features)
|
||||
- [The Basics](#the-basics)
|
||||
- [Mapping Nested Objects](#easy-mapping-of-nested-objects)
|
||||
- [Custom Transformations](#custom-transforms)
|
||||
- [Subclassing](#subclasses)
|
||||
- [Generic Objects](#generic-objects)
|
||||
- [Mapping Context](#mapping-context)
|
||||
- [ObjectMapper + Alamofire](#objectmapper--alamofire)
|
||||
- [ObjectMapper + Realm](#objectmapper--realm)
|
||||
- [Projects using ObjectMapper](#projects-using-objectmapper)
|
||||
- [To Do](#to-do)
|
||||
- [Contributing](#contributing)
|
||||
- [Installation](#installation)
|
||||
|
||||
# Features:
|
||||
- Mapping JSON to objects
|
||||
- Mapping objects to JSON
|
||||
- Nested Objects (stand alone, in arrays or in dictionaries)
|
||||
- Custom transformations during mapping
|
||||
- Struct support
|
||||
- [Immutable support](#immutablemappable-protocol)
|
||||
|
||||
# The Basics
|
||||
To support mapping, a class or struct just needs to implement the ```Mappable``` protocol which includes the following functions:
|
||||
```swift
|
||||
init?(map: Map)
|
||||
mutating func mapping(map: Map)
|
||||
```
|
||||
ObjectMapper uses the ```<-``` operator to define how each member variable maps to and from JSON.
|
||||
|
||||
```swift
|
||||
class User: Mappable {
|
||||
var username: String?
|
||||
var age: Int?
|
||||
var weight: Double!
|
||||
var array: [Any]?
|
||||
var dictionary: [String : Any] = [:]
|
||||
var bestFriend: User? // Nested User object
|
||||
var friends: [User]? // Array of Users
|
||||
var birthday: Date?
|
||||
|
||||
required init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
// Mappable
|
||||
func mapping(map: Map) {
|
||||
username <- map["username"]
|
||||
age <- map["age"]
|
||||
weight <- map["weight"]
|
||||
array <- map["arr"]
|
||||
dictionary <- map["dict"]
|
||||
bestFriend <- map["best_friend"]
|
||||
friends <- map["friends"]
|
||||
birthday <- (map["birthday"], DateTransform())
|
||||
}
|
||||
}
|
||||
|
||||
struct Temperature: Mappable {
|
||||
var celsius: Double?
|
||||
var fahrenheit: Double?
|
||||
|
||||
init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
celsius <- map["celsius"]
|
||||
fahrenheit <- map["fahrenheit"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
Once your class implements `Mappable`, ObjectMapper allows you to easily convert to and from JSON.
|
||||
|
||||
Convert a JSON string to a model object:
|
||||
```swift
|
||||
let user = User(JSONString: JSONString)
|
||||
```
|
||||
|
||||
Convert a model object to a JSON string:
|
||||
```swift
|
||||
let JSONString = user.toJSONString(prettyPrint: true)
|
||||
```
|
||||
|
||||
Alternatively, the `Mapper.swift` class can also be used to accomplish the above (it also provides extra functionality for other situations):
|
||||
```swift
|
||||
// Convert JSON String to Model
|
||||
let user = Mapper<User>().map(JSONString: JSONString)
|
||||
// Create JSON String from Model
|
||||
let JSONString = Mapper().toJSONString(user, prettyPrint: true)
|
||||
```
|
||||
|
||||
ObjectMapper can map classes composed of the following types:
|
||||
- `Int`
|
||||
- `Bool`
|
||||
- `Double`
|
||||
- `Float`
|
||||
- `String`
|
||||
- `RawRepresentable` (Enums)
|
||||
- `Array<Any>`
|
||||
- `Dictionary<String, Any>`
|
||||
- `Object<T: Mappable>`
|
||||
- `Array<T: Mappable>`
|
||||
- `Array<Array<T: Mappable>>`
|
||||
- `Set<T: Mappable>`
|
||||
- `Dictionary<String, T: Mappable>`
|
||||
- `Dictionary<String, Array<T: Mappable>>`
|
||||
- Optionals of all the above
|
||||
- Implicitly Unwrapped Optionals of the above
|
||||
|
||||
## `Mappable` Protocol
|
||||
|
||||
#### `mutating func mapping(map: Map)`
|
||||
This 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.
|
||||
|
||||
#### `init?(map: Map)`
|
||||
This 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:
|
||||
```swift
|
||||
required init?(map: Map){
|
||||
// check if a required "name" property exists within the JSON.
|
||||
if map.JSON["name"] == nil {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## `StaticMappable` Protocol
|
||||
`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)`.
|
||||
|
||||
Note: `StaticMappable`, like `Mappable`, is a sub protocol of `BaseMappable` which is where the `mapping(map: Map)` function is defined.
|
||||
|
||||
#### `static func objectForMapping(map: Map) -> BaseMappable?`
|
||||
ObjectMapper 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:
|
||||
- validate JSON prior to object serialization
|
||||
- provide an existing cached object to be used for mapping
|
||||
- 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://github.com/Hearst-DD/ObjectMapper/blob/master/Tests/ObjectMapperTests/ClassClusterTests.swift#L67))
|
||||
|
||||
If you need to implement ObjectMapper in an extension, you will need to adopt this protocol instead of `Mappable`.
|
||||
|
||||
## `ImmutableMappable` Protocol
|
||||
|
||||
`ImmutableMappable` provides the ability to map immutable properties. This is how `ImmutableMappable` differs from `Mappable`:
|
||||
|
||||
<table>
|
||||
<tr>
|
||||
<th>ImmutableMappable</th>
|
||||
<th>Mappable</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">Properties</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
<strong>let</strong> id: Int
|
||||
<strong>let</strong> name: String?
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
var id: Int!
|
||||
var name: String?
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">JSON -> Model</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
init(map: Map) <strong>throws</strong> {
|
||||
id = <strong>try</strong> map.value("id")
|
||||
name = <strong>try?</strong> map.value("name")
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
mutating func mapping(map: Map) {
|
||||
id <- map["id"]
|
||||
name <- map["name"]
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">Model -> JSON</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
func mapping(map: Map) {
|
||||
id <strong>>>></strong> map["id"]
|
||||
name <strong>>>></strong> map["name"]
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
mutating func mapping(map: Map) {
|
||||
id <- map["id"]
|
||||
name <- map["name"]
|
||||
}
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<th colspan="2">Initializing</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<pre>
|
||||
<strong>try</strong> User(JSONString: JSONString)
|
||||
</pre>
|
||||
</td>
|
||||
<td>
|
||||
<pre>
|
||||
User(JSONString: JSONString)
|
||||
</pre>
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
|
||||
#### `init(map: Map) throws`
|
||||
|
||||
This throwable initializer is used to map immutable properties from the given `Map`. Every immutable property should be initialized in this initializer.
|
||||
|
||||
This initializer throws an error when:
|
||||
- `Map` fails to get a value for the given key
|
||||
- `Map` fails to transform a value using `Transform`
|
||||
|
||||
`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?`.
|
||||
|
||||
```swift
|
||||
init(map: Map) throws {
|
||||
name = try map.value("name") // throws an error when it fails
|
||||
createdAt = try map.value("createdAt", using: DateTransform()) // throws an error when it fails
|
||||
updatedAt = try? map.value("updatedAt", using: DateTransform()) // optional
|
||||
posts = (try? map.value("posts")) ?? [] // optional + default value
|
||||
surname = try? map.value("surname", default: "DefaultSurname") // optional + default value as an argument
|
||||
}
|
||||
```
|
||||
|
||||
#### `mutating func mapping(map: Map)`
|
||||
|
||||
This method is where the reverse transform is performed (model to JSON). Since immutable properties cannot be mapped with the `<-` operator, developers have to define the reverse transform using the `>>>` operator.
|
||||
|
||||
```swift
|
||||
mutating func mapping(map: Map) {
|
||||
name >>> map["name"]
|
||||
createdAt >>> (map["createdAt"], DateTransform())
|
||||
updatedAt >>> (map["updatedAt"], DateTransform())
|
||||
posts >>> map["posts"]
|
||||
}
|
||||
```
|
||||
|
||||
# Easy Mapping of Nested Objects
|
||||
ObjectMapper supports dot notation within keys for easy mapping of nested objects. Given the following JSON String:
|
||||
```json
|
||||
"distance" : {
|
||||
"text" : "102 ft",
|
||||
"value" : 31
|
||||
}
|
||||
```
|
||||
You can access the nested objects as follows:
|
||||
```swift
|
||||
func mapping(map: Map) {
|
||||
distance <- map["distance.value"]
|
||||
}
|
||||
```
|
||||
Nested keys also support accessing values from an array. Given a JSON response with an array of distances, the value could be accessed as follows:
|
||||
```swift
|
||||
distance <- map["distances.0.value"]
|
||||
```
|
||||
If you have a key that contains `.`, you can individually disable the above feature as follows:
|
||||
```swift
|
||||
func mapping(map: Map) {
|
||||
identifier <- map["app.identifier", nested: false]
|
||||
}
|
||||
```
|
||||
When you have nested keys which contain `.`, you can pass the custom nested key delimiter as follows ([#629](https://github.com/tristanhimmelman/ObjectMapper/pull/629)):
|
||||
```swift
|
||||
func mapping(map: Map) {
|
||||
appName <- map["com.myapp.info->com.myapp.name", delimiter: "->"]
|
||||
}
|
||||
```
|
||||
|
||||
# Custom Transforms
|
||||
ObjectMapper 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 `<-` operator:
|
||||
```swift
|
||||
birthday <- (map["birthday"], DateTransform())
|
||||
```
|
||||
The 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.
|
||||
|
||||
You can easily create your own custom transforms by adopting and implementing the methods in the `TransformType` protocol:
|
||||
```swift
|
||||
public protocol TransformType {
|
||||
associatedtype Object
|
||||
associatedtype JSON
|
||||
|
||||
func transformFromJSON(_ value: Any?) -> Object?
|
||||
func transformToJSON(_ value: Object?) -> JSON?
|
||||
}
|
||||
```
|
||||
|
||||
### TransformOf
|
||||
In 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.
|
||||
|
||||
For example, if you want to transform a JSON `String` value to an `Int` you could use `TransformOf` as follows:
|
||||
```swift
|
||||
let transform = TransformOf<Int, String>(fromJSON: { (value: String?) -> Int? in
|
||||
// transform value from String? to Int?
|
||||
return Int(value!)
|
||||
}, toJSON: { (value: Int?) -> String? in
|
||||
// transform value from Int? to String?
|
||||
if let value = value {
|
||||
return String(value)
|
||||
}
|
||||
return nil
|
||||
})
|
||||
|
||||
id <- (map["id"], transform)
|
||||
```
|
||||
Here is a more condensed version of the above:
|
||||
```swift
|
||||
id <- (map["id"], TransformOf<Int, String>(fromJSON: { Int($0!) }, toJSON: { $0.map { String($0) } }))
|
||||
```
|
||||
|
||||
# Subclasses
|
||||
|
||||
Classes that implement the `Mappable` protocol can easily be subclassed. When subclassing mappable classes, follow the structure below:
|
||||
|
||||
```swift
|
||||
class Base: Mappable {
|
||||
var base: String?
|
||||
|
||||
required init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
base <- map["base"]
|
||||
}
|
||||
}
|
||||
|
||||
class Subclass: Base {
|
||||
var sub: String?
|
||||
|
||||
required init?(map: Map) {
|
||||
super.init(map)
|
||||
}
|
||||
|
||||
override func mapping(map: Map) {
|
||||
super.mapping(map)
|
||||
|
||||
sub <- map["sub"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
Make sure your subclass implementation calls the right initializers and mapping functions to also apply the mappings from your superclass.
|
||||
|
||||
# Generic Objects
|
||||
|
||||
ObjectMapper can handle classes with generic types as long as the generic type also conforms to `Mappable`. See the following example:
|
||||
```swift
|
||||
class Result<T: Mappable>: Mappable {
|
||||
var result: T?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
result <- map["result"]
|
||||
}
|
||||
}
|
||||
|
||||
let result = Mapper<Result<User>>().map(JSON)
|
||||
```
|
||||
|
||||
# Mapping Context
|
||||
|
||||
The `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.
|
||||
|
||||
To take advantage of this feature, simply create an object that implements `MapContext` (which is an empty protocol) and pass it into `Mapper` during initialization.
|
||||
```swift
|
||||
struct Context: MapContext {
|
||||
var importantMappingInfo = "Info that I need during mapping"
|
||||
}
|
||||
|
||||
class User: Mappable {
|
||||
var name: String?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map){
|
||||
if let context = map.context as? Context {
|
||||
// use context to make decisions about mapping
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
let context = Context()
|
||||
let user = Mapper<User>(context: context).map(JSONString)
|
||||
```
|
||||
|
||||
# ObjectMapper + Alamofire
|
||||
|
||||
If you are using [Alamofire](https://github.com/Alamofire/Alamofire) for networking and you want to convert your responses to Swift objects, you can use [AlamofireObjectMapper](https://github.com/tristanhimmelman/AlamofireObjectMapper). It is a simple Alamofire extension that uses ObjectMapper to automatically map JSON response data to Swift objects.
|
||||
|
||||
|
||||
# ObjectMapper + Realm
|
||||
|
||||
ObjectMapper 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:
|
||||
|
||||
```swift
|
||||
class Model: Object, Mappable {
|
||||
dynamic var name = ""
|
||||
|
||||
required convenience init?(map: Map) {
|
||||
self.init()
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
name <- map["name"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
If you want to serialize associated RealmObjects, you can use [ObjectMapper+Realm](https://github.com/jakenberg/ObjectMapper-Realm). It is a simple Realm extension that serializes arbitrary JSON into Realm's `List` class.
|
||||
|
||||
To serialize Swift `String`, `Int`, `Double` and `Bool` arrays you can use [ObjectMapperAdditions/Realm](https://github.com/APUtils/ObjectMapperAdditions#realm-features). It'll wrap Swift types into RealmValues that can be stored in Realm's `List` class.
|
||||
|
||||
Note: 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 (`<-`) 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.
|
||||
|
||||
# Projects Using ObjectMapper
|
||||
- [Xcode Plugin for generating `Mappable` and `ImmutableMappable` code](https://github.com/liyanhuadev/ObjectMapper-Plugin)
|
||||
|
||||
- [Json4Swift - Supports generating `ImmutableMappable` structs online (no plugins needed)](http://www.json4swift.com)
|
||||
|
||||
- [JSON to Model - Template based MacOS app which generates structs with customisation.](https://github.com/chanonly123/Json-Model-Generator) [⬇️Download App](https://github.com/chanonly123/Json-Model-Generator/raw/master/JsonToModel.zip)
|
||||
|
||||
If 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.
|
||||
|
||||
# To Do
|
||||
- Improve error handling. Perhaps using `throws`
|
||||
- Class cluster documentation
|
||||
|
||||
# Contributing
|
||||
|
||||
Contributions are very welcome 👍😃.
|
||||
|
||||
Before 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.
|
||||
|
||||
# Installation
|
||||
### Cocoapods
|
||||
ObjectMapper can be added to your project using [CocoaPods 0.36 or later](http://blog.cocoapods.org/Pod-Authors-Guide-to-CocoaPods-Frameworks/) by adding the following line to your `Podfile`:
|
||||
|
||||
```ruby
|
||||
pod 'ObjectMapper', '~> 3.5' (check releases to make sure this is the latest version)
|
||||
```
|
||||
|
||||
### Carthage
|
||||
If you're using [Carthage](https://github.com/Carthage/Carthage) you can add a dependency on ObjectMapper by adding it to your `Cartfile`:
|
||||
|
||||
```
|
||||
github "tristanhimmelman/ObjectMapper" ~> 3.5 (check releases to make sure this is the latest version)
|
||||
```
|
||||
|
||||
### Swift Package Manager
|
||||
To add ObjectMapper to a [Swift Package Manager](https://swift.org/package-manager/) based project, add:
|
||||
|
||||
```swift
|
||||
.package(url: "https://github.com/tristanhimmelman/ObjectMapper.git", .upToNextMajor(from: "4.1.0")),
|
||||
```
|
||||
to your `Package.swift` files `dependencies` array.
|
||||
|
||||
### Submodule
|
||||
Otherwise, ObjectMapper can be added as a submodule:
|
||||
|
||||
1. Add ObjectMapper as a [submodule](http://git-scm.com/docs/git-submodule) by opening the terminal, `cd`-ing into your top-level project directory, and entering the command `git submodule add https://github.com/tristanhimmelman/ObjectMapper.git`
|
||||
2. Open the `ObjectMapper` folder, and drag `ObjectMapper.xcodeproj` into the file navigator of your app project.
|
||||
3. 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.
|
||||
4. Ensure that the deployment target of `ObjectMapper.framework` matches that of the application target.
|
||||
5. In the tab bar at the top of that window, open the "Build Phases" panel.
|
||||
6. Expand the "Target Dependencies" group, and add `ObjectMapper.framework`.
|
||||
7. 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`.
|
|
@ -1,73 +0,0 @@
|
|||
//
|
||||
// CodableTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Jari Kalinainen on 10/10/2018.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
/// Transforms JSON dictionary to Codable type T and back
|
||||
open class CodableTransform<T: Codable>: TransformType {
|
||||
|
||||
public typealias Object = T
|
||||
public typealias JSON = Any
|
||||
|
||||
public init() {}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> Object? {
|
||||
var _data: Data? = nil
|
||||
switch value {
|
||||
case let dict as [String : Any]:
|
||||
_data = try? JSONSerialization.data(withJSONObject: dict, options: [])
|
||||
case let array as [[String : Any]]:
|
||||
_data = try? JSONSerialization.data(withJSONObject: array, options: [])
|
||||
default:
|
||||
_data = nil
|
||||
}
|
||||
guard let data = _data else { return nil }
|
||||
|
||||
do {
|
||||
let decoder = JSONDecoder()
|
||||
let item = try decoder.decode(T.self, from: data)
|
||||
return item
|
||||
} catch {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: T?) -> JSON? {
|
||||
guard let item = value else {
|
||||
return nil
|
||||
}
|
||||
do {
|
||||
let encoder = JSONEncoder()
|
||||
let data = try encoder.encode(item)
|
||||
let dictionary = try JSONSerialization.jsonObject(with: data, options: .allowFragments)
|
||||
return dictionary
|
||||
} catch {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,40 +0,0 @@
|
|||
//
|
||||
// CustomDateFormatTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Dan McCracken on 3/8/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
open class CustomDateFormatTransform: DateFormatterTransform {
|
||||
|
||||
public init(formatString: String) {
|
||||
let formatter = DateFormatter()
|
||||
formatter.locale = Locale(identifier: "en_US_POSIX")
|
||||
formatter.dateFormat = formatString
|
||||
|
||||
super.init(dateFormatter: formatter)
|
||||
}
|
||||
}
|
|
@ -1,50 +0,0 @@
|
|||
//
|
||||
// DataTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Yagrushkin, Evgeny on 8/30/16.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
open class DataTransform: TransformType {
|
||||
public typealias Object = Data
|
||||
public typealias JSON = String
|
||||
|
||||
public init() {}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> Data? {
|
||||
guard let string = value as? String else{
|
||||
return nil
|
||||
}
|
||||
return Data(base64Encoded: string)
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: Data?) -> String? {
|
||||
guard let data = value else{
|
||||
return nil
|
||||
}
|
||||
return data.base64EncodedString()
|
||||
}
|
||||
}
|
|
@ -1,54 +0,0 @@
|
|||
//
|
||||
// DateFormatterTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-03-09.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
open class DateFormatterTransform: TransformType {
|
||||
public typealias Object = Date
|
||||
public typealias JSON = String
|
||||
|
||||
public let dateFormatter: DateFormatter
|
||||
|
||||
public init(dateFormatter: DateFormatter) {
|
||||
self.dateFormatter = dateFormatter
|
||||
}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> Date? {
|
||||
if let dateString = value as? String {
|
||||
return dateFormatter.date(from: dateString)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: Date?) -> String? {
|
||||
if let date = value {
|
||||
return dateFormatter.string(from: date)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
}
|
|
@ -1,75 +0,0 @@
|
|||
//
|
||||
// DateTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-13.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
open class DateTransform: TransformType {
|
||||
public typealias Object = Date
|
||||
public typealias JSON = Double
|
||||
|
||||
public enum Unit: TimeInterval {
|
||||
case seconds = 1
|
||||
case milliseconds = 1_000
|
||||
|
||||
func addScale(to interval: TimeInterval) -> TimeInterval {
|
||||
return interval * rawValue
|
||||
}
|
||||
|
||||
func removeScale(from interval: TimeInterval) -> TimeInterval {
|
||||
return interval / rawValue
|
||||
}
|
||||
}
|
||||
|
||||
private let unit: Unit
|
||||
|
||||
public init(unit: Unit = .seconds) {
|
||||
self.unit = unit
|
||||
}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> Date? {
|
||||
var timeInterval: TimeInterval?
|
||||
if let timeInt = value as? Double {
|
||||
timeInterval = TimeInterval(timeInt)
|
||||
}
|
||||
|
||||
if let timeStr = value as? String {
|
||||
timeInterval = TimeInterval(atof(timeStr))
|
||||
}
|
||||
|
||||
return timeInterval.flatMap {
|
||||
return Date(timeIntervalSince1970: unit.removeScale(from: $0))
|
||||
}
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: Date?) -> Double? {
|
||||
if let date = value {
|
||||
return Double(unit.addScale(to: date.timeIntervalSince1970))
|
||||
}
|
||||
return nil
|
||||
}
|
||||
}
|
|
@ -1,76 +0,0 @@
|
|||
//
|
||||
// DictionaryTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Milen Halachev on 7/20/16.
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
///Transforms [String: AnyObject] <-> [Key: Value] where Key is RawRepresentable as String, Value is Mappable
|
||||
public struct DictionaryTransform<Key, Value>: TransformType where Key: Hashable, Key: RawRepresentable, Key.RawValue == String, Value: Mappable {
|
||||
|
||||
public init() {
|
||||
|
||||
}
|
||||
|
||||
public func transformFromJSON(_ value: Any?) -> [Key: Value]? {
|
||||
|
||||
guard let json = value as? [String: Any] else {
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
let result = json.reduce([:]) { (result, element) -> [Key: Value] in
|
||||
|
||||
guard
|
||||
let key = Key(rawValue: element.0),
|
||||
let valueJSON = element.1 as? [String: Any],
|
||||
let value = Value(JSON: valueJSON)
|
||||
else {
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
var result = result
|
||||
result[key] = value
|
||||
return result
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
public func transformToJSON(_ value: [Key: Value]?) -> Any? {
|
||||
|
||||
let result = value?.reduce([:]) { (result, element) -> [String: Any] in
|
||||
|
||||
let key = element.0.rawValue
|
||||
let value = element.1.toJSON()
|
||||
|
||||
var result = result
|
||||
result[key] = value
|
||||
return result
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
}
|
|
@ -1,120 +0,0 @@
|
|||
//
|
||||
// EnumOperators.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2016-09-26.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
|
||||
// MARK:- Raw Representable types
|
||||
|
||||
/// Object of Raw Representable type
|
||||
public func <- <T: RawRepresentable>(left: inout T, right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
|
||||
public func >>> <T: RawRepresentable>(left: T, right: Map) {
|
||||
left >>> (right, EnumTransform())
|
||||
}
|
||||
|
||||
|
||||
/// Optional Object of Raw Representable type
|
||||
public func <- <T: RawRepresentable>(left: inout T?, right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
|
||||
public func >>> <T: RawRepresentable>(left: T?, right: Map) {
|
||||
left >>> (right, EnumTransform())
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly Unwrapped Optional Object of Raw Representable type
|
||||
public func <- <T: RawRepresentable>(left: inout T!, right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Arrays of Raw Representable type
|
||||
|
||||
/// Array of Raw Representable object
|
||||
public func <- <T: RawRepresentable>(left: inout [T], right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
|
||||
public func >>> <T: RawRepresentable>(left: [T], right: Map) {
|
||||
left >>> (right, EnumTransform())
|
||||
}
|
||||
|
||||
|
||||
/// Array of Raw Representable object
|
||||
public func <- <T: RawRepresentable>(left: inout [T]?, right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
|
||||
public func >>> <T: RawRepresentable>(left: [T]?, right: Map) {
|
||||
left >>> (right, EnumTransform())
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Array of Raw Representable object
|
||||
public func <- <T: RawRepresentable>(left: inout [T]!, right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Dictionaries of Raw Representable type
|
||||
|
||||
/// Dictionary of Raw Representable object
|
||||
public func <- <T: RawRepresentable>(left: inout [String: T], right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
|
||||
public func >>> <T: RawRepresentable>(left: [String: T], right: Map) {
|
||||
left >>> (right, EnumTransform())
|
||||
}
|
||||
|
||||
|
||||
/// Dictionary of Raw Representable object
|
||||
public func <- <T: RawRepresentable>(left: inout [String: T]?, right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
|
||||
public func >>> <T: RawRepresentable>(left: [String: T]?, right: Map) {
|
||||
left >>> (right, EnumTransform())
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Dictionary of Raw Representable object
|
||||
public func <- <T: RawRepresentable>(left: inout [String: T]!, right: Map) {
|
||||
left <- (right, EnumTransform())
|
||||
}
|
||||
#endif
|
|
@ -1,50 +0,0 @@
|
|||
//
|
||||
// EnumTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Kaan Dedeoglu on 3/20/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
open class EnumTransform<T: RawRepresentable>: TransformType {
|
||||
public typealias Object = T
|
||||
public typealias JSON = T.RawValue
|
||||
|
||||
public init() {}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> T? {
|
||||
if let raw = value as? T.RawValue {
|
||||
return T(rawValue: raw)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: T?) -> T.RawValue? {
|
||||
if let obj = value {
|
||||
return obj.rawValue
|
||||
}
|
||||
return nil
|
||||
}
|
||||
}
|
|
@ -1,202 +0,0 @@
|
|||
//
|
||||
// FromJSON.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-09.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2016 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
internal final class FromJSON {
|
||||
|
||||
/// Basic type
|
||||
class func basicType<FieldType>(_ field: inout FieldType, object: FieldType?) {
|
||||
if let value = object {
|
||||
field = value
|
||||
}
|
||||
}
|
||||
|
||||
/// optional basic type
|
||||
class func optionalBasicType<FieldType>(_ field: inout FieldType?, object: FieldType?) {
|
||||
field = object
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional basic type
|
||||
class func optionalBasicType<FieldType>(_ field: inout FieldType!, object: FieldType?) {
|
||||
field = object
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Mappable object
|
||||
class func object<N: BaseMappable>(_ field: inout N, map: Map) {
|
||||
if map.toObject {
|
||||
field = Mapper(context: map.context).map(JSONObject: map.currentValue, toObject: field)
|
||||
} else if let value: N = Mapper(context: map.context).map(JSONObject: map.currentValue) {
|
||||
field = value
|
||||
}
|
||||
}
|
||||
|
||||
/// Optional Mappable Object
|
||||
|
||||
class func optionalObject<N: BaseMappable>(_ field: inout N?, map: Map) {
|
||||
if let f = field , map.toObject && map.currentValue != nil {
|
||||
field = Mapper(context: map.context).map(JSONObject: map.currentValue, toObject: f)
|
||||
} else {
|
||||
field = Mapper(context: map.context).map(JSONObject: map.currentValue)
|
||||
}
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional Mappable Object
|
||||
class func optionalObject<N: BaseMappable>(_ field: inout N!, map: Map) {
|
||||
if let f = field , map.toObject && map.currentValue != nil {
|
||||
field = Mapper(context: map.context).map(JSONObject: map.currentValue, toObject: f)
|
||||
} else {
|
||||
field = Mapper(context: map.context).map(JSONObject: map.currentValue)
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/// mappable object array
|
||||
class func objectArray<N: BaseMappable>(_ field: inout Array<N>, map: Map) {
|
||||
if let objects = Mapper<N>(context: map.context).mapArray(JSONObject: map.currentValue) {
|
||||
field = objects
|
||||
}
|
||||
}
|
||||
|
||||
/// optional mappable object array
|
||||
|
||||
class func optionalObjectArray<N: BaseMappable>(_ field: inout Array<N>?, map: Map) {
|
||||
if let objects: Array<N> = Mapper(context: map.context).mapArray(JSONObject: map.currentValue) {
|
||||
field = objects
|
||||
} else {
|
||||
field = nil
|
||||
}
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional mappable object array
|
||||
class func optionalObjectArray<N: BaseMappable>(_ field: inout Array<N>!, map: Map) {
|
||||
if let objects: Array<N> = Mapper(context: map.context).mapArray(JSONObject: map.currentValue) {
|
||||
field = objects
|
||||
} else {
|
||||
field = nil
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/// mappable object array
|
||||
class func twoDimensionalObjectArray<N: BaseMappable>(_ field: inout Array<Array<N>>, map: Map) {
|
||||
if let objects = Mapper<N>(context: map.context).mapArrayOfArrays(JSONObject: map.currentValue) {
|
||||
field = objects
|
||||
}
|
||||
}
|
||||
|
||||
/// optional mappable 2 dimentional object array
|
||||
class func optionalTwoDimensionalObjectArray<N: BaseMappable>(_ field: inout Array<Array<N>>?, map: Map) {
|
||||
field = Mapper(context: map.context).mapArrayOfArrays(JSONObject: map.currentValue)
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional 2 dimentional mappable object array
|
||||
class func optionalTwoDimensionalObjectArray<N: BaseMappable>(_ field: inout Array<Array<N>>!, map: Map) {
|
||||
field = Mapper(context: map.context).mapArrayOfArrays(JSONObject: map.currentValue)
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Dctionary containing Mappable objects
|
||||
class func objectDictionary<N: BaseMappable>(_ field: inout Dictionary<String, N>, map: Map) {
|
||||
if map.toObject {
|
||||
field = Mapper<N>(context: map.context).mapDictionary(JSONObject: map.currentValue, toDictionary: field)
|
||||
} else {
|
||||
if let objects = Mapper<N>(context: map.context).mapDictionary(JSONObject: map.currentValue) {
|
||||
field = objects
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Optional dictionary containing Mappable objects
|
||||
class func optionalObjectDictionary<N: BaseMappable>(_ field: inout Dictionary<String, N>?, map: Map) {
|
||||
if let f = field , map.toObject && map.currentValue != nil {
|
||||
field = Mapper(context: map.context).mapDictionary(JSONObject: map.currentValue, toDictionary: f)
|
||||
} else {
|
||||
field = Mapper(context: map.context).mapDictionary(JSONObject: map.currentValue)
|
||||
}
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Dictionary containing Mappable objects
|
||||
class func optionalObjectDictionary<N: BaseMappable>(_ field: inout Dictionary<String, N>!, map: Map) {
|
||||
if let f = field , map.toObject && map.currentValue != nil {
|
||||
field = Mapper(context: map.context).mapDictionary(JSONObject: map.currentValue, toDictionary: f)
|
||||
} else {
|
||||
field = Mapper(context: map.context).mapDictionary(JSONObject: map.currentValue)
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Dictionary containing Array of Mappable objects
|
||||
class func objectDictionaryOfArrays<N: BaseMappable>(_ field: inout Dictionary<String, [N]>, map: Map) {
|
||||
if let objects = Mapper<N>(context: map.context).mapDictionaryOfArrays(JSONObject: map.currentValue) {
|
||||
field = objects
|
||||
}
|
||||
}
|
||||
|
||||
/// Optional Dictionary containing Array of Mappable objects
|
||||
class func optionalObjectDictionaryOfArrays<N: BaseMappable>(_ field: inout Dictionary<String, [N]>?, map: Map) {
|
||||
field = Mapper<N>(context: map.context).mapDictionaryOfArrays(JSONObject: map.currentValue)
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Dictionary containing Array of Mappable objects
|
||||
class func optionalObjectDictionaryOfArrays<N: BaseMappable>(_ field: inout Dictionary<String, [N]>!, map: Map) {
|
||||
field = Mapper<N>(context: map.context).mapDictionaryOfArrays(JSONObject: map.currentValue)
|
||||
}
|
||||
#endif
|
||||
|
||||
/// mappable object Set
|
||||
class func objectSet<N: BaseMappable>(_ field: inout Set<N>, map: Map) {
|
||||
if let objects = Mapper<N>(context: map.context).mapSet(JSONObject: map.currentValue) {
|
||||
field = objects
|
||||
}
|
||||
}
|
||||
|
||||
/// optional mappable object array
|
||||
class func optionalObjectSet<N: BaseMappable>(_ field: inout Set<N>?, map: Map) {
|
||||
field = Mapper(context: map.context).mapSet(JSONObject: map.currentValue)
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional mappable object array
|
||||
class func optionalObjectSet<N: BaseMappable>(_ field: inout Set<N>!, map: Map) {
|
||||
field = Mapper(context: map.context).mapSet(JSONObject: map.currentValue)
|
||||
}
|
||||
#endif
|
||||
}
|
|
@ -1,144 +0,0 @@
|
|||
//
|
||||
// HexColorTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Vitaliy Kuzmenko on 10/10/16.
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
#if os(iOS) || os(tvOS) || os(watchOS)
|
||||
import UIKit
|
||||
#elseif os(macOS)
|
||||
import Cocoa
|
||||
#endif
|
||||
|
||||
#if os(iOS) || os(tvOS) || os(watchOS) || os(macOS)
|
||||
open class HexColorTransform: TransformType {
|
||||
|
||||
#if os(iOS) || os(tvOS) || os(watchOS)
|
||||
public typealias Object = UIColor
|
||||
#else
|
||||
public typealias Object = NSColor
|
||||
#endif
|
||||
|
||||
public typealias JSON = String
|
||||
|
||||
var prefix: Bool = false
|
||||
|
||||
var alpha: Bool = false
|
||||
|
||||
public init(prefixToJSON: Bool = false, alphaToJSON: Bool = false) {
|
||||
alpha = alphaToJSON
|
||||
prefix = prefixToJSON
|
||||
}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> Object? {
|
||||
if let rgba = value as? String {
|
||||
if rgba.hasPrefix("#") {
|
||||
let index = rgba.index(rgba.startIndex, offsetBy: 1)
|
||||
let hex = String(rgba[index...])
|
||||
return getColor(hex: hex)
|
||||
} else {
|
||||
return getColor(hex: rgba)
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: Object?) -> JSON? {
|
||||
if let value = value {
|
||||
return hexString(color: value)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
fileprivate func hexString(color: Object) -> String {
|
||||
let comps = color.cgColor.components!
|
||||
let compsCount = color.cgColor.numberOfComponents
|
||||
let r: Int
|
||||
let g: Int
|
||||
var b: Int
|
||||
let a = Int(comps[compsCount - 1] * 255)
|
||||
if compsCount == 4 { // RGBA
|
||||
r = Int(comps[0] * 255)
|
||||
g = Int(comps[1] * 255)
|
||||
b = Int(comps[2] * 255)
|
||||
} else { // Grayscale
|
||||
r = Int(comps[0] * 255)
|
||||
g = Int(comps[0] * 255)
|
||||
b = Int(comps[0] * 255)
|
||||
}
|
||||
var hexString: String = ""
|
||||
if prefix {
|
||||
hexString = "#"
|
||||
}
|
||||
hexString += String(format: "%02X%02X%02X", r, g, b)
|
||||
|
||||
if alpha {
|
||||
hexString += String(format: "%02X", a)
|
||||
}
|
||||
return hexString
|
||||
}
|
||||
|
||||
fileprivate func getColor(hex: String) -> Object? {
|
||||
var red: CGFloat = 0.0
|
||||
var green: CGFloat = 0.0
|
||||
var blue: CGFloat = 0.0
|
||||
var alpha: CGFloat = 1.0
|
||||
|
||||
let scanner = Scanner(string: hex)
|
||||
var hexValue: CUnsignedLongLong = 0
|
||||
if scanner.scanHexInt64(&hexValue) {
|
||||
switch (hex.count) {
|
||||
case 3:
|
||||
red = CGFloat((hexValue & 0xF00) >> 8) / 15.0
|
||||
green = CGFloat((hexValue & 0x0F0) >> 4) / 15.0
|
||||
blue = CGFloat(hexValue & 0x00F) / 15.0
|
||||
case 4:
|
||||
red = CGFloat((hexValue & 0xF000) >> 12) / 15.0
|
||||
green = CGFloat((hexValue & 0x0F00) >> 8) / 15.0
|
||||
blue = CGFloat((hexValue & 0x00F0) >> 4) / 15.0
|
||||
alpha = CGFloat(hexValue & 0x000F) / 15.0
|
||||
case 6:
|
||||
red = CGFloat((hexValue & 0xFF0000) >> 16) / 255.0
|
||||
green = CGFloat((hexValue & 0x00FF00) >> 8) / 255.0
|
||||
blue = CGFloat(hexValue & 0x0000FF) / 255.0
|
||||
case 8:
|
||||
red = CGFloat((hexValue & 0xFF000000) >> 24) / 255.0
|
||||
green = CGFloat((hexValue & 0x00FF0000) >> 16) / 255.0
|
||||
blue = CGFloat((hexValue & 0x0000FF00) >> 8) / 255.0
|
||||
alpha = CGFloat(hexValue & 0x000000FF) / 255.0
|
||||
default:
|
||||
// Invalid RGB string, number of characters after '#' should be either 3, 4, 6 or 8
|
||||
return nil
|
||||
}
|
||||
} else {
|
||||
// "Scan hex error
|
||||
return nil
|
||||
}
|
||||
#if os(iOS) || os(tvOS) || os(watchOS)
|
||||
return UIColor(red: red, green: green, blue: blue, alpha: alpha)
|
||||
#else
|
||||
return NSColor(red: red, green: green, blue: blue, alpha: alpha)
|
||||
#endif
|
||||
}
|
||||
}
|
||||
#endif
|
|
@ -1,47 +0,0 @@
|
|||
//
|
||||
// ISO8601DateTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Jean-Pierre Mouilleseaux on 21 Nov 2014.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
public extension DateFormatter {
|
||||
convenience init(withFormat format : String, locale : String) {
|
||||
self.init()
|
||||
self.locale = Locale(identifier: locale)
|
||||
dateFormat = format
|
||||
}
|
||||
}
|
||||
|
||||
open class ISO8601DateTransform: DateFormatterTransform {
|
||||
|
||||
static let reusableISODateFormatter = DateFormatter(withFormat: "yyyy-MM-dd'T'HH:mm:ssZZZZZ", locale: "en_US_POSIX")
|
||||
|
||||
public init() {
|
||||
super.init(dateFormatter: ISO8601DateTransform.reusableISODateFormatter)
|
||||
}
|
||||
}
|
||||
|
|
@ -1,376 +0,0 @@
|
|||
//
|
||||
// ImmutableMappble.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Suyeol Jeon on 23/09/2016.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
public protocol ImmutableMappable: BaseMappable {
|
||||
init(map: Map) throws
|
||||
}
|
||||
|
||||
public extension ImmutableMappable {
|
||||
|
||||
/// Implement this method to support object -> JSON transform.
|
||||
func mapping(map: Map) {}
|
||||
|
||||
/// Initializes object from a JSON String
|
||||
init(JSONString: String, context: MapContext? = nil) throws {
|
||||
self = try Mapper(context: context).map(JSONString: JSONString)
|
||||
}
|
||||
|
||||
/// Initializes object from a JSON Dictionary
|
||||
init(JSON: [String: Any], context: MapContext? = nil) throws {
|
||||
self = try Mapper(context: context).map(JSON: JSON)
|
||||
}
|
||||
|
||||
/// Initializes object from a JSONObject
|
||||
init(JSONObject: Any, context: MapContext? = nil) throws {
|
||||
self = try Mapper(context: context).map(JSONObject: JSONObject)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public extension Map {
|
||||
|
||||
fileprivate func currentValue(for key: String, nested: Bool? = nil, delimiter: String = ".") -> Any? {
|
||||
let isNested = nested ?? key.contains(delimiter)
|
||||
return self[key, nested: isNested, delimiter: delimiter].currentValue
|
||||
}
|
||||
|
||||
// MARK: Basic
|
||||
|
||||
/// Returns a value or throws an error.
|
||||
func value<T>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> T {
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let value = currentValue as? T else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '\(T.self)'", file: file, function: function, line: line)
|
||||
}
|
||||
return value
|
||||
}
|
||||
|
||||
/// Returns a transformed value or throws an error.
|
||||
func value<Transform: TransformType>(_ key: String, nested: Bool? = nil, delimiter: String = ".", using transform: Transform, file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> Transform.Object {
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let value = transform.transformFromJSON(currentValue) else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot transform to '\(Transform.Object.self)' using \(transform)", file: file, function: function, line: line)
|
||||
}
|
||||
return value
|
||||
}
|
||||
|
||||
/// Returns a RawRepresentable type or throws an error.
|
||||
func value<T: RawRepresentable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> T {
|
||||
return try self.value(key, nested: nested, delimiter: delimiter, using: EnumTransform(), file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
/// Returns a RawRepresentable type or throws an error.
|
||||
func value<T: RawRepresentable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> T? {
|
||||
return try self.value(key, nested: nested, delimiter: delimiter, using: EnumTransform(), file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
/// Returns a `[RawRepresentable]` type or throws an error.
|
||||
func value<T: RawRepresentable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [T] {
|
||||
return try self.value(key, nested: nested, delimiter: delimiter, using: EnumTransform(), file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
/// Returns a `[RawRepresentable]` type or throws an error.
|
||||
func value<T: RawRepresentable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [T]? {
|
||||
return try self.value(key, nested: nested, delimiter: delimiter, using: EnumTransform(), file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
// MARK: BaseMappable
|
||||
|
||||
/// Returns a `BaseMappable` object or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> T {
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let JSONObject = currentValue else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Found unexpected nil value", file: file, function: function, line: line)
|
||||
}
|
||||
return try Mapper<T>(context: context).mapOrFail(JSONObject: JSONObject)
|
||||
}
|
||||
|
||||
/// Returns a `BaseMappable` object boxed in `Optional` or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> T? {
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let JSONObject = currentValue else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Found unexpected nil value", file: file, function: function, line: line)
|
||||
}
|
||||
return try Mapper<T>(context: context).mapOrFail(JSONObject: JSONObject)
|
||||
}
|
||||
|
||||
// MARK: [BaseMappable]
|
||||
|
||||
/// Returns a `[BaseMappable]` or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [T] {
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let jsonArray = currentValue as? [Any] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[Any]'", file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
return try jsonArray.map { JSONObject -> T in
|
||||
return try Mapper<T>(context: context).mapOrFail(JSONObject: JSONObject)
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns a `[BaseMappable]` boxed in `Optional` or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [T]? {
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let jsonArray = currentValue as? [Any] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[Any]'", file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
return try jsonArray.map { JSONObject -> T in
|
||||
return try Mapper<T>(context: context).mapOrFail(JSONObject: JSONObject)
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns a `[BaseMappable]` using transform or throws an error.
|
||||
func value<Transform: TransformType>(_ key: String, nested: Bool? = nil, delimiter: String = ".", using transform: Transform, file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [Transform.Object] {
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let jsonArray = currentValue as? [Any] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[Any]'", file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
return try jsonArray.map { json -> Transform.Object in
|
||||
guard let object = transform.transformFromJSON(json) else {
|
||||
throw MapError(key: "\(key)", currentValue: json, reason: "Cannot transform to '\(Transform.Object.self)' using \(transform)", file: file, function: function, line: line)
|
||||
}
|
||||
return object
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: [String: BaseMappable]
|
||||
|
||||
/// Returns a `[String: BaseMappable]` or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [String: T] {
|
||||
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let jsonDictionary = currentValue as? [String: Any] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[String: Any]'", file: file, function: function, line: line)
|
||||
}
|
||||
return try jsonDictionary.mapValues { json in
|
||||
return try Mapper<T>(context: context).mapOrFail(JSONObject: json)
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns a `[String: BaseMappable]` boxed in `Optional` or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [String: T]? {
|
||||
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let jsonDictionary = currentValue as? [String: Any] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[String: Any]'", file: file, function: function, line: line)
|
||||
}
|
||||
var value: [String: T] = [:]
|
||||
for (key, json) in jsonDictionary {
|
||||
value[key] = try Mapper<T>(context: context).mapOrFail(JSONObject: json)
|
||||
}
|
||||
return value
|
||||
}
|
||||
|
||||
/// Returns a `[String: BaseMappable]` using transform or throws an error.
|
||||
func value<Transform: TransformType>(_ key: String, nested: Bool? = nil, delimiter: String = ".", using transform: Transform, file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [String: Transform.Object] {
|
||||
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let jsonDictionary = currentValue as? [String: Any] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[String: Any]'", file: file, function: function, line: line)
|
||||
}
|
||||
return try jsonDictionary.mapValues { json in
|
||||
guard let object = transform.transformFromJSON(json) else {
|
||||
throw MapError(key: key, currentValue: json, reason: "Cannot transform to '\(Transform.Object.self)' using \(transform)", file: file, function: function, line: line)
|
||||
}
|
||||
return object
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns a `[String: BaseMappable]` using transform or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [[T]]? {
|
||||
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let json2DArray = currentValue as? [[Any]] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[[Any]]'", file: file, function: function, line: line)
|
||||
}
|
||||
return try json2DArray.map { jsonArray in
|
||||
try jsonArray.map { jsonObject -> T in
|
||||
return try Mapper<T>(context: context).mapOrFail(JSONObject: jsonObject)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: [[BaseMappable]]
|
||||
/// Returns a `[[BaseMappable]]` or throws an error.
|
||||
func value<T: BaseMappable>(_ key: String, nested: Bool? = nil, delimiter: String = ".", file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [[T]] {
|
||||
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let json2DArray = currentValue as? [[Any]] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[[Any]]'", file: file, function: function, line: line)
|
||||
}
|
||||
return try json2DArray.map { jsonArray in
|
||||
try jsonArray.map { jsonObject -> T in
|
||||
return try Mapper<T>(context: context).mapOrFail(JSONObject: jsonObject)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns a `[[BaseMappable]]` using transform or throws an error.
|
||||
func value<Transform: TransformType>(_ key: String, nested: Bool? = nil, delimiter: String = ".", using transform: Transform, file: StaticString = #file, function: StaticString = #function, line: UInt = #line) throws -> [[Transform.Object]] {
|
||||
|
||||
let currentValue = self.currentValue(for: key, nested: nested, delimiter: delimiter)
|
||||
guard let json2DArray = currentValue as? [[Any]] else {
|
||||
throw MapError(key: key, currentValue: currentValue, reason: "Cannot cast to '[[Any]]'",
|
||||
file: file, function: function, line: line)
|
||||
}
|
||||
|
||||
return try json2DArray.map { jsonArray in
|
||||
try jsonArray.map { json -> Transform.Object in
|
||||
guard let object = transform.transformFromJSON(json) else {
|
||||
throw MapError(key: "\(key)", currentValue: json, reason: "Cannot transform to '\(Transform.Object.self)' using \(transform)", file: file, function: function, line: line)
|
||||
}
|
||||
return object
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public extension Mapper where N: ImmutableMappable {
|
||||
|
||||
func map(JSON: [String: Any]) throws -> N {
|
||||
return try self.mapOrFail(JSON: JSON)
|
||||
}
|
||||
|
||||
func map(JSONString: String) throws -> N {
|
||||
return try mapOrFail(JSONString: JSONString)
|
||||
}
|
||||
|
||||
func map(JSONObject: Any) throws -> N {
|
||||
return try mapOrFail(JSONObject: JSONObject)
|
||||
}
|
||||
|
||||
// MARK: Array mapping functions
|
||||
|
||||
func mapArray(JSONArray: [[String: Any]]) throws -> [N] {
|
||||
#if swift(>=4.1)
|
||||
return try JSONArray.compactMap(mapOrFail)
|
||||
#else
|
||||
return try JSONArray.flatMap(mapOrFail)
|
||||
#endif
|
||||
}
|
||||
|
||||
func mapArray(JSONString: String) throws -> [N] {
|
||||
guard let JSONObject = Mapper.parseJSONString(JSONString: JSONString) else {
|
||||
throw MapError(key: nil, currentValue: JSONString, reason: "Cannot convert string into Any'")
|
||||
}
|
||||
|
||||
return try mapArray(JSONObject: JSONObject)
|
||||
}
|
||||
|
||||
func mapArray(JSONObject: Any) throws -> [N] {
|
||||
guard let JSONArray = JSONObject as? [[String: Any]] else {
|
||||
throw MapError(key: nil, currentValue: JSONObject, reason: "Cannot cast to '[[String: Any]]'")
|
||||
}
|
||||
|
||||
return try mapArray(JSONArray: JSONArray)
|
||||
}
|
||||
|
||||
// MARK: Dictionary mapping functions
|
||||
|
||||
func mapDictionary(JSONString: String) throws -> [String: N] {
|
||||
guard let JSONObject = Mapper.parseJSONString(JSONString: JSONString) else {
|
||||
throw MapError(key: nil, currentValue: JSONString, reason: "Cannot convert string into Any'")
|
||||
}
|
||||
|
||||
return try mapDictionary(JSONObject: JSONObject)
|
||||
}
|
||||
|
||||
func mapDictionary(JSONObject: Any?) throws -> [String: N] {
|
||||
guard let JSON = JSONObject as? [String: [String: Any]] else {
|
||||
throw MapError(key: nil, currentValue: JSONObject, reason: "Cannot cast to '[String: [String: Any]]''")
|
||||
}
|
||||
|
||||
return try mapDictionary(JSON: JSON)
|
||||
}
|
||||
|
||||
func mapDictionary(JSON: [String: [String: Any]]) throws -> [String: N] {
|
||||
return try JSON.filterMap(mapOrFail)
|
||||
}
|
||||
|
||||
// MARK: Dictinoary of arrays mapping functions
|
||||
|
||||
func mapDictionaryOfArrays(JSONObject: Any?) throws -> [String: [N]] {
|
||||
guard let JSON = JSONObject as? [String: [[String: Any]]] else {
|
||||
throw MapError(key: nil, currentValue: JSONObject, reason: "Cannot cast to '[String: [String: Any]]''")
|
||||
}
|
||||
return try mapDictionaryOfArrays(JSON: JSON)
|
||||
}
|
||||
|
||||
func mapDictionaryOfArrays(JSON: [String: [[String: Any]]]) throws -> [String: [N]] {
|
||||
return try JSON.filterMap { array -> [N] in
|
||||
try mapArray(JSONArray: array)
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: 2 dimentional array mapping functions
|
||||
|
||||
func mapArrayOfArrays(JSONObject: Any?) throws -> [[N]] {
|
||||
guard let JSONArray = JSONObject as? [[[String: Any]]] else {
|
||||
throw MapError(key: nil, currentValue: JSONObject, reason: "Cannot cast to '[[[String: Any]]]''")
|
||||
}
|
||||
return try JSONArray.map(mapArray)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
internal extension Mapper {
|
||||
|
||||
func mapOrFail(JSON: [String: Any]) throws -> N {
|
||||
let map = Map(mappingType: .fromJSON, JSON: JSON, context: context, shouldIncludeNilValues: shouldIncludeNilValues)
|
||||
|
||||
// Check if object is ImmutableMappable, if so use ImmutableMappable protocol for mapping
|
||||
if let klass = N.self as? ImmutableMappable.Type,
|
||||
var object = try klass.init(map: map) as? N {
|
||||
object.mapping(map: map)
|
||||
return object
|
||||
}
|
||||
|
||||
// If not, map the object the standard way
|
||||
guard let value = self.map(JSON: JSON) else {
|
||||
throw MapError(key: nil, currentValue: JSON, reason: "Cannot map to '\(N.self)'")
|
||||
}
|
||||
return value
|
||||
}
|
||||
|
||||
func mapOrFail(JSONString: String) throws -> N {
|
||||
guard let JSON = Mapper.parseJSONStringIntoDictionary(JSONString: JSONString) else {
|
||||
throw MapError(key: nil, currentValue: JSONString, reason: "Cannot parse into '[String: Any]'")
|
||||
}
|
||||
return try mapOrFail(JSON: JSON)
|
||||
}
|
||||
|
||||
func mapOrFail(JSONObject: Any) throws -> N {
|
||||
guard let JSON = JSONObject as? [String: Any] else {
|
||||
throw MapError(key: nil, currentValue: JSONObject, reason: "Cannot cast to '[String: Any]'")
|
||||
}
|
||||
return try mapOrFail(JSON: JSON)
|
||||
}
|
||||
|
||||
}
|
|
@ -1,26 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>en</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>FMWK</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>0.14</string>
|
||||
<key>CFBundleSignature</key>
|
||||
<string>????</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>$(CURRENT_PROJECT_VERSION)</string>
|
||||
<key>NSPrincipalClass</key>
|
||||
<string></string>
|
||||
</dict>
|
||||
</plist>
|
|
@ -1,171 +0,0 @@
|
|||
//
|
||||
// IntegerOperators.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Suyeol Jeon on 17/02/2017.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
// MARK: - Signed Integer
|
||||
|
||||
/// SignedInteger mapping
|
||||
public func <- <T: SignedInteger>(left: inout T, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
let value: T = toSignedInteger(right.currentValue) ?? 0
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
/// Optional SignedInteger mapping
|
||||
public func <- <T: SignedInteger>(left: inout T?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
let value: T? = toSignedInteger(right.currentValue)
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// ImplicitlyUnwrappedOptional SignedInteger mapping
|
||||
public func <- <T: SignedInteger>(left: inout T!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
let value: T! = toSignedInteger(right.currentValue)
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
// MARK: - Unsigned Integer
|
||||
|
||||
/// UnsignedInteger mapping
|
||||
public func <- <T: UnsignedInteger>(left: inout T, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
let value: T = toUnsignedInteger(right.currentValue) ?? 0
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional UnsignedInteger mapping
|
||||
public func <- <T: UnsignedInteger>(left: inout T?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
let value: T? = toUnsignedInteger(right.currentValue)
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// ImplicitlyUnwrappedOptional UnsignedInteger mapping
|
||||
public func <- <T: UnsignedInteger>(left: inout T!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
let value: T! = toUnsignedInteger(right.currentValue)
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK: - Casting Utils
|
||||
|
||||
/// Convert any value to `SignedInteger`.
|
||||
private func toSignedInteger<T: SignedInteger>(_ value: Any?) -> T? {
|
||||
guard
|
||||
let value = value,
|
||||
case let number as NSNumber = value
|
||||
else {
|
||||
return nil
|
||||
}
|
||||
|
||||
if T.self == Int.self, let x = Int(exactly: number.int64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == Int8.self, let x = Int8(exactly: number.int64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == Int16.self, let x = Int16(exactly: number.int64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == Int32.self, let x = Int32(exactly: number.int64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == Int64.self, let x = Int64(exactly: number.int64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Convert any value to `UnsignedInteger`.
|
||||
private func toUnsignedInteger<T: UnsignedInteger>(_ value: Any?) -> T? {
|
||||
guard
|
||||
let value = value,
|
||||
case let number as NSNumber = value
|
||||
else {
|
||||
return nil
|
||||
}
|
||||
|
||||
if T.self == UInt.self, let x = UInt(exactly: number.uint64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == UInt8.self, let x = UInt8(exactly: number.uint64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == UInt16.self, let x = UInt16(exactly: number.uint64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == UInt32.self, let x = UInt32(exactly: number.uint64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
if T.self == UInt64.self, let x = UInt64(exactly: number.uint64Value) {
|
||||
return T.init(x)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
|
@ -1,246 +0,0 @@
|
|||
//
|
||||
// Map.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-10-09.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
|
||||
import Foundation
|
||||
|
||||
/// MapContext is available for developers who wish to pass information around during the mapping process.
|
||||
public protocol MapContext {
|
||||
|
||||
}
|
||||
|
||||
/// A class used for holding mapping data
|
||||
public final class Map {
|
||||
public let mappingType: MappingType
|
||||
|
||||
public internal(set) var JSON: [String: Any] = [:]
|
||||
public internal(set) var isKeyPresent = false
|
||||
public internal(set) var currentValue: Any?
|
||||
public internal(set) var currentKey: String?
|
||||
var keyIsNested = false
|
||||
public internal(set) var nestedKeyDelimiter: String = "."
|
||||
public var context: MapContext?
|
||||
public var shouldIncludeNilValues = false /// If this is set to true, toJSON output will include null values for any variables that are not set.
|
||||
|
||||
public let toObject: Bool // indicates whether the mapping is being applied to an existing object
|
||||
|
||||
public init(mappingType: MappingType, JSON: [String: Any], toObject: Bool = false, context: MapContext? = nil, shouldIncludeNilValues: Bool = false) {
|
||||
|
||||
self.mappingType = mappingType
|
||||
self.JSON = JSON
|
||||
self.toObject = toObject
|
||||
self.context = context
|
||||
self.shouldIncludeNilValues = shouldIncludeNilValues
|
||||
}
|
||||
|
||||
/// Sets the current mapper value and key.
|
||||
/// The Key paramater can be a period separated string (ex. "distance.value") to access sub objects.
|
||||
public subscript(key: String) -> Map {
|
||||
// save key and value associated to it
|
||||
return self.subscript(key: key)
|
||||
}
|
||||
|
||||
public subscript(key: String, delimiter delimiter: String) -> Map {
|
||||
return self.subscript(key: key, delimiter: delimiter)
|
||||
}
|
||||
|
||||
public subscript(key: String, nested nested: Bool) -> Map {
|
||||
return self.subscript(key: key, nested: nested)
|
||||
}
|
||||
|
||||
public subscript(key: String, nested nested: Bool, delimiter delimiter: String) -> Map {
|
||||
return self.subscript(key: key, nested: nested, delimiter: delimiter)
|
||||
}
|
||||
|
||||
public subscript(key: String, ignoreNil ignoreNil: Bool) -> Map {
|
||||
return self.subscript(key: key, ignoreNil: ignoreNil)
|
||||
}
|
||||
|
||||
public subscript(key: String, delimiter delimiter: String, ignoreNil ignoreNil: Bool) -> Map {
|
||||
return self.subscript(key: key, delimiter: delimiter, ignoreNil: ignoreNil)
|
||||
}
|
||||
|
||||
public subscript(key: String, nested nested: Bool, ignoreNil ignoreNil: Bool) -> Map {
|
||||
return self.subscript(key: key, nested: nested, ignoreNil: ignoreNil)
|
||||
}
|
||||
|
||||
public subscript(key: String, nested nested: Bool?, delimiter delimiter: String, ignoreNil ignoreNil: Bool) -> Map {
|
||||
return self.subscript(key: key, nested: nested, delimiter: delimiter, ignoreNil: ignoreNil)
|
||||
}
|
||||
|
||||
private func `subscript`(key: String, nested: Bool? = nil, delimiter: String = ".", ignoreNil: Bool = false) -> Map {
|
||||
// save key and value associated to it
|
||||
currentKey = key
|
||||
keyIsNested = nested ?? key.contains(delimiter)
|
||||
nestedKeyDelimiter = delimiter
|
||||
|
||||
if mappingType == .fromJSON {
|
||||
// check if a value exists for the current key
|
||||
// do this pre-check for performance reasons
|
||||
if keyIsNested {
|
||||
// break down the components of the key that are separated by delimiter
|
||||
(isKeyPresent, currentValue) = valueFor(ArraySlice(key.components(separatedBy: delimiter)), dictionary: JSON)
|
||||
} else {
|
||||
let object = JSON[key]
|
||||
let isNSNull = object is NSNull
|
||||
isKeyPresent = isNSNull ? true : object != nil
|
||||
currentValue = isNSNull ? nil : object
|
||||
}
|
||||
|
||||
// update isKeyPresent if ignoreNil is true
|
||||
if ignoreNil && currentValue == nil {
|
||||
isKeyPresent = false
|
||||
}
|
||||
}
|
||||
|
||||
return self
|
||||
}
|
||||
|
||||
public func value<T>() -> T? {
|
||||
let value = currentValue as? T
|
||||
|
||||
// Swift 4.1 breaks Float casting from `NSNumber`. So Added extra checks for `Float` `[Float]` and `[String:Float]`
|
||||
if value == nil && T.self == Float.self {
|
||||
if let v = currentValue as? NSNumber {
|
||||
return v.floatValue as? T
|
||||
}
|
||||
} else if value == nil && T.self == [Float].self {
|
||||
if let v = currentValue as? [Double] {
|
||||
#if swift(>=4.1)
|
||||
return v.compactMap{ Float($0) } as? T
|
||||
#else
|
||||
return v.flatMap{ Float($0) } as? T
|
||||
#endif
|
||||
}
|
||||
} else if value == nil && T.self == [String:Float].self {
|
||||
if let v = currentValue as? [String:Double] {
|
||||
return v.mapValues{ Float($0) } as? T
|
||||
}
|
||||
}
|
||||
return value
|
||||
}
|
||||
}
|
||||
|
||||
/// Fetch value from JSON dictionary, loop through keyPathComponents until we reach the desired object
|
||||
private func valueFor(_ keyPathComponents: ArraySlice<String>, dictionary: [String: Any]) -> (Bool, Any?) {
|
||||
// Implement it as a tail recursive function.
|
||||
if keyPathComponents.isEmpty {
|
||||
return (false, nil)
|
||||
}
|
||||
|
||||
if let keyPath = keyPathComponents.first {
|
||||
let isTail = keyPathComponents.count == 1
|
||||
let object = dictionary[keyPath]
|
||||
if object is NSNull {
|
||||
return (isTail, nil)
|
||||
} else if keyPathComponents.count > 1, let dict = object as? [String: Any] {
|
||||
let tail = keyPathComponents.dropFirst()
|
||||
return valueFor(tail, dictionary: dict)
|
||||
} else if keyPathComponents.count > 1, let array = object as? [Any] {
|
||||
let tail = keyPathComponents.dropFirst()
|
||||
return valueFor(tail, array: array)
|
||||
} else {
|
||||
return (isTail && object != nil, object)
|
||||
}
|
||||
}
|
||||
|
||||
return (false, nil)
|
||||
}
|
||||
|
||||
/// Fetch value from JSON Array, loop through keyPathComponents them until we reach the desired object
|
||||
private func valueFor(_ keyPathComponents: ArraySlice<String>, array: [Any]) -> (Bool, Any?) {
|
||||
// Implement it as a tail recursive function.
|
||||
|
||||
if keyPathComponents.isEmpty {
|
||||
return (false, nil)
|
||||
}
|
||||
|
||||
//Try to convert keypath to Int as index
|
||||
if let keyPath = keyPathComponents.first,
|
||||
let index = Int(keyPath) , index >= 0 && index < array.count {
|
||||
|
||||
let isTail = keyPathComponents.count == 1
|
||||
let object = array[index]
|
||||
|
||||
if object is NSNull {
|
||||
return (isTail, nil)
|
||||
} else if keyPathComponents.count > 1, let array = object as? [Any] {
|
||||
let tail = keyPathComponents.dropFirst()
|
||||
return valueFor(tail, array: array)
|
||||
} else if keyPathComponents.count > 1, let dict = object as? [String: Any] {
|
||||
let tail = keyPathComponents.dropFirst()
|
||||
return valueFor(tail, dictionary: dict)
|
||||
} else {
|
||||
return (isTail, object)
|
||||
}
|
||||
}
|
||||
|
||||
return (false, nil)
|
||||
}
|
||||
|
||||
// MARK: - Default Value
|
||||
|
||||
public extension Map {
|
||||
|
||||
/// Returns `default` value if there is nothing to parse.
|
||||
func value<T>(_ key: String, default: T.Object, using transform: T) throws -> T.Object where T: TransformType {
|
||||
if let value: T.Object = try? self.value(key, using: transform) {
|
||||
return value
|
||||
} else {
|
||||
return `default`
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns `default` value if there is nothing to parse.
|
||||
func value<T>(_ key: String, default: T) throws -> T {
|
||||
if let value: T = try? self.value(key) {
|
||||
return value
|
||||
} else {
|
||||
return `default`
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns `default` value if there is nothing to parse.
|
||||
func value<T: BaseMappable>(_ key: String, default: [T]) -> [T] {
|
||||
do {
|
||||
let value: [T] = try self.value(key)
|
||||
return value
|
||||
} catch {
|
||||
return `default`
|
||||
}
|
||||
}
|
||||
|
||||
/// Returns `default` value if there is nothing to parse.
|
||||
func value<T>(_ key: String, default: T) throws -> T where T: BaseMappable {
|
||||
if let value: T = try? self.value(key) as T {
|
||||
return value
|
||||
} else {
|
||||
return `default`
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,68 +0,0 @@
|
|||
//
|
||||
// MapError.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2016-09-26.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
public struct MapError: Error {
|
||||
public var key: String?
|
||||
public var currentValue: Any?
|
||||
public var reason: String?
|
||||
public var file: StaticString?
|
||||
public var function: StaticString?
|
||||
public var line: UInt?
|
||||
|
||||
public init(key: String?, currentValue: Any?, reason: String?, file: StaticString? = nil, function: StaticString? = nil, line: UInt? = nil) {
|
||||
self.key = key
|
||||
self.currentValue = currentValue
|
||||
self.reason = reason
|
||||
self.file = file
|
||||
self.function = function
|
||||
self.line = line
|
||||
}
|
||||
}
|
||||
|
||||
extension MapError: CustomStringConvertible {
|
||||
|
||||
private var location: String? {
|
||||
guard let file = file, let function = function, let line = line else { return nil }
|
||||
let fileName = ((String(describing: file).components(separatedBy: "/").last ?? "").components(separatedBy: ".").first ?? "")
|
||||
return "\(fileName).\(function):\(line)"
|
||||
}
|
||||
|
||||
public var description: String {
|
||||
let info: [(String, Any?)] = [
|
||||
("- reason", reason),
|
||||
("- location", location),
|
||||
("- key", key),
|
||||
("- currentValue", currentValue),
|
||||
]
|
||||
let infoString = info.map { "\($0.0): \($0.1 ?? "nil")" }.joined(separator: "\n")
|
||||
return "Got an error while mapping.\n\(infoString)"
|
||||
}
|
||||
|
||||
}
|
|
@ -1,139 +0,0 @@
|
|||
//
|
||||
// Mappable.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Scott Hoyt on 10/25/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
/// BaseMappable should not be implemented directly. Mappable or StaticMappable should be used instead
|
||||
public protocol BaseMappable {
|
||||
/// This function is where all variable mappings should occur. It is executed by Mapper during the mapping (serialization and deserialization) process.
|
||||
mutating func mapping(map: Map)
|
||||
}
|
||||
|
||||
public protocol Mappable: BaseMappable {
|
||||
/// This function can be used to validate JSON prior to mapping. Return nil to cancel mapping at this point
|
||||
init?(map: Map)
|
||||
}
|
||||
|
||||
public protocol StaticMappable: BaseMappable {
|
||||
/// This is function that can be used to:
|
||||
/// 1) provide an existing cached object to be used for mapping
|
||||
/// 2) return an object of another class (which 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 any given mapping
|
||||
static func objectForMapping(map: Map) -> BaseMappable?
|
||||
}
|
||||
|
||||
public extension Mappable {
|
||||
|
||||
/// Initializes object from a JSON String
|
||||
init?(JSONString: String, context: MapContext? = nil) {
|
||||
if let obj: Self = Mapper(context: context).map(JSONString: JSONString) {
|
||||
self = obj
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
/// Initializes object from a JSON Dictionary
|
||||
init?(JSON: [String: Any], context: MapContext? = nil) {
|
||||
if let obj: Self = Mapper(context: context).map(JSON: JSON) {
|
||||
self = obj
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public extension BaseMappable {
|
||||
|
||||
/// Returns the JSON Dictionary for the object
|
||||
func toJSON() -> [String: Any] {
|
||||
return Mapper().toJSON(self)
|
||||
}
|
||||
|
||||
/// Returns the JSON String for the object
|
||||
func toJSONString(prettyPrint: Bool = false) -> String? {
|
||||
return Mapper().toJSONString(self, prettyPrint: prettyPrint)
|
||||
}
|
||||
}
|
||||
|
||||
public extension Array where Element: BaseMappable {
|
||||
|
||||
/// Initialize Array from a JSON String
|
||||
init?(JSONString: String, context: MapContext? = nil) {
|
||||
if let obj: [Element] = Mapper(context: context).mapArray(JSONString: JSONString) {
|
||||
self = obj
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
/// Initialize Array from a JSON Array
|
||||
init(JSONArray: [[String: Any]], context: MapContext? = nil) {
|
||||
let obj: [Element] = Mapper(context: context).mapArray(JSONArray: JSONArray)
|
||||
self = obj
|
||||
}
|
||||
|
||||
/// Returns the JSON Array
|
||||
func toJSON() -> [[String: Any]] {
|
||||
return Mapper().toJSONArray(self)
|
||||
}
|
||||
|
||||
/// Returns the JSON String for the object
|
||||
func toJSONString(prettyPrint: Bool = false) -> String? {
|
||||
return Mapper().toJSONString(self, prettyPrint: prettyPrint)
|
||||
}
|
||||
}
|
||||
|
||||
public extension Set where Element: BaseMappable {
|
||||
|
||||
/// Initializes a set from a JSON String
|
||||
init?(JSONString: String, context: MapContext? = nil) {
|
||||
if let obj: Set<Element> = Mapper(context: context).mapSet(JSONString: JSONString) {
|
||||
self = obj
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
/// Initializes a set from JSON
|
||||
init?(JSONArray: [[String: Any]], context: MapContext? = nil) {
|
||||
guard let obj = Mapper(context: context).mapSet(JSONArray: JSONArray) as Set<Element>? else {
|
||||
return nil
|
||||
}
|
||||
self = obj
|
||||
}
|
||||
|
||||
/// Returns the JSON Set
|
||||
func toJSON() -> [[String: Any]] {
|
||||
return Mapper().toJSONSet(self)
|
||||
}
|
||||
|
||||
/// Returns the JSON String for the object
|
||||
func toJSONString(prettyPrint: Bool = false) -> String? {
|
||||
return Mapper().toJSONString(self, prettyPrint: prettyPrint)
|
||||
}
|
||||
}
|
|
@ -1,493 +0,0 @@
|
|||
//
|
||||
// Mapper.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-09.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
public enum MappingType {
|
||||
case fromJSON
|
||||
case toJSON
|
||||
}
|
||||
|
||||
/// The Mapper class provides methods for converting Model objects to JSON and methods for converting JSON to Model objects
|
||||
public final class Mapper<N: BaseMappable> {
|
||||
|
||||
public var context: MapContext?
|
||||
public var shouldIncludeNilValues = false /// If this is set to true, toJSON output will include null values for any variables that are not set.
|
||||
|
||||
public init(context: MapContext? = nil, shouldIncludeNilValues: Bool = false){
|
||||
self.context = context
|
||||
self.shouldIncludeNilValues = shouldIncludeNilValues
|
||||
}
|
||||
|
||||
// MARK: Mapping functions that map to an existing object toObject
|
||||
|
||||
/// Maps a JSON object to an existing Mappable object if it is a JSON dictionary, or returns the passed object as is
|
||||
public func map(JSONObject: Any?, toObject object: N) -> N {
|
||||
if let JSON = JSONObject as? [String: Any] {
|
||||
return map(JSON: JSON, toObject: object)
|
||||
}
|
||||
|
||||
return object
|
||||
}
|
||||
|
||||
/// Map a JSON string onto an existing object
|
||||
public func map(JSONString: String, toObject object: N) -> N {
|
||||
if let JSON = Mapper.parseJSONStringIntoDictionary(JSONString: JSONString) {
|
||||
return map(JSON: JSON, toObject: object)
|
||||
}
|
||||
return object
|
||||
}
|
||||
|
||||
/// Maps a JSON dictionary to an existing object that conforms to Mappable.
|
||||
/// Usefull for those pesky objects that have crappy designated initializers like NSManagedObject
|
||||
public func map(JSON: [String: Any], toObject object: N) -> N {
|
||||
var mutableObject = object
|
||||
let map = Map(mappingType: .fromJSON, JSON: JSON, toObject: true, context: context, shouldIncludeNilValues: shouldIncludeNilValues)
|
||||
mutableObject.mapping(map: map)
|
||||
return mutableObject
|
||||
}
|
||||
|
||||
//MARK: Mapping functions that create an object
|
||||
|
||||
/// Map a JSON string to an object that conforms to Mappable
|
||||
public func map(JSONString: String) -> N? {
|
||||
if let JSON = Mapper.parseJSONStringIntoDictionary(JSONString: JSONString) {
|
||||
return map(JSON: JSON)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps a JSON object to a Mappable object if it is a JSON dictionary or NSString, or returns nil.
|
||||
public func map(JSONObject: Any?) -> N? {
|
||||
if let JSON = JSONObject as? [String: Any] {
|
||||
return map(JSON: JSON)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps a JSON dictionary to an object that conforms to Mappable
|
||||
public func map(JSON: [String: Any]) -> N? {
|
||||
let map = Map(mappingType: .fromJSON, JSON: JSON, context: context, shouldIncludeNilValues: shouldIncludeNilValues)
|
||||
|
||||
if let klass = N.self as? StaticMappable.Type { // Check if object is StaticMappable
|
||||
if var object = klass.objectForMapping(map: map) as? N {
|
||||
object.mapping(map: map)
|
||||
return object
|
||||
}
|
||||
} else if let klass = N.self as? Mappable.Type { // Check if object is Mappable
|
||||
if var object = klass.init(map: map) as? N {
|
||||
object.mapping(map: map)
|
||||
return object
|
||||
}
|
||||
} else if let klass = N.self as? ImmutableMappable.Type { // Check if object is ImmutableMappable
|
||||
do {
|
||||
if var object = try klass.init(map: map) as? N {
|
||||
object.mapping(map: map)
|
||||
return object
|
||||
}
|
||||
} catch let error {
|
||||
#if DEBUG
|
||||
#if !os(Linux)
|
||||
let exception: NSException
|
||||
if let mapError = error as? MapError {
|
||||
exception = NSException(name: .init(rawValue: "MapError"), reason: mapError.description, userInfo: nil)
|
||||
} else {
|
||||
exception = NSException(name: .init(rawValue: "ImmutableMappableError"), reason: error.localizedDescription, userInfo: nil)
|
||||
}
|
||||
exception.raise()
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
} else {
|
||||
// Ensure BaseMappable is not implemented directly
|
||||
assert(false, "BaseMappable should not be implemented directly. Please implement Mappable, StaticMappable or ImmutableMappable")
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// MARK: Mapping functions for Arrays and Dictionaries
|
||||
|
||||
/// Maps a JSON array to an object that conforms to Mappable
|
||||
public func mapArray(JSONString: String) -> [N]? {
|
||||
let parsedJSON: Any? = Mapper.parseJSONString(JSONString: JSONString)
|
||||
|
||||
if let objectArray = mapArray(JSONObject: parsedJSON) {
|
||||
return objectArray
|
||||
}
|
||||
|
||||
// failed to parse JSON into array form
|
||||
// try to parse it into a dictionary and then wrap it in an array
|
||||
if let object = map(JSONObject: parsedJSON) {
|
||||
return [object]
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps a JSON object to an array of Mappable objects if it is an array of JSON dictionary, or returns nil.
|
||||
public func mapArray(JSONObject: Any?) -> [N]? {
|
||||
if let JSONArray = JSONObject as? [[String: Any]] {
|
||||
return mapArray(JSONArray: JSONArray)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps an array of JSON dictionary to an array of Mappable objects
|
||||
public func mapArray(JSONArray: [[String: Any]]) -> [N] {
|
||||
// map every element in JSON array to type N
|
||||
#if swift(>=4.1)
|
||||
let result = JSONArray.compactMap(map)
|
||||
#else
|
||||
let result = JSONArray.flatMap(map)
|
||||
#endif
|
||||
return result
|
||||
}
|
||||
|
||||
/// Maps a JSON object to a dictionary of Mappable objects if it is a JSON dictionary of dictionaries, or returns nil.
|
||||
public func mapDictionary(JSONString: String) -> [String: N]? {
|
||||
let parsedJSON: Any? = Mapper.parseJSONString(JSONString: JSONString)
|
||||
return mapDictionary(JSONObject: parsedJSON)
|
||||
}
|
||||
|
||||
/// Maps a JSON object to a dictionary of Mappable objects if it is a JSON dictionary of dictionaries, or returns nil.
|
||||
public func mapDictionary(JSONObject: Any?) -> [String: N]? {
|
||||
if let JSON = JSONObject as? [String: [String: Any]] {
|
||||
return mapDictionary(JSON: JSON)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps a JSON dictionary of dictionaries to a dictionary of Mappable objects
|
||||
public func mapDictionary(JSON: [String: [String: Any]]) -> [String: N]? {
|
||||
// map every value in dictionary to type N
|
||||
let result = JSON.filterMap(map)
|
||||
if !result.isEmpty {
|
||||
return result
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps a JSON object to a dictionary of Mappable objects if it is a JSON dictionary of dictionaries, or returns nil.
|
||||
public func mapDictionary(JSONObject: Any?, toDictionary dictionary: [String: N]) -> [String: N] {
|
||||
if let JSON = JSONObject as? [String : [String : Any]] {
|
||||
return mapDictionary(JSON: JSON, toDictionary: dictionary)
|
||||
}
|
||||
|
||||
return dictionary
|
||||
}
|
||||
|
||||
/// Maps a JSON dictionary of dictionaries to an existing dictionary of Mappable objects
|
||||
public func mapDictionary(JSON: [String: [String: Any]], toDictionary dictionary: [String: N]) -> [String: N] {
|
||||
var mutableDictionary = dictionary
|
||||
for (key, value) in JSON {
|
||||
if let object = dictionary[key] {
|
||||
_ = map(JSON: value, toObject: object)
|
||||
} else {
|
||||
mutableDictionary[key] = map(JSON: value)
|
||||
}
|
||||
}
|
||||
|
||||
return mutableDictionary
|
||||
}
|
||||
|
||||
/// Maps a JSON object to a dictionary of arrays of Mappable objects
|
||||
public func mapDictionaryOfArrays(JSONObject: Any?) -> [String: [N]]? {
|
||||
if let JSON = JSONObject as? [String: [[String: Any]]] {
|
||||
return mapDictionaryOfArrays(JSON: JSON)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
///Maps a JSON dictionary of arrays to a dictionary of arrays of Mappable objects
|
||||
public func mapDictionaryOfArrays(JSON: [String: [[String: Any]]]) -> [String: [N]]? {
|
||||
// map every value in dictionary to type N
|
||||
let result = JSON.filterMap {
|
||||
mapArray(JSONArray: $0)
|
||||
}
|
||||
|
||||
if !result.isEmpty {
|
||||
return result
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps an 2 dimentional array of JSON dictionaries to a 2 dimentional array of Mappable objects
|
||||
public func mapArrayOfArrays(JSONObject: Any?) -> [[N]]? {
|
||||
if let JSONArray = JSONObject as? [[[String: Any]]] {
|
||||
let objectArray = JSONArray.map { innerJSONArray in
|
||||
return mapArray(JSONArray: innerJSONArray)
|
||||
}
|
||||
|
||||
if !objectArray.isEmpty {
|
||||
return objectArray
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// MARK: Utility functions for converting strings to JSON objects
|
||||
|
||||
/// Convert a JSON String into a Dictionary<String, Any> using NSJSONSerialization
|
||||
public static func parseJSONStringIntoDictionary(JSONString: String) -> [String: Any]? {
|
||||
let parsedJSON: Any? = Mapper.parseJSONString(JSONString: JSONString)
|
||||
return parsedJSON as? [String: Any]
|
||||
}
|
||||
|
||||
/// Convert a JSON String into an Object using NSJSONSerialization
|
||||
public static func parseJSONString(JSONString: String) -> Any? {
|
||||
let data = JSONString.data(using: String.Encoding.utf8, allowLossyConversion: true)
|
||||
if let data = data {
|
||||
let parsedJSON: Any?
|
||||
do {
|
||||
parsedJSON = try JSONSerialization.jsonObject(with: data, options: JSONSerialization.ReadingOptions.allowFragments)
|
||||
} catch let error {
|
||||
print(error)
|
||||
parsedJSON = nil
|
||||
}
|
||||
return parsedJSON
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
extension Mapper {
|
||||
// MARK: Functions that create model from JSON file
|
||||
|
||||
/// JSON file to Mappable object
|
||||
/// - parameter JSONfile: Filename
|
||||
/// - Returns: Mappable object
|
||||
public func map(JSONfile: String) -> N? {
|
||||
if let path = Bundle.main.path(forResource: JSONfile, ofType: nil) {
|
||||
do {
|
||||
let JSONString = try String(contentsOfFile: path)
|
||||
do {
|
||||
return self.map(JSONString: JSONString)
|
||||
}
|
||||
} catch {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
/// JSON file to Mappable object array
|
||||
/// - parameter JSONfile: Filename
|
||||
/// - Returns: Mappable object array
|
||||
public func mapArray(JSONfile: String) -> [N]? {
|
||||
if let path = Bundle.main.path(forResource: JSONfile, ofType: nil) {
|
||||
do {
|
||||
let JSONString = try String(contentsOfFile: path)
|
||||
do {
|
||||
return self.mapArray(JSONString: JSONString)
|
||||
}
|
||||
} catch {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
extension Mapper {
|
||||
|
||||
// MARK: Functions that create JSON from objects
|
||||
|
||||
///Maps an object that conforms to Mappable to a JSON dictionary <String, Any>
|
||||
public func toJSON(_ object: N) -> [String: Any] {
|
||||
var mutableObject = object
|
||||
let map = Map(mappingType: .toJSON, JSON: [:], context: context, shouldIncludeNilValues: shouldIncludeNilValues)
|
||||
mutableObject.mapping(map: map)
|
||||
return map.JSON
|
||||
}
|
||||
|
||||
///Maps an array of Objects to an array of JSON dictionaries [[String: Any]]
|
||||
public func toJSONArray(_ array: [N]) -> [[String: Any]] {
|
||||
return array.map {
|
||||
// convert every element in array to JSON dictionary equivalent
|
||||
self.toJSON($0)
|
||||
}
|
||||
}
|
||||
|
||||
///Maps a dictionary of Objects that conform to Mappable to a JSON dictionary of dictionaries.
|
||||
public func toJSONDictionary(_ dictionary: [String: N]) -> [String: [String: Any]] {
|
||||
return dictionary.map { (arg: (key: String, value: N)) in
|
||||
// convert every value in dictionary to its JSON dictionary equivalent
|
||||
return (arg.key, self.toJSON(arg.value))
|
||||
}
|
||||
}
|
||||
|
||||
///Maps a dictionary of Objects that conform to Mappable to a JSON dictionary of dictionaries.
|
||||
public func toJSONDictionaryOfArrays(_ dictionary: [String: [N]]) -> [String: [[String: Any]]] {
|
||||
return dictionary.map { (arg: (key: String, value: [N])) in
|
||||
// convert every value (array) in dictionary to its JSON dictionary equivalent
|
||||
return (arg.key, self.toJSONArray(arg.value))
|
||||
}
|
||||
}
|
||||
|
||||
/// Maps an Object to a JSON string with option of pretty formatting
|
||||
public func toJSONString(_ object: N, prettyPrint: Bool = false) -> String? {
|
||||
let JSONDict = toJSON(object)
|
||||
|
||||
return Mapper.toJSONString(JSONDict as Any, prettyPrint: prettyPrint)
|
||||
}
|
||||
|
||||
/// Maps an array of Objects to a JSON string with option of pretty formatting
|
||||
public func toJSONString(_ array: [N], prettyPrint: Bool = false) -> String? {
|
||||
let JSONDict = toJSONArray(array)
|
||||
|
||||
return Mapper.toJSONString(JSONDict as Any, prettyPrint: prettyPrint)
|
||||
}
|
||||
|
||||
/// Converts an Object to a JSON string with option of pretty formatting
|
||||
public static func toJSONString(_ JSONObject: Any, prettyPrint: Bool) -> String? {
|
||||
let options: JSONSerialization.WritingOptions = prettyPrint ? .prettyPrinted : []
|
||||
if let JSON = Mapper.toJSONData(JSONObject, options: options) {
|
||||
return String(data: JSON, encoding: String.Encoding.utf8)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Converts an Object to JSON data with options
|
||||
public static func toJSONData(_ JSONObject: Any, options: JSONSerialization.WritingOptions) -> Data? {
|
||||
if JSONSerialization.isValidJSONObject(JSONObject) {
|
||||
let JSONData: Data?
|
||||
do {
|
||||
JSONData = try JSONSerialization.data(withJSONObject: JSONObject, options: options)
|
||||
} catch let error {
|
||||
print(error)
|
||||
JSONData = nil
|
||||
}
|
||||
|
||||
return JSONData
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
extension Mapper where N: Hashable {
|
||||
|
||||
/// Maps a JSON array to an object that conforms to Mappable
|
||||
public func mapSet(JSONString: String) -> Set<N>? {
|
||||
let parsedJSON: Any? = Mapper.parseJSONString(JSONString: JSONString)
|
||||
|
||||
if let objectArray = mapArray(JSONObject: parsedJSON) {
|
||||
return Set(objectArray)
|
||||
}
|
||||
|
||||
// failed to parse JSON into array form
|
||||
// try to parse it into a dictionary and then wrap it in an array
|
||||
if let object = map(JSONObject: parsedJSON) {
|
||||
return Set([object])
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps a JSON object to an Set of Mappable objects if it is an array of JSON dictionary, or returns nil.
|
||||
public func mapSet(JSONObject: Any?) -> Set<N>? {
|
||||
if let JSONArray = JSONObject as? [[String: Any]] {
|
||||
return mapSet(JSONArray: JSONArray)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
/// Maps an Set of JSON dictionary to an array of Mappable objects
|
||||
public func mapSet(JSONArray: [[String: Any]]) -> Set<N> {
|
||||
// map every element in JSON array to type N
|
||||
#if swift(>=4.1)
|
||||
return Set(JSONArray.compactMap(map))
|
||||
#else
|
||||
return Set(JSONArray.flatMap(map))
|
||||
#endif
|
||||
}
|
||||
|
||||
///Maps a Set of Objects to a Set of JSON dictionaries [[String : Any]]
|
||||
public func toJSONSet(_ set: Set<N>) -> [[String: Any]] {
|
||||
return set.map {
|
||||
// convert every element in set to JSON dictionary equivalent
|
||||
self.toJSON($0)
|
||||
}
|
||||
}
|
||||
|
||||
/// Maps a set of Objects to a JSON string with option of pretty formatting
|
||||
public func toJSONString(_ set: Set<N>, prettyPrint: Bool = false) -> String? {
|
||||
let JSONDict = toJSONSet(set)
|
||||
|
||||
return Mapper.toJSONString(JSONDict as Any, prettyPrint: prettyPrint)
|
||||
}
|
||||
}
|
||||
|
||||
extension Dictionary {
|
||||
internal func map<K, V>(_ f: (Element) throws -> (K, V)) rethrows -> [K: V] {
|
||||
var mapped = [K: V]()
|
||||
|
||||
for element in self {
|
||||
let newElement = try f(element)
|
||||
mapped[newElement.0] = newElement.1
|
||||
}
|
||||
|
||||
return mapped
|
||||
}
|
||||
|
||||
internal func map<K, V>(_ f: (Element) throws -> (K, [V])) rethrows -> [K: [V]] {
|
||||
var mapped = [K: [V]]()
|
||||
|
||||
for element in self {
|
||||
let newElement = try f(element)
|
||||
mapped[newElement.0] = newElement.1
|
||||
}
|
||||
|
||||
return mapped
|
||||
}
|
||||
|
||||
|
||||
internal func filterMap<U>(_ f: (Value) throws -> U?) rethrows -> [Key: U] {
|
||||
var mapped = [Key: U]()
|
||||
|
||||
for (key, value) in self {
|
||||
if let newValue = try f(value) {
|
||||
mapped[key] = newValue
|
||||
}
|
||||
}
|
||||
|
||||
return mapped
|
||||
}
|
||||
}
|
|
@ -1,52 +0,0 @@
|
|||
//
|
||||
// TransformOf.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 8/22/16.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
open class NSDecimalNumberTransform: TransformType {
|
||||
public typealias Object = NSDecimalNumber
|
||||
public typealias JSON = String
|
||||
|
||||
public init() {}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> NSDecimalNumber? {
|
||||
if let string = value as? String {
|
||||
return NSDecimalNumber(string: string)
|
||||
} else if let number = value as? NSNumber {
|
||||
return NSDecimalNumber(decimal: number.decimalValue)
|
||||
} else if let double = value as? Double {
|
||||
return NSDecimalNumber(floatLiteral: double)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: NSDecimalNumber?) -> String? {
|
||||
guard let value = value else { return nil }
|
||||
return value.description
|
||||
}
|
||||
}
|
|
@ -1,40 +0,0 @@
|
|||
//
|
||||
// ObjectMapper.h
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-16.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
|
||||
//! Project version number for ObjectMapper.
|
||||
FOUNDATION_EXPORT double ObjectMapperVersionNumber;
|
||||
|
||||
//! Project version string for ObjectMapper.
|
||||
FOUNDATION_EXPORT const unsigned char ObjectMapperVersionString[];
|
||||
|
||||
// In this header, you should import all the public headers of your framework using statements like #import <ObjectMapper/PublicHeader.h>
|
||||
|
||||
|
|
@ -1,398 +0,0 @@
|
|||
//
|
||||
// Operators.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-09.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
/**
|
||||
* This file defines a new operator which is used to create a mapping between an object and a JSON key value.
|
||||
* There is an overloaded operator definition for each type of object that is supported in ObjectMapper.
|
||||
* This provides a way to add custom logic to handle specific types of objects
|
||||
*/
|
||||
|
||||
/// Operator used for defining mappings to and from JSON
|
||||
infix operator <-
|
||||
|
||||
/// Operator used to define mappings to JSON
|
||||
infix operator >>>
|
||||
|
||||
// MARK:- Objects with Basic types
|
||||
|
||||
/// Object of Basic type
|
||||
public func <- <T>(left: inout T, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.basicType(&left, object: right.value())
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T>(left: T, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.basicType(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional object of basic type
|
||||
public func <- <T>(left: inout T?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalBasicType(&left, object: right.value())
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T>(left: T?, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.optionalBasicType(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional object of basic type
|
||||
public func <- <T>(left: inout T!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalBasicType(&left, object: right.value())
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Mappable Objects - <T: BaseMappable>
|
||||
|
||||
/// Object conforming to Mappable
|
||||
public func <- <T: BaseMappable>(left: inout T, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON:
|
||||
FromJSON.object(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: T, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.object(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout T?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObject(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: T?, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.optionalObject(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout T!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObject(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Dictionary of Mappable objects - Dictionary<String, T: BaseMappable>
|
||||
|
||||
/// Dictionary of Mappable objects <String, T: Mappable>
|
||||
public func <- <T: BaseMappable>(left: inout Dictionary<String, T>, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.objectDictionary(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Dictionary<String, T>, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.objectDictionary(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional Dictionary of Mappable object <String, T: Mappable>
|
||||
public func <- <T: BaseMappable>(left: inout Dictionary<String, T>?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectDictionary(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Dictionary<String, T>?, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.optionalObjectDictionary(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional Dictionary of Mappable object <String, T: Mappable>
|
||||
public func <- <T: BaseMappable>(left: inout Dictionary<String, T>!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectDictionary(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Dictionary of Mappable objects <String, T: Mappable>
|
||||
public func <- <T: BaseMappable>(left: inout Dictionary<String, [T]>, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.objectDictionaryOfArrays(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Dictionary<String, [T]>, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.objectDictionaryOfArrays(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
/// Optional Dictionary of Mappable object <String, T: Mappable>
|
||||
public func <- <T: BaseMappable>(left: inout Dictionary<String, [T]>?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectDictionaryOfArrays(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Dictionary<String, [T]>?, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.optionalObjectDictionaryOfArrays(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional Dictionary of Mappable object <String, T: Mappable>
|
||||
public func <- <T: BaseMappable>(left: inout Dictionary<String, [T]>!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectDictionaryOfArrays(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Array of Mappable objects - Array<T: BaseMappable>
|
||||
|
||||
/// Array of Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Array<T>, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.objectArray(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Array<T>, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.objectArray(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
/// Optional array of Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Array<T>?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectArray(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Array<T>?, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.optionalObjectArray(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional array of Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Array<T>!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectArray(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Array of Array of Mappable objects - Array<Array<T: BaseMappable>>
|
||||
|
||||
/// Array of Array Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Array<Array<T>>, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.twoDimensionalObjectArray(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Array<Array<T>>, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.twoDimensionalObjectArray(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional array of Mappable objects
|
||||
public func <- <T: BaseMappable>(left:inout Array<Array<T>>?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalTwoDimensionalObjectArray(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Array<Array<T>>?, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.optionalTwoDimensionalObjectArray(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional array of Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Array<Array<T>>!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalTwoDimensionalObjectArray(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Set of Mappable objects - Set<T: BaseMappable>
|
||||
|
||||
/// Set of Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Set<T>, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.objectSet(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Set<T>, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.objectSet(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional Set of Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Set<T>?, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectSet(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <T: BaseMappable>(left: Set<T>?, right: Map) {
|
||||
if right.mappingType == .toJSON {
|
||||
ToJSON.optionalObjectSet(left, map: right)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional Set of Mappable objects
|
||||
public func <- <T: BaseMappable>(left: inout Set<T>!, right: Map) {
|
||||
switch right.mappingType {
|
||||
case .fromJSON where right.isKeyPresent:
|
||||
FromJSON.optionalObjectSet(&left, map: right)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
|
@ -1,177 +0,0 @@
|
|||
//
|
||||
// ToJSON.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-13.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
private func setValue(_ value: Any, map: Map) {
|
||||
setValue(value, key: map.currentKey!, checkForNestedKeys: map.keyIsNested, delimiter: map.nestedKeyDelimiter, dictionary: &map.JSON)
|
||||
}
|
||||
|
||||
private func setValue(_ value: Any, key: String, checkForNestedKeys: Bool, delimiter: String, dictionary: inout [String : Any]) {
|
||||
if checkForNestedKeys {
|
||||
let keyComponents = ArraySlice(key.components(separatedBy: delimiter).filter { !$0.isEmpty }.map { $0 })
|
||||
setValue(value, forKeyPathComponents: keyComponents, dictionary: &dictionary)
|
||||
} else {
|
||||
dictionary[key] = value
|
||||
}
|
||||
}
|
||||
|
||||
private func setValue(_ value: Any, forKeyPathComponents components: ArraySlice<String>, dictionary: inout [String : Any]) {
|
||||
guard let head = components.first else {
|
||||
return
|
||||
}
|
||||
|
||||
let headAsString = String(head)
|
||||
if components.count == 1 {
|
||||
dictionary[headAsString] = value
|
||||
} else {
|
||||
var child = dictionary[headAsString] as? [String : Any] ?? [:]
|
||||
|
||||
let tail = components.dropFirst()
|
||||
setValue(value, forKeyPathComponents: tail, dictionary: &child)
|
||||
|
||||
dictionary[headAsString] = child
|
||||
}
|
||||
}
|
||||
|
||||
internal final class ToJSON {
|
||||
|
||||
class func basicType<N>(_ field: N, map: Map) {
|
||||
if let x = field as Any? , false
|
||||
|| x is NSNumber // Basic types
|
||||
|| x is Bool
|
||||
|| x is Int
|
||||
|| x is Double
|
||||
|| x is Float
|
||||
|| x is String
|
||||
|| x is NSNull
|
||||
|| x is Array<NSNumber> // Arrays
|
||||
|| x is Array<Bool>
|
||||
|| x is Array<Int>
|
||||
|| x is Array<Double>
|
||||
|| x is Array<Float>
|
||||
|| x is Array<String>
|
||||
|| x is Array<Any>
|
||||
|| x is Array<Dictionary<String, Any>>
|
||||
|| x is Dictionary<String, NSNumber> // Dictionaries
|
||||
|| x is Dictionary<String, Bool>
|
||||
|| x is Dictionary<String, Int>
|
||||
|| x is Dictionary<String, Double>
|
||||
|| x is Dictionary<String, Float>
|
||||
|| x is Dictionary<String, String>
|
||||
|| x is Dictionary<String, Any>
|
||||
{
|
||||
setValue(x, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
class func optionalBasicType<N>(_ field: N?, map: Map) {
|
||||
if let field = field {
|
||||
basicType(field, map: map)
|
||||
} else if map.shouldIncludeNilValues {
|
||||
basicType(NSNull(), map: map) //If BasicType is nil, emit NSNull into the JSON output
|
||||
}
|
||||
}
|
||||
|
||||
class func object<N: BaseMappable>(_ field: N, map: Map) {
|
||||
if let result = Mapper(context: map.context, shouldIncludeNilValues: map.shouldIncludeNilValues).toJSON(field) as Any? {
|
||||
setValue(result, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
class func optionalObject<N: BaseMappable>(_ field: N?, map: Map) {
|
||||
if let field = field {
|
||||
object(field, map: map)
|
||||
} else if map.shouldIncludeNilValues {
|
||||
basicType(NSNull(), map: map) //If field is nil, emit NSNull into the JSON output
|
||||
}
|
||||
}
|
||||
|
||||
class func objectArray<N: BaseMappable>(_ field: Array<N>, map: Map) {
|
||||
let JSONObjects = Mapper(context: map.context, shouldIncludeNilValues: map.shouldIncludeNilValues).toJSONArray(field)
|
||||
|
||||
setValue(JSONObjects, map: map)
|
||||
}
|
||||
|
||||
class func optionalObjectArray<N: BaseMappable>(_ field: Array<N>?, map: Map) {
|
||||
if let field = field {
|
||||
objectArray(field, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
class func twoDimensionalObjectArray<N: BaseMappable>(_ field: Array<Array<N>>, map: Map) {
|
||||
var array = [[[String: Any]]]()
|
||||
for innerArray in field {
|
||||
let JSONObjects = Mapper(context: map.context, shouldIncludeNilValues: map.shouldIncludeNilValues).toJSONArray(innerArray)
|
||||
array.append(JSONObjects)
|
||||
}
|
||||
setValue(array, map: map)
|
||||
}
|
||||
|
||||
class func optionalTwoDimensionalObjectArray<N: BaseMappable>(_ field: Array<Array<N>>?, map: Map) {
|
||||
if let field = field {
|
||||
twoDimensionalObjectArray(field, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
class func objectSet<N: BaseMappable>(_ field: Set<N>, map: Map) {
|
||||
let JSONObjects = Mapper(context: map.context, shouldIncludeNilValues: map.shouldIncludeNilValues).toJSONSet(field)
|
||||
|
||||
setValue(JSONObjects, map: map)
|
||||
}
|
||||
|
||||
class func optionalObjectSet<N: BaseMappable>(_ field: Set<N>?, map: Map) {
|
||||
if let field = field {
|
||||
objectSet(field, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
class func objectDictionary<N: BaseMappable>(_ field: Dictionary<String, N>, map: Map) {
|
||||
let JSONObjects = Mapper(context: map.context, shouldIncludeNilValues: map.shouldIncludeNilValues).toJSONDictionary(field)
|
||||
|
||||
setValue(JSONObjects, map: map)
|
||||
}
|
||||
|
||||
class func optionalObjectDictionary<N: BaseMappable>(_ field: Dictionary<String, N>?, map: Map) {
|
||||
if let field = field {
|
||||
objectDictionary(field, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
class func objectDictionaryOfArrays<N: BaseMappable>(_ field: Dictionary<String, [N]>, map: Map) {
|
||||
let JSONObjects = Mapper(context: map.context, shouldIncludeNilValues: map.shouldIncludeNilValues).toJSONDictionaryOfArrays(field)
|
||||
|
||||
setValue(JSONObjects, map: map)
|
||||
}
|
||||
|
||||
class func optionalObjectDictionaryOfArrays<N: BaseMappable>(_ field: Dictionary<String, [N]>?, map: Map) {
|
||||
if let field = field {
|
||||
objectDictionaryOfArrays(field, map: map)
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,48 +0,0 @@
|
|||
//
|
||||
// TransformOf.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Syo Ikeda on 1/23/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
open class TransformOf<ObjectType, JSONType>: TransformType {
|
||||
public typealias Object = ObjectType
|
||||
public typealias JSON = JSONType
|
||||
|
||||
private let fromJSON: (JSONType?) -> ObjectType?
|
||||
private let toJSON: (ObjectType?) -> JSONType?
|
||||
|
||||
public init(fromJSON: @escaping(JSONType?) -> ObjectType?, toJSON: @escaping(ObjectType?) -> JSONType?) {
|
||||
self.fromJSON = fromJSON
|
||||
self.toJSON = toJSON
|
||||
}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> ObjectType? {
|
||||
return fromJSON(value as? JSONType)
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: ObjectType?) -> JSONType? {
|
||||
return toJSON(value)
|
||||
}
|
||||
}
|
|
@ -1,709 +0,0 @@
|
|||
//
|
||||
// TransformOperators.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2016-09-26.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
// MARK:- Transforms
|
||||
|
||||
/// Object of Basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout Transform.Object, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let value = transform.transformFromJSON(map.currentValue)
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Transform.Object, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let value: Transform.JSON? = transform.transformToJSON(left)
|
||||
ToJSON.optionalBasicType(value, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional object of basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout Transform.Object?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let value = transform.transformFromJSON(map.currentValue)
|
||||
FromJSON.optionalBasicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Transform.Object?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let value: Transform.JSON? = transform.transformToJSON(left)
|
||||
ToJSON.optionalBasicType(value, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional object of basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout Transform.Object!, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let value = transform.transformFromJSON(map.currentValue)
|
||||
FromJSON.optionalBasicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Array of Basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout [Transform.Object], right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let values = fromJSONArrayWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.basicType(&left, object: values)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: [Transform.Object], right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON{
|
||||
let values = toJSONArrayWithTransform(left, transform: transform)
|
||||
ToJSON.optionalBasicType(values, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional array of Basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout [Transform.Object]?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let values = fromJSONArrayWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.optionalBasicType(&left, object: values)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: [Transform.Object]?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let values = toJSONArrayWithTransform(left, transform: transform)
|
||||
ToJSON.optionalBasicType(values, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional array of Basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout [Transform.Object]!, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let values = fromJSONArrayWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.optionalBasicType(&left, object: values)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Dictionary of Basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout [String: Transform.Object], right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let values = fromJSONDictionaryWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.basicType(&left, object: values)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: [String: Transform.Object], right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == . toJSON {
|
||||
let values = toJSONDictionaryWithTransform(left, transform: transform)
|
||||
ToJSON.optionalBasicType(values, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional dictionary of Basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout [String: Transform.Object]?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let values = fromJSONDictionaryWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.optionalBasicType(&left, object: values)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: [String: Transform.Object]?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let values = toJSONDictionaryWithTransform(left, transform: transform)
|
||||
ToJSON.optionalBasicType(values, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional dictionary of Basic type with Transform
|
||||
public func <- <Transform: TransformType>(left: inout [String: Transform.Object]!, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let values = fromJSONDictionaryWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.optionalBasicType(&left, object: values)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Transforms of Mappable Objects - <T: BaseMappable>
|
||||
|
||||
/// Object conforming to Mappable that have transforms
|
||||
public func <- <Transform: TransformType>(left: inout Transform.Object, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let value: Transform.Object? = transform.transformFromJSON(map.currentValue)
|
||||
FromJSON.basicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Transform.Object, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let value: Transform.JSON? = transform.transformToJSON(left)
|
||||
ToJSON.optionalBasicType(value, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional Mappable objects that have transforms
|
||||
public func <- <Transform: TransformType>(left: inout Transform.Object?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let value: Transform.Object? = transform.transformFromJSON(map.currentValue)
|
||||
FromJSON.optionalBasicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Transform.Object?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON{
|
||||
let value: Transform.JSON? = transform.transformToJSON(left)
|
||||
ToJSON.optionalBasicType(value, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped optional Mappable objects that have transforms
|
||||
public func <- <Transform: TransformType>(left: inout Transform.Object!, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let value: Transform.Object? = transform.transformFromJSON(map.currentValue)
|
||||
FromJSON.optionalBasicType(&left, object: value)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
// MARK:- Dictionary of Mappable objects with a transform - Dictionary<String, T: BaseMappable>
|
||||
|
||||
/// Dictionary of Mappable objects <String, T: Mappable> with a transform
|
||||
public func <- <Transform: TransformType>(left: inout Dictionary<String, Transform.Object>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .fromJSON && map.isKeyPresent,
|
||||
let object = map.currentValue as? [String: Any] {
|
||||
let value = fromJSONDictionaryWithTransform(object as Any?, transform: transform) ?? left
|
||||
FromJSON.basicType(&left, object: value)
|
||||
} else if map.mappingType == .toJSON {
|
||||
left >>> right
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Dictionary<String, Transform.Object>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let value = toJSONDictionaryWithTransform(left, transform: transform)
|
||||
ToJSON.basicType(value, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional Dictionary of Mappable object <String, T: Mappable> with a transform
|
||||
public func <- <Transform: TransformType>(left: inout Dictionary<String, Transform.Object>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .fromJSON && map.isKeyPresent, let object = map.currentValue as? [String : Any]{
|
||||
let value = fromJSONDictionaryWithTransform(object as Any?, transform: transform) ?? left
|
||||
FromJSON.optionalBasicType(&left, object: value)
|
||||
} else if map.mappingType == .toJSON {
|
||||
left >>> right
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Dictionary<String, Transform.Object>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let value = toJSONDictionaryWithTransform(left, transform: transform)
|
||||
ToJSON.optionalBasicType(value, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional Dictionary of Mappable object <String, T: Mappable> with a transform
|
||||
public func <- <Transform: TransformType>(left: inout Dictionary<String, Transform.Object>!, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .fromJSON && map.isKeyPresent, let dictionary = map.currentValue as? [String : Any]{
|
||||
let transformedDictionary = fromJSONDictionaryWithTransform(dictionary as Any?, transform: transform) ?? left
|
||||
FromJSON.optionalBasicType(&left, object: transformedDictionary)
|
||||
} else if map.mappingType == .toJSON {
|
||||
left >>> right
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/// Dictionary of Mappable objects <String, T: Mappable> with a transform
|
||||
public func <- <Transform: TransformType>(left: inout Dictionary<String, [Transform.Object]>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
|
||||
if let dictionary = map.currentValue as? [String : [Any]], map.mappingType == .fromJSON && map.isKeyPresent {
|
||||
let transformedDictionary = dictionary.map { (arg: (key: String, values: [Any])) -> (String, [Transform.Object]) in
|
||||
let (key, values) = arg
|
||||
if let jsonArray = fromJSONArrayWithTransform(values, transform: transform) {
|
||||
return (key, jsonArray)
|
||||
}
|
||||
if let leftValue = left[key] {
|
||||
return (key, leftValue)
|
||||
}
|
||||
return (key, [])
|
||||
}
|
||||
|
||||
FromJSON.basicType(&left, object: transformedDictionary)
|
||||
} else if map.mappingType == .toJSON {
|
||||
left >>> right
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Dictionary<String, [Transform.Object]>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
|
||||
if map.mappingType == .toJSON {
|
||||
|
||||
let transformedDictionary = left.map { (arg: (key: String, value: [Transform.Object])) in
|
||||
return (arg.key, toJSONArrayWithTransform(arg.value, transform: transform) ?? [])
|
||||
}
|
||||
|
||||
ToJSON.basicType(transformedDictionary, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional Dictionary of Mappable object <String, T: Mappable> with a transform
|
||||
public func <- <Transform: TransformType>(left: inout Dictionary<String, [Transform.Object]>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
|
||||
if let dictionary = map.currentValue as? [String : [Any]], map.mappingType == .fromJSON && map.isKeyPresent {
|
||||
|
||||
let transformedDictionary = dictionary.map { (arg: (key: String, values: [Any])) -> (String, [Transform.Object]) in
|
||||
let (key, values) = arg
|
||||
if let jsonArray = fromJSONArrayWithTransform(values, transform: transform) {
|
||||
return (key, jsonArray)
|
||||
}
|
||||
if let leftValue = left?[key] {
|
||||
return (key, leftValue)
|
||||
}
|
||||
return (key, [])
|
||||
}
|
||||
|
||||
FromJSON.optionalBasicType(&left, object: transformedDictionary)
|
||||
} else if map.mappingType == .toJSON {
|
||||
left >>> right
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Dictionary<String, [Transform.Object]>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
|
||||
if map.mappingType == .toJSON {
|
||||
let transformedDictionary = left?.map { (arg: (key: String, values: [Transform.Object])) in
|
||||
return (arg.key, toJSONArrayWithTransform(arg.values, transform: transform) ?? [])
|
||||
}
|
||||
|
||||
ToJSON.optionalBasicType(transformedDictionary, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional Dictionary of Mappable object <String, T: Mappable> with a transform
|
||||
public func <- <Transform: TransformType>(left: inout Dictionary<String, [Transform.Object]>!, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
|
||||
if let dictionary = map.currentValue as? [String : [Any]], map.mappingType == .fromJSON && map.isKeyPresent {
|
||||
let transformedDictionary = dictionary.map { (arg: (key: String, values: [Any])) -> (String, [Transform.Object]) in
|
||||
let (key, values) = arg
|
||||
if let jsonArray = fromJSONArrayWithTransform(values, transform: transform) {
|
||||
return (key, jsonArray)
|
||||
}
|
||||
if let leftValue = left?[key] {
|
||||
return (key, leftValue)
|
||||
}
|
||||
return (key, [])
|
||||
}
|
||||
FromJSON.optionalBasicType(&left, object: transformedDictionary)
|
||||
} else if map.mappingType == .toJSON {
|
||||
left >>> right
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Array of Mappable objects with transforms - Array<T: BaseMappable>
|
||||
|
||||
/// Array of Mappable objects
|
||||
public func <- <Transform: TransformType>(left: inout Array<Transform.Object>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
if let transformedValues = fromJSONArrayWithTransform(map.currentValue, transform: transform) {
|
||||
FromJSON.basicType(&left, object: transformedValues)
|
||||
}
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Array<Transform.Object>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let transformedValues = toJSONArrayWithTransform(left, transform: transform)
|
||||
ToJSON.optionalBasicType(transformedValues, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional array of Mappable objects
|
||||
public func <- <Transform: TransformType>(left: inout Array<Transform.Object>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let transformedValues = fromJSONArrayWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.optionalBasicType(&left, object: transformedValues)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Array<Transform.Object>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let transformedValues = toJSONArrayWithTransform(left, transform: transform)
|
||||
ToJSON.optionalBasicType(transformedValues, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional array of Mappable objects
|
||||
public func <- <Transform: TransformType>(left: inout Array<Transform.Object>!, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
let transformedValues = fromJSONArrayWithTransform(map.currentValue, transform: transform)
|
||||
FromJSON.optionalBasicType(&left, object: transformedValues)
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Array of Array of objects - Array<Array<T>>> with transforms
|
||||
|
||||
/// Array of Array of objects with transform
|
||||
public func <- <Transform: TransformType>(left: inout [[Transform.Object]], right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
guard let original2DArray = map.currentValue as? [[Any]] else { break }
|
||||
#if swift(>=4.1)
|
||||
let transformed2DArray = original2DArray.compactMap { values in
|
||||
fromJSONArrayWithTransform(values as Any?, transform: transform)
|
||||
}
|
||||
#else
|
||||
let transformed2DArray = original2DArray.flatMap { values in
|
||||
fromJSONArrayWithTransform(values as Any?, transform: transform)
|
||||
}
|
||||
#endif
|
||||
FromJSON.basicType(&left, object: transformed2DArray)
|
||||
default:
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: [[Transform.Object]], right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON{
|
||||
#if swift(>=4.1)
|
||||
let transformed2DArray = left.compactMap { values in
|
||||
toJSONArrayWithTransform(values, transform: transform)
|
||||
}
|
||||
#else
|
||||
let transformed2DArray = left.flatMap { values in
|
||||
toJSONArrayWithTransform(values, transform: transform)
|
||||
}
|
||||
#endif
|
||||
ToJSON.basicType(transformed2DArray, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
/// Optional array of array of objects with transform
|
||||
public func <- <Transform: TransformType>(left: inout [[Transform.Object]]?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
guard let original2DArray = map.currentValue as? [[Any]] else { break }
|
||||
#if swift(>=4.1)
|
||||
let transformed2DArray = original2DArray.compactMap { values in
|
||||
fromJSONArrayWithTransform(values as Any?, transform: transform)
|
||||
}
|
||||
#else
|
||||
let transformed2DArray = original2DArray.flatMap { values in
|
||||
fromJSONArrayWithTransform(values as Any?, transform: transform)
|
||||
}
|
||||
#endif
|
||||
FromJSON.optionalBasicType(&left, object: transformed2DArray)
|
||||
default:
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: [[Transform.Object]]?, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
#if swift(>=4.1)
|
||||
let transformed2DArray = left?.compactMap { values in
|
||||
toJSONArrayWithTransform(values, transform: transform)
|
||||
}
|
||||
#else
|
||||
let transformed2DArray = left?.flatMap { values in
|
||||
toJSONArrayWithTransform(values, transform: transform)
|
||||
}
|
||||
#endif
|
||||
ToJSON.optionalBasicType(transformed2DArray, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional array of array of objects with transform
|
||||
public func <- <Transform: TransformType>(left: inout [[Transform.Object]]!, right: (Map, Transform)) {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
guard let original2DArray = map.currentValue as? [[Any]] else { break }
|
||||
#if swift(>=4.1)
|
||||
let transformed2DArray = original2DArray.compactMap { values in
|
||||
fromJSONArrayWithTransform(values as Any?, transform: transform)
|
||||
}
|
||||
#else
|
||||
let transformed2DArray = original2DArray.flatMap { values in
|
||||
fromJSONArrayWithTransform(values as Any?, transform: transform)
|
||||
}
|
||||
#endif
|
||||
FromJSON.optionalBasicType(&left, object: transformed2DArray)
|
||||
default:
|
||||
break
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// MARK:- Set of Mappable objects with a transform - Set<T: BaseMappable>
|
||||
|
||||
/// Set of Mappable objects with transform
|
||||
public func <- <Transform: TransformType>(left: inout Set<Transform.Object>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
if let transformedValues = fromJSONArrayWithTransform(map.currentValue, transform: transform) {
|
||||
FromJSON.basicType(&left, object: Set(transformedValues))
|
||||
}
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Set<Transform.Object>, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
let transformedValues = toJSONArrayWithTransform(Array(left), transform: transform)
|
||||
ToJSON.optionalBasicType(transformedValues, map: map)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// Optional Set of Mappable objects with transform
|
||||
public func <- <Transform: TransformType>(left: inout Set<Transform.Object>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
if let transformedValues = fromJSONArrayWithTransform(map.currentValue, transform: transform) {
|
||||
FromJSON.basicType(&left, object: Set(transformedValues))
|
||||
}
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
|
||||
public func >>> <Transform: TransformType>(left: Set<Transform.Object>?, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
if map.mappingType == .toJSON {
|
||||
if let values = left {
|
||||
let transformedValues = toJSONArrayWithTransform(Array(values), transform: transform)
|
||||
ToJSON.optionalBasicType(transformedValues, map: map)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Code targeting the Swift 4.1 compiler and below.
|
||||
#if !(swift(>=4.1.50) || (swift(>=3.4) && !swift(>=4.0)))
|
||||
/// Implicitly unwrapped Optional set of Mappable objects with transform
|
||||
public func <- <Transform: TransformType>(left: inout Set<Transform.Object>!, right: (Map, Transform)) where Transform.Object: BaseMappable {
|
||||
let (map, transform) = right
|
||||
switch map.mappingType {
|
||||
case .fromJSON where map.isKeyPresent:
|
||||
if let transformedValues = fromJSONArrayWithTransform(map.currentValue, transform: transform) {
|
||||
FromJSON.basicType(&left, object: Set(transformedValues))
|
||||
}
|
||||
case .toJSON:
|
||||
left >>> right
|
||||
default: ()
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
private func fromJSONArrayWithTransform<Transform: TransformType>(_ input: Any?, transform: Transform) -> [Transform.Object]? {
|
||||
if let values = input as? [Any] {
|
||||
#if swift(>=4.1)
|
||||
return values.compactMap { value in
|
||||
return transform.transformFromJSON(value)
|
||||
}
|
||||
#else
|
||||
return values.flatMap { value in
|
||||
return transform.transformFromJSON(value)
|
||||
}
|
||||
#endif
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
private func fromJSONDictionaryWithTransform<Transform: TransformType>(_ input: Any?, transform: Transform) -> [String: Transform.Object]? {
|
||||
if let values = input as? [String: Any] {
|
||||
return values.filterMap { value in
|
||||
return transform.transformFromJSON(value)
|
||||
}
|
||||
} else {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
private func toJSONArrayWithTransform<Transform: TransformType>(_ input: [Transform.Object]?, transform: Transform) -> [Transform.JSON]? {
|
||||
#if swift(>=4.1)
|
||||
return input?.compactMap { value in
|
||||
return transform.transformToJSON(value)
|
||||
}
|
||||
#else
|
||||
return input?.flatMap { value in
|
||||
return transform.transformToJSON(value)
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
private func toJSONDictionaryWithTransform<Transform: TransformType>(_ input: [String: Transform.Object]?, transform: Transform) -> [String: Transform.JSON]? {
|
||||
return input?.filterMap { value in
|
||||
return transform.transformToJSON(value)
|
||||
}
|
||||
}
|
|
@ -1,35 +0,0 @@
|
|||
//
|
||||
// TransformType.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Syo Ikeda on 2/4/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
public protocol TransformType {
|
||||
associatedtype Object
|
||||
associatedtype JSON
|
||||
|
||||
func transformFromJSON(_ value: Any?) -> Object?
|
||||
func transformToJSON(_ value: Object?) -> JSON?
|
||||
}
|
|
@ -1,67 +0,0 @@
|
|||
//
|
||||
// URLTransform.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-27.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
|
||||
open class URLTransform: TransformType {
|
||||
public typealias Object = URL
|
||||
public typealias JSON = String
|
||||
private let shouldEncodeURLString: Bool
|
||||
private let allowedCharacterSet: CharacterSet
|
||||
|
||||
/**
|
||||
Initializes the URLTransform with an option to encode URL strings before converting them to an NSURL
|
||||
- parameter shouldEncodeUrlString: when true (the default) the string is encoded before passing
|
||||
to `NSURL(string:)`
|
||||
- returns: an initialized transformer
|
||||
*/
|
||||
public init(shouldEncodeURLString: Bool = false, allowedCharacterSet: CharacterSet = .urlQueryAllowed) {
|
||||
self.shouldEncodeURLString = shouldEncodeURLString
|
||||
self.allowedCharacterSet = allowedCharacterSet
|
||||
}
|
||||
|
||||
open func transformFromJSON(_ value: Any?) -> URL? {
|
||||
guard let URLString = value as? String else { return nil }
|
||||
|
||||
if !shouldEncodeURLString {
|
||||
return URL(string: URLString)
|
||||
}
|
||||
|
||||
guard let escapedURLString = URLString.addingPercentEncoding(withAllowedCharacters: allowedCharacterSet) else {
|
||||
return nil
|
||||
}
|
||||
return URL(string: escapedURLString)
|
||||
}
|
||||
|
||||
open func transformToJSON(_ value: URL?) -> String? {
|
||||
if let URL = value {
|
||||
return URL.absoluteString
|
||||
}
|
||||
return nil
|
||||
}
|
||||
}
|
|
@ -1,24 +0,0 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>en</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>BNDL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>1.0</string>
|
||||
<key>CFBundleSignature</key>
|
||||
<string>????</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
</dict>
|
||||
</plist>
|
|
@ -1,333 +0,0 @@
|
|||
//
|
||||
// BasicTypes.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-02-17.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import ObjectMapper
|
||||
|
||||
class BasicTypes: Mappable {
|
||||
var bool: Bool = true
|
||||
var boolOptional: Bool?
|
||||
var boolImplicityUnwrapped: Bool!
|
||||
|
||||
var int: Int = 0
|
||||
var intOptional: Int?
|
||||
var intImplicityUnwrapped: Int!
|
||||
|
||||
var int8: Int8 = 0
|
||||
var int8Optional: Int8?
|
||||
var int8ImplicityUnwrapped: Int8!
|
||||
|
||||
var int16: Int16 = 0
|
||||
var int16Optional: Int16?
|
||||
var int16ImplicityUnwrapped: Int16!
|
||||
|
||||
var int32: Int32 = 0
|
||||
var int32Optional: Int32?
|
||||
var int32ImplicityUnwrapped: Int32!
|
||||
|
||||
var int64: Int64 = 0
|
||||
var int64Optional: Int64?
|
||||
var int64ImplicityUnwrapped: Int64!
|
||||
|
||||
var uint: UInt = 0
|
||||
var uintOptional: UInt?
|
||||
var uintImplicityUnwrapped: UInt!
|
||||
|
||||
var uint8: UInt8 = 0
|
||||
var uint8Optional: UInt8?
|
||||
var uint8ImplicityUnwrapped: UInt8!
|
||||
|
||||
var uint16: UInt16 = 0
|
||||
var uint16Optional: UInt16?
|
||||
var uint16ImplicityUnwrapped: UInt16!
|
||||
|
||||
var uint32: UInt32 = 0
|
||||
var uint32Optional: UInt32?
|
||||
var uint32ImplicityUnwrapped: UInt32!
|
||||
|
||||
var uint64: UInt64 = 0
|
||||
var uint64Optional: UInt64?
|
||||
var uint64ImplicityUnwrapped: UInt64!
|
||||
|
||||
var double: Double = 1.1
|
||||
var doubleOptional: Double?
|
||||
var doubleImplicityUnwrapped: Double!
|
||||
var float: Float = 1.11
|
||||
var floatOptional: Float?
|
||||
var floatImplicityUnwrapped: Float!
|
||||
var string: String = ""
|
||||
var stringOptional: String?
|
||||
var stringImplicityUnwrapped: String!
|
||||
var anyObject: Any = true
|
||||
var anyObjectOptional: Any?
|
||||
var anyObjectImplicitlyUnwrapped: Any!
|
||||
|
||||
var arrayBool: Array<Bool> = []
|
||||
var arrayBoolOptional: Array<Bool>?
|
||||
var arrayBoolImplicityUnwrapped: Array<Bool>!
|
||||
var arrayInt: Array<Int> = []
|
||||
var arrayIntOptional: Array<Int>?
|
||||
var arrayIntImplicityUnwrapped: Array<Int>!
|
||||
var arrayDouble: Array<Double> = []
|
||||
var arrayDoubleOptional: Array<Double>?
|
||||
var arrayDoubleImplicityUnwrapped: Array<Double>!
|
||||
var arrayFloat: Array<Float> = []
|
||||
var arrayFloatOptional: Array<Float>?
|
||||
var arrayFloatImplicityUnwrapped: Array<Float>!
|
||||
var arrayString: Array<String> = []
|
||||
var arrayStringOptional: Array<String>?
|
||||
var arrayStringImplicityUnwrapped: Array<String>!
|
||||
var arrayAnyObject: Array<Any> = []
|
||||
var arrayAnyObjectOptional: Array<Any>?
|
||||
var arrayAnyObjectImplicitlyUnwrapped: Array<Any>!
|
||||
|
||||
var dictBool: Dictionary<String,Bool> = [:]
|
||||
var dictBoolOptional: Dictionary<String, Bool>?
|
||||
var dictBoolImplicityUnwrapped: Dictionary<String, Bool>!
|
||||
var dictInt: Dictionary<String,Int> = [:]
|
||||
var dictIntOptional: Dictionary<String,Int>?
|
||||
var dictIntImplicityUnwrapped: Dictionary<String,Int>!
|
||||
var dictDouble: Dictionary<String,Double> = [:]
|
||||
var dictDoubleOptional: Dictionary<String,Double>?
|
||||
var dictDoubleImplicityUnwrapped: Dictionary<String,Double>!
|
||||
var dictFloat: Dictionary<String,Float> = [:]
|
||||
var dictFloatOptional: Dictionary<String,Float>?
|
||||
var dictFloatImplicityUnwrapped: Dictionary<String,Float>!
|
||||
var dictString: Dictionary<String,String> = [:]
|
||||
var dictStringOptional: Dictionary<String,String>?
|
||||
var dictStringImplicityUnwrapped: Dictionary<String,String>!
|
||||
var dictAnyObject: Dictionary<String, Any> = [:]
|
||||
var dictAnyObjectOptional: Dictionary<String, Any>?
|
||||
var dictAnyObjectImplicitlyUnwrapped: Dictionary<String, Any>!
|
||||
|
||||
enum EnumInt: Int {
|
||||
case Default
|
||||
case Another
|
||||
}
|
||||
var enumInt: EnumInt = .Default
|
||||
var enumIntOptional: EnumInt?
|
||||
var enumIntImplicitlyUnwrapped: EnumInt!
|
||||
|
||||
enum EnumDouble: Double {
|
||||
case Default
|
||||
case Another
|
||||
}
|
||||
var enumDouble: EnumDouble = .Default
|
||||
var enumDoubleOptional: EnumDouble?
|
||||
var enumDoubleImplicitlyUnwrapped: EnumDouble!
|
||||
|
||||
enum EnumFloat: Float {
|
||||
case Default
|
||||
case Another
|
||||
}
|
||||
var enumFloat: EnumFloat = .Default
|
||||
var enumFloatOptional: EnumFloat?
|
||||
var enumFloatImplicitlyUnwrapped: EnumFloat!
|
||||
|
||||
enum EnumString: String {
|
||||
case Default = "Default"
|
||||
case Another = "Another"
|
||||
}
|
||||
var enumString: EnumString = .Default
|
||||
var enumStringOptional: EnumString?
|
||||
var enumStringImplicitlyUnwrapped: EnumString!
|
||||
|
||||
var arrayEnumInt: [EnumInt] = []
|
||||
var arrayEnumIntOptional: [EnumInt]?
|
||||
var arrayEnumIntImplicitlyUnwrapped: [EnumInt]!
|
||||
|
||||
var dictEnumInt: [String: EnumInt] = [:]
|
||||
var dictEnumIntOptional: [String: EnumInt]?
|
||||
var dictEnumIntImplicitlyUnwrapped: [String: EnumInt]!
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
bool <- map["bool"]
|
||||
boolOptional <- map["boolOpt"]
|
||||
boolImplicityUnwrapped <- map["boolImp"]
|
||||
|
||||
int <- map["int"]
|
||||
intOptional <- map["intOpt"]
|
||||
intImplicityUnwrapped <- map["intImp"]
|
||||
|
||||
int8 <- map["int8"]
|
||||
int8Optional <- map["int8Opt"]
|
||||
int8ImplicityUnwrapped <- map["int8Imp"]
|
||||
|
||||
int16 <- map["int16"]
|
||||
int16Optional <- map["int16Opt"]
|
||||
int16ImplicityUnwrapped <- map["int16Imp"]
|
||||
|
||||
int32 <- map["int32"]
|
||||
int32Optional <- map["int32Opt"]
|
||||
int32ImplicityUnwrapped <- map["int32Imp"]
|
||||
|
||||
int64 <- map["int64"]
|
||||
int64Optional <- map["int64Opt"]
|
||||
int64ImplicityUnwrapped <- map["int64Imp"]
|
||||
|
||||
uint <- map["uint"]
|
||||
uintOptional <- map["uintOpt"]
|
||||
uintImplicityUnwrapped <- map["uintImp"]
|
||||
|
||||
uint8 <- map["uint8"]
|
||||
uint8Optional <- map["uint8Opt"]
|
||||
uint8ImplicityUnwrapped <- map["uint8Imp"]
|
||||
|
||||
uint16 <- map["uint16"]
|
||||
uint16Optional <- map["uint16Opt"]
|
||||
uint16ImplicityUnwrapped <- map["uint16Imp"]
|
||||
|
||||
uint32 <- map["uint32"]
|
||||
uint32Optional <- map["uint32Opt"]
|
||||
uint32ImplicityUnwrapped <- map["uint32Imp"]
|
||||
|
||||
uint64 <- map["uint64"]
|
||||
uint64Optional <- map["uint64Opt"]
|
||||
uint64ImplicityUnwrapped <- map["uint64Imp"]
|
||||
|
||||
double <- map["double"]
|
||||
doubleOptional <- map["doubleOpt"]
|
||||
doubleImplicityUnwrapped <- map["doubleImp"]
|
||||
float <- map["float"]
|
||||
floatOptional <- map["floatOpt"]
|
||||
floatImplicityUnwrapped <- map["floatImp"]
|
||||
string <- map["string"]
|
||||
stringOptional <- map["stringOpt"]
|
||||
stringImplicityUnwrapped <- map["stringImp"]
|
||||
anyObject <- map["anyObject"]
|
||||
anyObjectOptional <- map["anyObjectOpt"]
|
||||
anyObjectImplicitlyUnwrapped <- map["anyObjectImp"]
|
||||
|
||||
arrayBool <- map["arrayBool"]
|
||||
arrayBoolOptional <- map["arrayBoolOpt"]
|
||||
arrayBoolImplicityUnwrapped <- map["arrayBoolImp"]
|
||||
arrayInt <- map["arrayInt"]
|
||||
arrayIntOptional <- map["arrayIntOpt"]
|
||||
arrayIntImplicityUnwrapped <- map["arrayIntImp"]
|
||||
arrayDouble <- map["arrayDouble"]
|
||||
arrayDoubleOptional <- map["arrayDoubleOpt"]
|
||||
arrayDoubleImplicityUnwrapped <- map["arrayDoubleImp"]
|
||||
arrayFloat <- map["arrayFloat"]
|
||||
arrayFloatOptional <- map["arrayFloatOpt"]
|
||||
arrayFloatImplicityUnwrapped <- map["arrayFloatImp"]
|
||||
arrayString <- map["arrayString"]
|
||||
arrayStringOptional <- map["arrayStringOpt"]
|
||||
arrayStringImplicityUnwrapped <- map["arrayStringImp"]
|
||||
arrayAnyObject <- map["arrayAnyObject"]
|
||||
arrayAnyObjectOptional <- map["arrayAnyObjectOpt"]
|
||||
arrayAnyObjectImplicitlyUnwrapped <- map["arrayAnyObjectImp"]
|
||||
|
||||
dictBool <- map["dictBool"]
|
||||
dictBoolOptional <- map["dictBoolOpt"]
|
||||
dictBoolImplicityUnwrapped <- map["dictBoolImp"]
|
||||
dictInt <- map["dictInt"]
|
||||
dictIntOptional <- map["dictIntOpt"]
|
||||
dictIntImplicityUnwrapped <- map["dictIntImp"]
|
||||
dictDouble <- map["dictDouble"]
|
||||
dictDoubleOptional <- map["dictDoubleOpt"]
|
||||
dictDoubleImplicityUnwrapped <- map["dictDoubleImp"]
|
||||
dictFloat <- map["dictFloat"]
|
||||
dictFloatOptional <- map["dictFloatOpt"]
|
||||
dictFloatImplicityUnwrapped <- map["dictFloatImp"]
|
||||
dictString <- map["dictString"]
|
||||
dictStringOptional <- map["dictStringOpt"]
|
||||
dictStringImplicityUnwrapped <- map["dictStringImp"]
|
||||
dictAnyObject <- map["dictAnyObject"]
|
||||
dictAnyObjectOptional <- map["dictAnyObjectOpt"]
|
||||
dictAnyObjectImplicitlyUnwrapped <- map["dictAnyObjectImp"]
|
||||
|
||||
enumInt <- map["enumInt"]
|
||||
enumIntOptional <- map["enumIntOpt"]
|
||||
enumIntImplicitlyUnwrapped <- map["enumIntImp"]
|
||||
enumDouble <- map["enumDouble"]
|
||||
enumDoubleOptional <- map["enumDoubleOpt"]
|
||||
enumDoubleImplicitlyUnwrapped <- map["enumDoubleImp"]
|
||||
enumFloat <- map["enumFloat"]
|
||||
enumFloatOptional <- map["enumFloatOpt"]
|
||||
enumFloatImplicitlyUnwrapped <- map["enumFloatImp"]
|
||||
enumString <- map["enumString"]
|
||||
enumStringOptional <- map["enumStringOpt"]
|
||||
enumStringImplicitlyUnwrapped <- map["enumStringImp"]
|
||||
|
||||
arrayEnumInt <- map["arrayEnumInt"]
|
||||
arrayEnumIntOptional <- map["arrayEnumIntOpt"]
|
||||
arrayEnumIntImplicitlyUnwrapped <- map["arrayEnumIntImp"]
|
||||
|
||||
dictEnumInt <- map["dictEnumInt"]
|
||||
dictEnumIntOptional <- map["dictEnumIntOpt"]
|
||||
dictEnumIntImplicitlyUnwrapped <- map["dictEnumIntImp"]
|
||||
}
|
||||
}
|
||||
|
||||
class TestCollectionOfPrimitives: Mappable {
|
||||
var dictStringString: [String: String] = [:]
|
||||
var dictStringInt: [String: Int] = [:]
|
||||
var dictStringBool: [String: Bool] = [:]
|
||||
var dictStringDouble: [String: Double] = [:]
|
||||
var dictStringFloat: [String: Float] = [:]
|
||||
|
||||
var arrayString: [String] = []
|
||||
var arrayInt: [Int] = []
|
||||
var arrayBool: [Bool] = []
|
||||
var arrayDouble: [Double] = []
|
||||
var arrayFloat: [Float] = []
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
if map["value"].value() == nil {
|
||||
|
||||
}
|
||||
if map.JSON["value"] == nil {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
dictStringString <- map["dictStringString"]
|
||||
dictStringBool <- map["dictStringBool"]
|
||||
dictStringInt <- map["dictStringInt"]
|
||||
dictStringDouble <- map["dictStringDouble"]
|
||||
dictStringFloat <- map["dictStringFloat"]
|
||||
arrayString <- map["arrayString"]
|
||||
arrayInt <- map["arrayInt"]
|
||||
arrayBool <- map["arrayBool"]
|
||||
arrayDouble <- map["arrayDouble"]
|
||||
arrayFloat <- map["arrayFloat"]
|
||||
}
|
||||
}
|
|
@ -1,616 +0,0 @@
|
|||
//
|
||||
// BasicTypesFromJSON.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-02-17.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class BasicTypesTestsFromJSON: XCTestCase {
|
||||
|
||||
let mapper = Mapper<BasicTypes>()
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
// MARK: Test mapping to JSON and back (basic types: Bool, Int, Double, Float, String)
|
||||
|
||||
func testMappingBoolFromJSON(){
|
||||
let value: Bool = true
|
||||
let JSONString = "{\"bool\" : \(value), \"boolOpt\" : \(value), \"boolImp\" : \(value)}"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.bool, value)
|
||||
XCTAssertEqual(mappedObject?.boolOptional, value)
|
||||
XCTAssertEqual(mappedObject?.boolImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
/// - warning: This test doens't consider integer overflow/underflow.
|
||||
func testMappingIntegerFromJSON(){
|
||||
func parameterize<T: FixedWidthInteger>(_ type: T.Type) {
|
||||
let value: T = 123
|
||||
let json: [String: Any] = [
|
||||
"int": value,
|
||||
"intOpt": value,
|
||||
"intImp": value,
|
||||
|
||||
"int8": value,
|
||||
"int8Opt": value,
|
||||
"int8Imp": value,
|
||||
|
||||
"int16": value,
|
||||
"int16Opt": value,
|
||||
"int16Imp": value,
|
||||
|
||||
"int32": value,
|
||||
"int32Opt": value,
|
||||
"int32Imp": value,
|
||||
|
||||
"int64": value,
|
||||
"int64Opt": value,
|
||||
"int64Imp": value,
|
||||
|
||||
"uint": value,
|
||||
"uintOpt": value,
|
||||
"uintImp": value,
|
||||
|
||||
"uint8": value,
|
||||
"uint8Opt": value,
|
||||
"uint8Imp": value,
|
||||
|
||||
"uint16": value,
|
||||
"uint16Opt": value,
|
||||
"uint16Imp": value,
|
||||
|
||||
"uint32": value,
|
||||
"uint32Opt": value,
|
||||
"uint32Imp": value,
|
||||
|
||||
"uint64": value,
|
||||
"uint64Opt": value,
|
||||
"uint64Imp": value,
|
||||
]
|
||||
let mappedObject = mapper.map(JSON: json)
|
||||
XCTAssertNotNil(mappedObject)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int, 123)
|
||||
XCTAssertEqual(mappedObject?.intOptional, 123)
|
||||
XCTAssertEqual(mappedObject?.intImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int8, 123)
|
||||
XCTAssertEqual(mappedObject?.int8Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int8ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int16, 123)
|
||||
XCTAssertEqual(mappedObject?.int16Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int16ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int32, 123)
|
||||
XCTAssertEqual(mappedObject?.int32Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int32ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int64, 123)
|
||||
XCTAssertEqual(mappedObject?.int64Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int64ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint, 123)
|
||||
XCTAssertEqual(mappedObject?.uintOptional, 123)
|
||||
XCTAssertEqual(mappedObject?.uintImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint8, 123)
|
||||
XCTAssertEqual(mappedObject?.uint8Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint8ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint16, 123)
|
||||
XCTAssertEqual(mappedObject?.uint16Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint16ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint32, 123)
|
||||
XCTAssertEqual(mappedObject?.uint32Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint32ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint64, 123)
|
||||
XCTAssertEqual(mappedObject?.uint64Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint64ImplicityUnwrapped, 123)
|
||||
}
|
||||
|
||||
parameterize(Int.self)
|
||||
parameterize(Int8.self)
|
||||
parameterize(Int16.self)
|
||||
parameterize(Int32.self)
|
||||
parameterize(Int64.self)
|
||||
|
||||
parameterize(UInt.self)
|
||||
parameterize(UInt8.self)
|
||||
parameterize(UInt16.self)
|
||||
parameterize(UInt32.self)
|
||||
parameterize(UInt64.self)
|
||||
}
|
||||
|
||||
func testMappingIntegerWithOverflowFromJSON(){
|
||||
let signedValue = Int.max
|
||||
let unsignedValue = UInt.max
|
||||
|
||||
let json: [String: Any] = [
|
||||
"int": signedValue,
|
||||
"intOpt": signedValue,
|
||||
"intImp": signedValue,
|
||||
|
||||
"int8": signedValue,
|
||||
"int8Opt": signedValue,
|
||||
"int8Imp": signedValue,
|
||||
|
||||
"int16": signedValue,
|
||||
"int16Opt": signedValue,
|
||||
"int16Imp": signedValue,
|
||||
|
||||
"int32": signedValue,
|
||||
"int32Opt": signedValue,
|
||||
"int32Imp": signedValue,
|
||||
|
||||
"int64": signedValue,
|
||||
"int64Opt": signedValue,
|
||||
"int64Imp": signedValue,
|
||||
|
||||
"uint": unsignedValue,
|
||||
"uintOpt": unsignedValue,
|
||||
"uintImp": unsignedValue,
|
||||
|
||||
"uint8": unsignedValue,
|
||||
"uint8Opt": unsignedValue,
|
||||
"uint8Imp": unsignedValue,
|
||||
|
||||
"uint16": unsignedValue,
|
||||
"uint16Opt": unsignedValue,
|
||||
"uint16Imp": unsignedValue,
|
||||
|
||||
"uint32": unsignedValue,
|
||||
"uint32Opt": unsignedValue,
|
||||
"uint32Imp": unsignedValue,
|
||||
|
||||
"uint64": unsignedValue,
|
||||
"uint64Opt": unsignedValue,
|
||||
"uint64Imp": unsignedValue,
|
||||
]
|
||||
let mappedObject = mapper.map(JSON: json)
|
||||
XCTAssertNotNil(mappedObject)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int, Int.max)
|
||||
XCTAssertEqual(mappedObject?.intOptional, Int.max)
|
||||
XCTAssertEqual(mappedObject?.intImplicityUnwrapped, Int.max)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int8, 0)
|
||||
XCTAssertEqual(mappedObject?.int8Optional, nil)
|
||||
XCTAssertEqual(mappedObject?.int8ImplicityUnwrapped, nil)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int16, 0)
|
||||
XCTAssertEqual(mappedObject?.int16Optional, nil)
|
||||
XCTAssertEqual(mappedObject?.int16ImplicityUnwrapped, nil)
|
||||
|
||||
#if arch(x86_64) || arch(arm64)
|
||||
XCTAssertEqual(mappedObject?.int32, 0)
|
||||
XCTAssertEqual(mappedObject?.int32Optional, nil)
|
||||
XCTAssertEqual(mappedObject?.int32ImplicityUnwrapped, nil)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int64, Int64.max)
|
||||
XCTAssertEqual(mappedObject?.int64Optional, Int64.max)
|
||||
XCTAssertEqual(mappedObject?.int64ImplicityUnwrapped, Int64.max)
|
||||
#else
|
||||
XCTAssertEqual(mappedObject?.int32, Int32.max)
|
||||
XCTAssertEqual(mappedObject?.int32Optional, Int32.max)
|
||||
XCTAssertEqual(mappedObject?.int32ImplicityUnwrapped, Int32.max)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int64, Int64(Int32.max))
|
||||
XCTAssertEqual(mappedObject?.int64Optional, Int64(Int32.max))
|
||||
XCTAssertEqual(mappedObject?.int64ImplicityUnwrapped, Int64(Int32.max))
|
||||
#endif
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint, UInt.max)
|
||||
XCTAssertEqual(mappedObject?.uintOptional, UInt.max)
|
||||
XCTAssertEqual(mappedObject?.uintImplicityUnwrapped, UInt.max)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint8, 0)
|
||||
XCTAssertEqual(mappedObject?.uint8Optional, nil)
|
||||
XCTAssertEqual(mappedObject?.uint8ImplicityUnwrapped, nil)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint16, 0)
|
||||
XCTAssertEqual(mappedObject?.uint16Optional, nil)
|
||||
XCTAssertEqual(mappedObject?.uint16ImplicityUnwrapped, nil)
|
||||
|
||||
#if arch(x86_64) || arch(arm64)
|
||||
XCTAssertEqual(mappedObject?.uint32, 0)
|
||||
XCTAssertEqual(mappedObject?.uint32Optional, nil)
|
||||
XCTAssertEqual(mappedObject?.uint32ImplicityUnwrapped, nil)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint64, UInt64.max)
|
||||
XCTAssertEqual(mappedObject?.uint64Optional, UInt64.max)
|
||||
XCTAssertEqual(mappedObject?.uint64ImplicityUnwrapped, UInt64.max)
|
||||
#else
|
||||
XCTAssertEqual(mappedObject?.uint32, UInt32.max)
|
||||
XCTAssertEqual(mappedObject?.uint32Optional, UInt32.max)
|
||||
XCTAssertEqual(mappedObject?.uint32ImplicityUnwrapped, UInt32.max)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint64, UInt64(UInt32.max))
|
||||
XCTAssertEqual(mappedObject?.uint64Optional, UInt64(UInt32.max))
|
||||
XCTAssertEqual(mappedObject?.uint64ImplicityUnwrapped, UInt64(UInt32.max))
|
||||
#endif
|
||||
}
|
||||
|
||||
func testMappingDoubleFromJSON(){
|
||||
let value: Double = 11
|
||||
let JSONString = "{\"double\" : \(value), \"doubleOpt\" : \(value), \"doubleImp\" : \(value)}"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.double, value)
|
||||
XCTAssertEqual(mappedObject?.doubleOptional, value)
|
||||
XCTAssertEqual(mappedObject?.doubleImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingFloatFromJSON(){
|
||||
let value: Float = 11
|
||||
let JSONString = "{\"float\" : \(value), \"floatOpt\" : \(value), \"floatImp\" : \(value)}"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.float, value)
|
||||
XCTAssertEqual(mappedObject?.floatOptional, value)
|
||||
XCTAssertEqual(mappedObject?.floatImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingStringFromJSON(){
|
||||
let value: String = "STRINGNGNGG"
|
||||
let JSONString = "{\"string\" : \"\(value)\", \"stringOpt\" : \"\(value)\", \"stringImp\" : \"\(value)\"}"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.string, value)
|
||||
XCTAssertEqual(mappedObject?.stringOptional, value)
|
||||
XCTAssertEqual(mappedObject?.stringImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingAnyObjectFromJSON(){
|
||||
let value1 = "STRING"
|
||||
let value2: Int = 1234
|
||||
let value3: Double = 11.11
|
||||
let JSONString = "{\"anyObject\" : \"\(value1)\", \"anyObjectOpt\" : \(value2), \"anyObjectImp\" : \(value3)}"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.anyObject as? String, value1)
|
||||
XCTAssertEqual(mappedObject?.anyObjectOptional as? Int, value2)
|
||||
XCTAssertEqual(mappedObject?.anyObjectImplicitlyUnwrapped as? Double, value3)
|
||||
}
|
||||
|
||||
func testMappingStringFromNSStringJSON(){
|
||||
let value: String = "STRINGNGNGG"
|
||||
let JSONNSString : NSString = "{\"string\" : \"\(value)\", \"stringOpt\" : \"\(value)\", \"stringImp\" : \"\(value)\"}" as NSString
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONNSString as String)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.string, value)
|
||||
XCTAssertEqual(mappedObject?.stringOptional, value)
|
||||
XCTAssertEqual(mappedObject?.stringImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
// MARK: Test mapping Arrays to JSON and back (with basic types in them Bool, Int, Double, Float, String)
|
||||
|
||||
func testMappingBoolArrayFromJSON(){
|
||||
let value: Bool = true
|
||||
let JSONString = "{\"arrayBool\" : [\(value)], \"arrayBoolOpt\" : [\(value)], \"arrayBoolImp\" : [\(value)] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayBool.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayBoolOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayBoolImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingIntArrayFromJSON(){
|
||||
let value: Int = 1
|
||||
let JSONString = "{\"arrayInt\" : [\(value)], \"arrayIntOpt\" : [\(value)], \"arrayIntImp\" : [\(value)] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayInt.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayIntOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayIntImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingDoubleArrayFromJSON(){
|
||||
let value: Double = 1.0
|
||||
let JSONString = "{\"arrayDouble\" : [\(value)], \"arrayDoubleOpt\" : [\(value)], \"arrayDoubleImp\" : [\(value)] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayDouble.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayDoubleOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayDoubleImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingFloatArrayFromJSON(){
|
||||
let value: Float = 1.001
|
||||
let JSONString = "{\"arrayFloat\" : [\(value)], \"arrayFloatOpt\" : [\(value)], \"arrayFloatImp\" : [\(value)] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayFloat.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayFloatOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayFloatImplicityUnwrapped?.first, value)
|
||||
}
|
||||
|
||||
func testMappingStringArrayFromJSON(){
|
||||
let value: String = "Stringgggg"
|
||||
let JSONString = "{\"arrayString\" : [\"\(value)\"], \"arrayStringOpt\" : [\"\(value)\"], \"arrayStringImp\" : [\"\(value)\"] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayString.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayStringOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayStringImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingAnyObjectArrayFromJSON(){
|
||||
let value1 = "STRING"
|
||||
let value2: Int = 1234
|
||||
let value3: Double = 11.11
|
||||
let JSONString = "{\"arrayAnyObject\" : [\"\(value1)\"], \"arrayAnyObjectOpt\" : [\(value2)], \"arrayAnyObjectImp\" : [\(value3)] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayAnyObject.first as? String, value1)
|
||||
XCTAssertEqual(mappedObject?.arrayAnyObjectOptional?.first as? Int, value2)
|
||||
XCTAssertEqual(mappedObject?.arrayAnyObjectImplicitlyUnwrapped.first as? Double, value3)
|
||||
}
|
||||
|
||||
// MARK: Test mapping Dictionaries to JSON and back (with basic types in them Bool, Int, Double, Float, String)
|
||||
|
||||
func testMappingBoolDictionaryFromJSON(){
|
||||
let key = "key"
|
||||
let value: Bool = true
|
||||
let JSONString = "{\"dictBool\" : { \"\(key)\" : \(value)}, \"dictBoolOpt\" : { \"\(key)\" : \(value)}, \"dictBoolImp\" : { \"\(key)\" : \(value)} }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictBool[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictBoolOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictBoolImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingIntDictionaryFromJSON(){
|
||||
let key = "key"
|
||||
let value: Int = 11
|
||||
let JSONString = "{\"dictInt\" : { \"\(key)\" : \(value)}, \"dictIntOpt\" : { \"\(key)\" : \(value)}, \"dictIntImp\" : { \"\(key)\" : \(value)} }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictInt[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictIntOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictIntImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingDoubleDictionaryFromJSON(){
|
||||
let key = "key"
|
||||
let value: Double = 11
|
||||
let JSONString = "{\"dictDouble\" : { \"\(key)\" : \(value)}, \"dictDoubleOpt\" : { \"\(key)\" : \(value)}, \"dictDoubleImp\" : { \"\(key)\" : \(value)} }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictDouble[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictDoubleOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictDoubleImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingFloatDictionaryFromJSON(){
|
||||
let key = "key"
|
||||
let value: Float = 111.1
|
||||
let JSONString = "{\"dictFloat\" : { \"\(key)\" : \(value)}, \"dictFloatOpt\" : { \"\(key)\" : \(value)}, \"dictFloatImp\" : { \"\(key)\" : \(value)} }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictFloat[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictFloatOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictFloatImplicityUnwrapped?[key], value)
|
||||
}
|
||||
|
||||
func testMappingStringDictionaryFromJSON(){
|
||||
let key = "key"
|
||||
let value = "value"
|
||||
let JSONString = "{\"dictString\" : { \"\(key)\" : \"\(value)\"}, \"dictStringOpt\" : { \"\(key)\" : \"\(value)\"}, \"dictStringImp\" : { \"\(key)\" : \"\(value)\"} }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictString[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictStringOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictStringImplicityUnwrapped?[key], value)
|
||||
}
|
||||
|
||||
func testMappingAnyObjectDictionaryFromJSON(){
|
||||
let key = "key"
|
||||
let value1 = "STRING"
|
||||
let value2: Int = 1234
|
||||
let value3: Double = 11.11
|
||||
let JSONString = "{\"dictAnyObject\" : { \"\(key)\" : \"\(value1)\"}, \"dictAnyObjectOpt\" : { \"\(key)\" : \(value2)}, \"dictAnyObjectImp\" : { \"\(key)\" : \(value3)} }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictAnyObject[key] as? String, value1)
|
||||
XCTAssertEqual(mappedObject?.dictAnyObjectOptional?[key] as? Int, value2)
|
||||
XCTAssertEqual(mappedObject?.dictAnyObjectImplicitlyUnwrapped[key] as? Double, value3)
|
||||
}
|
||||
|
||||
func testMappingIntEnumFromJSON(){
|
||||
let value: BasicTypes.EnumInt = .Another
|
||||
let JSONString = "{\"enumInt\" : \(value.rawValue), \"enumIntOpt\" : \(value.rawValue), \"enumIntImp\" : \(value.rawValue) }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumInt, value)
|
||||
XCTAssertEqual(mappedObject?.enumIntOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumIntImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingIntEnumFromJSONShouldNotCrashWithNonDefinedvalue() {
|
||||
let value = Int.min
|
||||
let JSONString = "{\"enumInt\" : \(value), \"enumIntOpt\" : \(value), \"enumIntImp\" : \(value) }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumInt, BasicTypes.EnumInt.Default)
|
||||
XCTAssertNil(mappedObject?.enumIntOptional)
|
||||
XCTAssertNil(mappedObject?.enumIntImplicitlyUnwrapped)
|
||||
}
|
||||
|
||||
func testMappingDoubleEnumFromJSON(){
|
||||
let value: BasicTypes.EnumDouble = .Another
|
||||
let JSONString = "{\"enumDouble\" : \(value.rawValue), \"enumDoubleOpt\" : \(value.rawValue), \"enumDoubleImp\" : \(value.rawValue) }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumDouble, value)
|
||||
XCTAssertEqual(mappedObject?.enumDoubleOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumDoubleImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingFloatEnumFromJSON(){
|
||||
let value: BasicTypes.EnumFloat = .Another
|
||||
let JSONString = "{\"enumFloat\" : \(value.rawValue), \"enumFloatOpt\" : \(value.rawValue), \"enumFloatImp\" : \(value.rawValue) }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumFloat, value)
|
||||
XCTAssertEqual(mappedObject?.enumFloatOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumFloatImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingStringEnumFromJSON(){
|
||||
let value: BasicTypes.EnumString = .Another
|
||||
let JSONString = "{\"enumString\" : \"\(value.rawValue)\", \"enumStringOpt\" : \"\(value.rawValue)\", \"enumStringImp\" : \"\(value.rawValue)\" }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumString, value)
|
||||
XCTAssertEqual(mappedObject?.enumStringOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumStringImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingEnumIntArrayFromJSON(){
|
||||
let value: BasicTypes.EnumInt = .Another
|
||||
let JSONString = "{ \"arrayEnumInt\" : [\(value.rawValue)], \"arrayEnumIntOpt\" : [\(value.rawValue)], \"arrayEnumIntImp\" : [\(value.rawValue)] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayEnumInt.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayEnumIntOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayEnumIntImplicitlyUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingEnumIntArrayFromJSONShouldNotCrashWithNonDefinedvalue() {
|
||||
let value = Int.min
|
||||
let JSONString = "{ \"arrayEnumInt\" : [\(value)], \"arrayEnumIntOpt\" : [\(value)], \"arrayEnumIntImp\" : [\(value)] }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertNil(mappedObject?.arrayEnumInt.first)
|
||||
XCTAssertNil(mappedObject?.arrayEnumIntOptional?.first)
|
||||
XCTAssertNil(mappedObject?.arrayEnumIntImplicitlyUnwrapped.first)
|
||||
}
|
||||
|
||||
func testMappingEnumIntDictionaryFromJSON(){
|
||||
let key = "key"
|
||||
let value: BasicTypes.EnumInt = .Another
|
||||
let JSONString = "{ \"dictEnumInt\" : { \"\(key)\" : \(value.rawValue) }, \"dictEnumIntOpt\" : { \"\(key)\" : \(value.rawValue) }, \"dictEnumIntImp\" : { \"\(key)\" : \(value.rawValue) } }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictEnumInt[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictEnumIntOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictEnumIntImplicitlyUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingEnumIntDictionaryFromJSONShouldNotCrashWithNonDefinedvalue() {
|
||||
let key = "key"
|
||||
let value = Int.min
|
||||
let JSONString = "{ \"dictEnumInt\" : { \"\(key)\" : \(value) }, \"dictEnumIntOpt\" : { \"\(key)\" : \(value) }, \"dictEnumIntImp\" : { \"\(key)\" : \(value) } }"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertNil(mappedObject?.dictEnumInt[key])
|
||||
XCTAssertNil(mappedObject?.dictEnumIntOptional?[key])
|
||||
XCTAssertNil(mappedObject?.dictEnumIntImplicitlyUnwrapped[key])
|
||||
}
|
||||
|
||||
func testObjectModelOptionalDictionnaryOfPrimitives() {
|
||||
let JSON: [String: [String: Any]] = ["dictStringString":["string": "string"], "dictStringBool":["string": false], "dictStringInt":["string": 1], "dictStringDouble":["string": 1.1], "dictStringFloat":["string": Float(1.2)]]
|
||||
|
||||
let mapper = Mapper<TestCollectionOfPrimitives>()
|
||||
let testSet: TestCollectionOfPrimitives! = mapper.map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(testSet)
|
||||
|
||||
XCTAssertTrue(testSet.dictStringString.count > 0)
|
||||
XCTAssertTrue(testSet.dictStringInt.count > 0)
|
||||
XCTAssertTrue(testSet.dictStringBool.count > 0)
|
||||
XCTAssertTrue(testSet.dictStringDouble.count > 0)
|
||||
XCTAssertTrue(testSet.dictStringFloat.count > 0)
|
||||
}
|
||||
}
|
|
@ -1,576 +0,0 @@
|
|||
//
|
||||
// BasicTypesTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-12-04.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class BasicTypesTestsToJSON: XCTestCase {
|
||||
|
||||
let mapper = Mapper<BasicTypes>()
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
// MARK: Test mapping to JSON and back (basic types: Bool, Int, Double, Float, String)
|
||||
|
||||
func testShouldIncludeNilValues(){
|
||||
let object = BasicTypes()
|
||||
|
||||
let JSONWithNil = Mapper<BasicTypes>(shouldIncludeNilValues: true).toJSONString(object, prettyPrint: true)
|
||||
let JSONWithoutNil = Mapper<BasicTypes>(shouldIncludeNilValues: false).toJSONString(object, prettyPrint: true)
|
||||
|
||||
//TODO This test could be improved
|
||||
XCTAssertNotNil(JSONWithNil)
|
||||
XCTAssertTrue((JSONWithNil!.count) > 5)
|
||||
XCTAssertTrue((JSONWithNil!.count) != (JSONWithoutNil!.count))
|
||||
}
|
||||
|
||||
func testMappingBoolToJSON(){
|
||||
let value: Bool = true
|
||||
let object = BasicTypes()
|
||||
object.bool = value
|
||||
object.boolOptional = value
|
||||
object.boolImplicityUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.bool, value)
|
||||
XCTAssertEqual(mappedObject?.boolOptional, value)
|
||||
XCTAssertEqual(mappedObject?.boolImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingIntegerToJSON(){
|
||||
let object = BasicTypes()
|
||||
|
||||
object.int = 123
|
||||
object.intOptional = 123
|
||||
object.intImplicityUnwrapped = 123
|
||||
|
||||
object.int8 = 123
|
||||
object.int8Optional = 123
|
||||
object.int8ImplicityUnwrapped = 123
|
||||
|
||||
object.int16 = 123
|
||||
object.int16Optional = 123
|
||||
object.int16ImplicityUnwrapped = 123
|
||||
|
||||
object.int32 = 123
|
||||
object.int32Optional = 123
|
||||
object.int32ImplicityUnwrapped = 123
|
||||
|
||||
object.int64 = 123
|
||||
object.int64Optional = 123
|
||||
object.int64ImplicityUnwrapped = 123
|
||||
|
||||
object.uint = 123
|
||||
object.uintOptional = 123
|
||||
object.uintImplicityUnwrapped = 123
|
||||
|
||||
object.uint8 = 123
|
||||
object.uint8Optional = 123
|
||||
object.uint8ImplicityUnwrapped = 123
|
||||
|
||||
object.uint16 = 123
|
||||
object.uint16Optional = 123
|
||||
object.uint16ImplicityUnwrapped = 123
|
||||
|
||||
object.uint32 = 123
|
||||
object.uint32Optional = 123
|
||||
object.uint32ImplicityUnwrapped = 123
|
||||
|
||||
object.uint64 = 123
|
||||
object.uint64Optional = 123
|
||||
object.uint64ImplicityUnwrapped = 123
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int, 123)
|
||||
XCTAssertEqual(mappedObject?.intOptional, 123)
|
||||
XCTAssertEqual(mappedObject?.intImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int8, 123)
|
||||
XCTAssertEqual(mappedObject?.int8Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int8ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int16, 123)
|
||||
XCTAssertEqual(mappedObject?.int16Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int16ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int32, 123)
|
||||
XCTAssertEqual(mappedObject?.int32Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int32ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.int64, 123)
|
||||
XCTAssertEqual(mappedObject?.int64Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.int64ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint, 123)
|
||||
XCTAssertEqual(mappedObject?.uintOptional, 123)
|
||||
XCTAssertEqual(mappedObject?.uintImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint8, 123)
|
||||
XCTAssertEqual(mappedObject?.uint8Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint8ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint16, 123)
|
||||
XCTAssertEqual(mappedObject?.uint16Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint16ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint32, 123)
|
||||
XCTAssertEqual(mappedObject?.uint32Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint32ImplicityUnwrapped, 123)
|
||||
|
||||
XCTAssertEqual(mappedObject?.uint64, 123)
|
||||
XCTAssertEqual(mappedObject?.uint64Optional, 123)
|
||||
XCTAssertEqual(mappedObject?.uint64ImplicityUnwrapped, 123)
|
||||
}
|
||||
|
||||
func testMappingDoubleToJSON(){
|
||||
let value: Double = 11
|
||||
let object = BasicTypes()
|
||||
object.double = value
|
||||
object.doubleOptional = value
|
||||
object.doubleImplicityUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.double, value)
|
||||
XCTAssertEqual(mappedObject?.doubleOptional, value)
|
||||
XCTAssertEqual(mappedObject?.doubleImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingFloatToJSON(){
|
||||
let value: Float = 11
|
||||
let object = BasicTypes()
|
||||
object.float = value
|
||||
object.floatOptional = value
|
||||
object.floatImplicityUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.float, value)
|
||||
XCTAssertEqual(mappedObject?.floatOptional, value)
|
||||
XCTAssertEqual(mappedObject?.floatImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingStringToJSON(){
|
||||
let value: String = "STRINGNGNGG"
|
||||
let object = BasicTypes()
|
||||
object.string = value
|
||||
object.stringOptional = value
|
||||
object.stringImplicityUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.string, value)
|
||||
XCTAssertEqual(mappedObject?.stringOptional, value)
|
||||
XCTAssertEqual(mappedObject?.stringImplicityUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingAnyObjectToJSON(){
|
||||
let value: String = "STRINGNGNGG"
|
||||
let object = BasicTypes()
|
||||
object.anyObject = value
|
||||
object.anyObjectOptional = value
|
||||
object.anyObjectImplicitlyUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.anyObject as? String, value)
|
||||
XCTAssertEqual(mappedObject?.anyObjectOptional as? String, value)
|
||||
XCTAssertEqual(mappedObject?.anyObjectImplicitlyUnwrapped as? String, value)
|
||||
}
|
||||
|
||||
// MARK: Test mapping Arrays to JSON and back (with basic types in them Bool, Int, Double, Float, String)
|
||||
|
||||
func testMappingEmptyArrayToJSON(){
|
||||
let object = BasicTypes()
|
||||
object.arrayBool = []
|
||||
object.arrayBoolOptional = []
|
||||
object.arrayBoolImplicityUnwrapped = []
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject!.arrayBool, [])
|
||||
XCTAssertEqual(mappedObject!.arrayBoolOptional!, [])
|
||||
XCTAssertEqual(mappedObject!.arrayBoolImplicityUnwrapped, [])
|
||||
}
|
||||
|
||||
func testMappingBoolArrayToJSON(){
|
||||
let value: Bool = true
|
||||
let object = BasicTypes()
|
||||
object.arrayBool = [value]
|
||||
object.arrayBoolOptional = [value]
|
||||
object.arrayBoolImplicityUnwrapped = [value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayBool.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayBoolOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayBoolImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingIntArrayToJSON(){
|
||||
let value: Int = 1
|
||||
let object = BasicTypes()
|
||||
object.arrayInt = [value]
|
||||
object.arrayIntOptional = [value]
|
||||
object.arrayIntImplicityUnwrapped = [value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayInt.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayIntOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayIntImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingDoubleArrayToJSON(){
|
||||
let value: Double = 1.0
|
||||
let object = BasicTypes()
|
||||
object.arrayDouble = [value]
|
||||
object.arrayDoubleOptional = [value]
|
||||
object.arrayDoubleImplicityUnwrapped = [value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayDouble.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayDoubleOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayDoubleImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingFloatArrayToJSON(){
|
||||
let value: Float = 1.001
|
||||
let object = BasicTypes()
|
||||
object.arrayFloat = [value]
|
||||
object.arrayFloatOptional = [value]
|
||||
object.arrayFloatImplicityUnwrapped = [value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayFloat.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayFloatOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayFloatImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingStringArrayToJSON(){
|
||||
let value: String = "Stringgggg"
|
||||
let object = BasicTypes()
|
||||
object.arrayString = [value]
|
||||
object.arrayStringOptional = [value]
|
||||
object.arrayStringImplicityUnwrapped = [value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayString.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayStringOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayStringImplicityUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingAnyObjectArrayToJSON(){
|
||||
let value: String = "Stringgggg"
|
||||
let object = BasicTypes()
|
||||
object.arrayAnyObject = [value]
|
||||
object.arrayAnyObjectOptional = [value]
|
||||
object.arrayAnyObjectImplicitlyUnwrapped = [value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayAnyObject.first as? String, value)
|
||||
XCTAssertEqual(mappedObject?.arrayAnyObjectOptional?.first as? String, value)
|
||||
XCTAssertEqual(mappedObject?.arrayAnyObjectImplicitlyUnwrapped.first as? String, value)
|
||||
}
|
||||
|
||||
// MARK: Test mapping Dictionaries to JSON and back (with basic types in them Bool, Int, Double, Float, String)
|
||||
|
||||
func testMappingEmptyDictionaryToJSON(){
|
||||
let object = BasicTypes()
|
||||
object.dictBool = [:]
|
||||
object.dictBoolOptional = [:]
|
||||
object.dictBoolImplicityUnwrapped = [:]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject!.dictBool, [:])
|
||||
XCTAssertEqual(mappedObject!.dictBoolOptional!, [:])
|
||||
XCTAssertEqual(mappedObject!.dictBoolImplicityUnwrapped, [:])
|
||||
}
|
||||
|
||||
func testMappingBoolDictionaryToJSON(){
|
||||
let key = "key"
|
||||
let value: Bool = true
|
||||
let object = BasicTypes()
|
||||
object.dictBool = [key:value]
|
||||
object.dictBoolOptional = [key:value]
|
||||
object.dictBoolImplicityUnwrapped = [key:value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictBool[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictBoolOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictBoolImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingIntDictionaryToJSON(){
|
||||
let key = "key"
|
||||
let value: Int = 11
|
||||
let object = BasicTypes()
|
||||
object.dictInt = [key:value]
|
||||
object.dictIntOptional = [key:value]
|
||||
object.dictIntImplicityUnwrapped = [key:value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictInt[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictIntOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictIntImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingDoubleDictionaryToJSON(){
|
||||
let key = "key"
|
||||
let value: Double = 11
|
||||
let object = BasicTypes()
|
||||
object.dictDouble = [key:value]
|
||||
object.dictDoubleOptional = [key:value]
|
||||
object.dictDoubleImplicityUnwrapped = [key:value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictDouble[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictDoubleOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictDoubleImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingFloatDictionaryToJSON(){
|
||||
let key = "key"
|
||||
let value: Float = 11
|
||||
let object = BasicTypes()
|
||||
object.dictFloat = [key:value]
|
||||
object.dictFloatOptional = [key:value]
|
||||
object.dictFloatImplicityUnwrapped = [key:value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictFloat[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictFloatOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictFloatImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingStringDictionaryToJSON(){
|
||||
let key = "key"
|
||||
let value = "value"
|
||||
let object = BasicTypes()
|
||||
object.dictString = [key:value]
|
||||
object.dictStringOptional = [key:value]
|
||||
object.dictStringImplicityUnwrapped = [key:value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictString[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictStringOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictStringImplicityUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testMappingAnyObjectDictionaryToJSON(){
|
||||
let key = "key"
|
||||
let value = "value"
|
||||
let object = BasicTypes()
|
||||
object.dictAnyObject = [key:value]
|
||||
object.dictAnyObjectOptional = [key:value]
|
||||
object.dictAnyObjectImplicitlyUnwrapped = [key:value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictAnyObject[key] as? String, value)
|
||||
XCTAssertEqual(mappedObject?.dictAnyObjectOptional?[key] as? String, value)
|
||||
XCTAssertEqual(mappedObject?.dictAnyObjectImplicitlyUnwrapped[key] as? String, value)
|
||||
}
|
||||
|
||||
func testMappingIntEnumToJSON(){
|
||||
let value = BasicTypes.EnumInt.Another
|
||||
let object = BasicTypes()
|
||||
object.enumInt = value
|
||||
object.enumIntOptional = value
|
||||
object.enumIntImplicitlyUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumInt, value)
|
||||
XCTAssertEqual(mappedObject?.enumIntOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumIntImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingDoubleEnumToJSON(){
|
||||
let value = BasicTypes.EnumDouble.Another
|
||||
let object = BasicTypes()
|
||||
object.enumDouble = value
|
||||
object.enumDoubleOptional = value
|
||||
object.enumDoubleImplicitlyUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumDouble, value)
|
||||
XCTAssertEqual(mappedObject?.enumDoubleOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumDoubleImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingFloatEnumToJSON(){
|
||||
let value = BasicTypes.EnumFloat.Another
|
||||
let object = BasicTypes()
|
||||
object.enumFloat = value
|
||||
object.enumFloatOptional = value
|
||||
object.enumFloatImplicitlyUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumFloat, value)
|
||||
XCTAssertEqual(mappedObject?.enumFloatOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumFloatImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingStringEnumToJSON(){
|
||||
let value = BasicTypes.EnumString.Another
|
||||
let object = BasicTypes()
|
||||
object.enumString = value
|
||||
object.enumStringOptional = value
|
||||
object.enumStringImplicitlyUnwrapped = value
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.enumString, value)
|
||||
XCTAssertEqual(mappedObject?.enumStringOptional, value)
|
||||
XCTAssertEqual(mappedObject?.enumStringImplicitlyUnwrapped, value)
|
||||
}
|
||||
|
||||
func testMappingEnumIntArrayToJSON(){
|
||||
let value = BasicTypes.EnumInt.Another
|
||||
let object = BasicTypes()
|
||||
object.arrayEnumInt = [value]
|
||||
object.arrayEnumIntOptional = [value]
|
||||
object.arrayEnumIntImplicitlyUnwrapped = [value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.arrayEnumInt.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayEnumIntOptional?.first, value)
|
||||
XCTAssertEqual(mappedObject?.arrayEnumIntImplicitlyUnwrapped.first, value)
|
||||
}
|
||||
|
||||
func testMappingEnumIntDictionaryToJSON(){
|
||||
let key = "key"
|
||||
let value = BasicTypes.EnumInt.Another
|
||||
let object = BasicTypes()
|
||||
object.dictEnumInt = [key: value]
|
||||
object.dictEnumIntOptional = [key: value]
|
||||
object.dictEnumIntImplicitlyUnwrapped = [key: value]
|
||||
|
||||
let JSONString = Mapper().toJSONString(object, prettyPrint: true)
|
||||
let mappedObject = mapper.map(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.dictEnumInt[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictEnumIntOptional?[key], value)
|
||||
XCTAssertEqual(mappedObject?.dictEnumIntImplicitlyUnwrapped[key], value)
|
||||
}
|
||||
|
||||
func testObjectToModelDictionnaryOfPrimitives() {
|
||||
let object = TestCollectionOfPrimitives()
|
||||
object.dictStringString = ["string": "string"]
|
||||
object.dictStringBool = ["string": false]
|
||||
object.dictStringInt = ["string": 1]
|
||||
object.dictStringDouble = ["string": 1.2]
|
||||
object.dictStringFloat = ["string": 1.3]
|
||||
|
||||
let json = Mapper<TestCollectionOfPrimitives>().toJSON(object)
|
||||
|
||||
XCTAssertTrue((json["dictStringString"] as? [String:String])?.count ?? 0 > 0)
|
||||
XCTAssertTrue((json["dictStringBool"] as? [String:Bool])?.count ?? 0 > 0)
|
||||
XCTAssertTrue((json["dictStringInt"] as? [String:Int])?.count ?? 0 > 0)
|
||||
XCTAssertTrue((json["dictStringDouble"] as? [String:Double])?.count ?? 0 > 0)
|
||||
XCTAssertTrue((json["dictStringFloat"] as? [String:Float])?.count ?? 0 > 0)
|
||||
XCTAssertEqual((json["dictStringString"] as? [String:String])?["string"], "string")
|
||||
}
|
||||
}
|
|
@ -1,128 +0,0 @@
|
|||
//
|
||||
// ClassClusterTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-09-18.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class ClassClusterTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testClassClusters() {
|
||||
let carName = "Honda"
|
||||
let JSON = ["name": carName, "type": "car"]
|
||||
|
||||
if let vehicle = Mapper<Vehicle>().map(JSON: JSON){
|
||||
XCTAssertNotNil(vehicle)
|
||||
XCTAssertNotNil(vehicle as? Car)
|
||||
XCTAssertEqual((vehicle as? Car)?.name, carName)
|
||||
}
|
||||
}
|
||||
|
||||
func testClassClustersFromJSONString() {
|
||||
let carName = "Honda"
|
||||
let JSON = "{\"name\": \"\(carName)\", \"type\": \"car\"}"
|
||||
|
||||
if let vehicle = Mapper<Vehicle>().map(JSONString: JSON){
|
||||
XCTAssertNotNil(vehicle)
|
||||
XCTAssertNotNil(vehicle as? Car)
|
||||
XCTAssertEqual((vehicle as? Car)?.name, carName)
|
||||
}
|
||||
}
|
||||
|
||||
func testClassClusterArray() {
|
||||
let carName = "Honda"
|
||||
let JSON = [["name": carName, "type": "car"], ["type": "bus"], ["type": "vehicle"]]
|
||||
|
||||
let vehicles = Mapper<Vehicle>().mapArray(JSONArray: JSON)
|
||||
XCTAssertNotNil(vehicles)
|
||||
XCTAssertTrue(vehicles.count == 3)
|
||||
XCTAssertNotNil(vehicles[0] as? Car)
|
||||
XCTAssertNotNil(vehicles[1] as? Bus)
|
||||
XCTAssertNotNil(vehicles[2])
|
||||
XCTAssertEqual((vehicles[0] as? Car)?.name, carName)
|
||||
}
|
||||
}
|
||||
|
||||
class Vehicle: StaticMappable {
|
||||
|
||||
var type: String?
|
||||
|
||||
class func objectForMapping(map: Map) -> BaseMappable? {
|
||||
if let type: String = map["type"].value() {
|
||||
switch type {
|
||||
case "car":
|
||||
return Car()
|
||||
case "bus":
|
||||
return Bus()
|
||||
default:
|
||||
return Vehicle()
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
type <- map["type"]
|
||||
}
|
||||
}
|
||||
|
||||
class Car: Vehicle {
|
||||
|
||||
var name: String?
|
||||
|
||||
override class func objectForMapping(map: Map) -> BaseMappable? {
|
||||
return nil
|
||||
}
|
||||
|
||||
override func mapping(map: Map) {
|
||||
super.mapping(map: map)
|
||||
|
||||
name <- map["name"]
|
||||
}
|
||||
}
|
||||
|
||||
class Bus: Vehicle {
|
||||
|
||||
override func mapping(map: Map) {
|
||||
super.mapping(map: map)
|
||||
}
|
||||
}
|
|
@ -1,85 +0,0 @@
|
|||
//
|
||||
// CodableTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Jari Kalinainen on 11.10.18.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class CodableTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testCodableTransform() {
|
||||
let value: [String: Any] = [ "one": "1", "two": 2, "three": true ]
|
||||
let JSON: [String: Any] = [ "value": value, "array_value": [value, value]]
|
||||
|
||||
let mapper = Mapper<ImmutableMappableObject>()
|
||||
|
||||
let object: ImmutableMappableObject! = mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(object)
|
||||
XCTAssertNil(object.nilValue) // without transform this is nil
|
||||
XCTAssertNotNil(object.value)
|
||||
XCTAssertNotNil(object.value?.one)
|
||||
XCTAssertNotNil(object.value?.two)
|
||||
XCTAssertNotNil(object.value?.three)
|
||||
XCTAssertNotNil(object.arrayValue)
|
||||
}
|
||||
}
|
||||
|
||||
class ImmutableMappableObject: ImmutableMappable {
|
||||
|
||||
var value: CodableModel?
|
||||
var arrayValue: [CodableModel]?
|
||||
var nilValue: CodableModel?
|
||||
|
||||
required init(map: Map) throws {
|
||||
nilValue = try? map.value("value")
|
||||
value = try? map.value("value", using: CodableTransform<CodableModel>())
|
||||
arrayValue = try? map.value("array_value", using: CodableTransform<[CodableModel]>())
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
nilValue <- map["value"]
|
||||
value <- (map["value"], using: CodableTransform<CodableModel>())
|
||||
arrayValue <- (map["array_value"], using: CodableTransform<[CodableModel]>())
|
||||
}
|
||||
}
|
||||
|
||||
struct CodableModel: Codable {
|
||||
let one: String
|
||||
let two: Int
|
||||
let three: Bool
|
||||
}
|
|
@ -1,266 +0,0 @@
|
|||
//
|
||||
// CustomTransformTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-03-09.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
#if os(iOS) || os(tvOS) || os(watchOS)
|
||||
typealias TestHexColor = UIColor
|
||||
#else
|
||||
typealias TestHexColor = NSColor
|
||||
#endif
|
||||
|
||||
class CustomTransformTests: XCTestCase {
|
||||
|
||||
let mapper = Mapper<Transforms>()
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testDateTransform() {
|
||||
let transforms = Transforms()
|
||||
transforms.date = Date(timeIntervalSince1970: 946684800)
|
||||
transforms.dateOpt = Date(timeIntervalSince1970: 946684912)
|
||||
transforms.dateMs = transforms.date
|
||||
transforms.dateOptMs = transforms.dateOpt
|
||||
|
||||
let JSON = mapper.toJSON(transforms)
|
||||
let parsedTransforms = mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(parsedTransforms)
|
||||
XCTAssertEqual(parsedTransforms?.date, transforms.date)
|
||||
XCTAssertEqual(parsedTransforms?.dateOpt, transforms.dateOpt)
|
||||
XCTAssertEqual(parsedTransforms?.dateMs, transforms.dateMs)
|
||||
XCTAssertEqual(parsedTransforms?.dateOptMs, transforms.dateOptMs)
|
||||
|
||||
let JSONDateString: [String: Any] = ["date": "946684800", "dateOpt": "946684912",
|
||||
"dateMs": "946684800000", "dateOptMs": "946684912000"]
|
||||
let parsedTransformsDateString = mapper.map(JSON: JSONDateString)
|
||||
|
||||
XCTAssertNotNil(parsedTransformsDateString)
|
||||
XCTAssertEqual(parsedTransforms?.date, parsedTransformsDateString?.date)
|
||||
XCTAssertEqual(parsedTransforms?.dateOpt, parsedTransformsDateString?.dateOpt)
|
||||
XCTAssertEqual(parsedTransforms?.dateMs, parsedTransformsDateString?.dateMs)
|
||||
XCTAssertEqual(parsedTransforms?.dateOptMs, parsedTransformsDateString?.dateOptMs)
|
||||
|
||||
}
|
||||
|
||||
func testISO8601DateTransform() {
|
||||
let transforms = Transforms()
|
||||
transforms.ISO8601Date = Date(timeIntervalSince1970: 1398956159)
|
||||
transforms.ISO8601DateOpt = Date(timeIntervalSince1970: 1398956159)
|
||||
let JSON = mapper.toJSON(transforms)
|
||||
|
||||
let parsedTransforms = mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(parsedTransforms)
|
||||
XCTAssertEqual(parsedTransforms?.ISO8601Date, transforms.ISO8601Date)
|
||||
XCTAssertEqual(parsedTransforms?.ISO8601DateOpt, transforms.ISO8601DateOpt)
|
||||
}
|
||||
|
||||
func testISO8601DateTransformWithInvalidInput() {
|
||||
var JSON: [String: Any] = ["ISO8601Date": ""]
|
||||
let transforms = mapper.map(JSON: JSON)
|
||||
|
||||
XCTAssertNil(transforms?.ISO8601DateOpt)
|
||||
|
||||
JSON["ISO8601Date"] = "incorrect format"
|
||||
|
||||
let transforms2 = mapper.map(JSON: JSON)
|
||||
|
||||
XCTAssertNil(transforms2?.ISO8601DateOpt)
|
||||
}
|
||||
|
||||
func testCustomFormatDateTransform(){
|
||||
let dateString = "2015-03-03T02:36:44"
|
||||
let JSON: [String: Any] = ["customFormateDate": dateString]
|
||||
let transform: Transforms! = mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(transform)
|
||||
|
||||
let JSONOutput = mapper.toJSON(transform)
|
||||
|
||||
XCTAssertEqual(JSONOutput["customFormateDate"] as? String, dateString)
|
||||
}
|
||||
|
||||
func testIntToStringTransformOf() {
|
||||
let intValue = 12345
|
||||
let JSON: [String: Any] = ["intWithString": "\(intValue)"]
|
||||
let transforms = mapper.map(JSON: JSON)
|
||||
|
||||
XCTAssertEqual(transforms?.intWithString, intValue)
|
||||
}
|
||||
|
||||
func testInt64MaxValue() {
|
||||
let transforms = Transforms()
|
||||
transforms.int64Value = INT64_MAX
|
||||
|
||||
let JSON = mapper.toJSON(transforms)
|
||||
|
||||
let parsedTransforms = mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(parsedTransforms)
|
||||
XCTAssertEqual(parsedTransforms?.int64Value, transforms.int64Value)
|
||||
}
|
||||
|
||||
func testURLTranform() {
|
||||
let transforms = Transforms()
|
||||
transforms.URL = URL(string: "http://google.com/image/1234")!
|
||||
transforms.URLOpt = URL(string: "http://google.com/image/1234")
|
||||
transforms.URLWithoutEncoding = URL(string: "http://google.com/image/1234#fragment")!
|
||||
|
||||
let JSON = mapper.toJSON(transforms)
|
||||
|
||||
let parsedTransforms = mapper.map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(parsedTransforms)
|
||||
XCTAssertEqual(parsedTransforms?.URL, transforms.URL)
|
||||
XCTAssertEqual(parsedTransforms?.URLOpt, transforms.URLOpt)
|
||||
XCTAssertEqual(parsedTransforms?.URLWithoutEncoding, transforms.URLWithoutEncoding)
|
||||
}
|
||||
|
||||
func testEnumTransform() {
|
||||
let JSON: [String: Any] = ["firstImageType": "cover", "secondImageType": "thumbnail"]
|
||||
let transforms = mapper.map(JSON: JSON)
|
||||
|
||||
let imageType = Transforms.ImageType.self
|
||||
XCTAssertEqual(transforms?.firstImageType, imageType.Cover)
|
||||
XCTAssertEqual(transforms?.secondImageType, imageType.Thumbnail)
|
||||
}
|
||||
|
||||
func testHexColorTransform() {
|
||||
let JSON: [String: Any] = [
|
||||
"colorRed": "#FF0000",
|
||||
"colorGreenLowercase": "#00FF00",
|
||||
"colorBlueWithoutHash": "0000FF",
|
||||
"color3lenght": "F00",
|
||||
"color4lenght": "F00f",
|
||||
"color8lenght": "ff0000ff"
|
||||
]
|
||||
|
||||
let transform = mapper.map(JSON: JSON)
|
||||
|
||||
XCTAssertEqual(transform?.colorRed, TestHexColor.red)
|
||||
XCTAssertEqual(transform?.colorGreenLowercase, TestHexColor.green)
|
||||
XCTAssertEqual(transform?.colorBlueWithoutHash, TestHexColor.blue)
|
||||
XCTAssertEqual(transform?.color3lenght, TestHexColor.red)
|
||||
XCTAssertEqual(transform?.color4lenght, TestHexColor.red)
|
||||
XCTAssertEqual(transform?.color8lenght, TestHexColor.red)
|
||||
|
||||
let JSONOutput = mapper.toJSON(transform!)
|
||||
|
||||
XCTAssertEqual(JSONOutput["colorRed"] as? String, "FF0000")
|
||||
XCTAssertEqual(JSONOutput["colorGreenLowercase"] as? String, "00FF00")
|
||||
XCTAssertEqual(JSONOutput["colorBlueWithoutHash"] as? String, "#0000FF") // prefixToJSON = true
|
||||
XCTAssertEqual(JSONOutput["color3lenght"] as? String, "FF0000")
|
||||
XCTAssertEqual(JSONOutput["color4lenght"] as? String, "FF0000")
|
||||
XCTAssertEqual(JSONOutput["color8lenght"] as? String, "FF0000FF") // alphaToJSON = true
|
||||
}
|
||||
}
|
||||
|
||||
class Transforms: Mappable {
|
||||
|
||||
internal enum ImageType: String {
|
||||
case Cover = "cover"
|
||||
case Thumbnail = "thumbnail"
|
||||
}
|
||||
|
||||
var date = Date()
|
||||
var dateOpt: Date?
|
||||
|
||||
var dateMs = Date()
|
||||
var dateOptMs: Date?
|
||||
|
||||
var ISO8601Date: Date = Date()
|
||||
var ISO8601DateOpt: Date?
|
||||
|
||||
var customFormatDate = Date()
|
||||
var customFormatDateOpt: Date?
|
||||
|
||||
var URL = Foundation.URL(string: "")
|
||||
var URLOpt: Foundation.URL?
|
||||
var URLWithoutEncoding = Foundation.URL(string: "")
|
||||
|
||||
var intWithString: Int = 0
|
||||
|
||||
var int64Value: Int64 = 0
|
||||
|
||||
var firstImageType: ImageType?
|
||||
var secondImageType: ImageType?
|
||||
|
||||
var colorRed: TestHexColor?
|
||||
var colorGreenLowercase: TestHexColor?
|
||||
var colorBlueWithoutHash: TestHexColor?
|
||||
var color3lenght: TestHexColor?
|
||||
var color4lenght: TestHexColor?
|
||||
var color8lenght: TestHexColor?
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
date <- (map["date"], DateTransform())
|
||||
dateOpt <- (map["dateOpt"], DateTransform())
|
||||
|
||||
dateMs <- (map["dateMs"], DateTransform(unit: .milliseconds))
|
||||
dateOptMs <- (map["dateOptMs"], DateTransform(unit: .milliseconds))
|
||||
|
||||
ISO8601Date <- (map["ISO8601Date"], ISO8601DateTransform())
|
||||
ISO8601DateOpt <- (map["ISO8601DateOpt"], ISO8601DateTransform())
|
||||
|
||||
customFormatDate <- (map["customFormateDate"], CustomDateFormatTransform(formatString: "yyyy-MM-dd'T'HH:mm:ss"))
|
||||
customFormatDateOpt <- (map["customFormateDateOpt"], CustomDateFormatTransform(formatString: "yyyy-MM-dd'T'HH:mm:ss"))
|
||||
|
||||
URL <- (map["URL"], URLTransform())
|
||||
URLOpt <- (map["URLOpt"], URLTransform())
|
||||
URLWithoutEncoding <- (map["URLWithoutEncoding"], URLTransform(shouldEncodeURLString: false))
|
||||
|
||||
intWithString <- (map["intWithString"], TransformOf<Int, String>(fromJSON: { $0 == nil ? nil : Int($0!) }, toJSON: { $0.map { String($0) } }))
|
||||
int64Value <- (map["int64Value"], TransformOf<Int64, NSNumber>(fromJSON: { $0?.int64Value }, toJSON: { $0.map { NSNumber(value: $0) } }))
|
||||
|
||||
firstImageType <- (map["firstImageType"], EnumTransform<ImageType>())
|
||||
secondImageType <- (map["secondImageType"], EnumTransform<ImageType>())
|
||||
|
||||
colorRed <- (map["colorRed"], HexColorTransform())
|
||||
colorGreenLowercase <- (map["colorGreenLowercase"], HexColorTransform())
|
||||
colorBlueWithoutHash <- (map["colorBlueWithoutHash"], HexColorTransform(prefixToJSON: true))
|
||||
color3lenght <- (map["color3lenght"], HexColorTransform())
|
||||
color4lenght <- (map["color4lenght"], HexColorTransform())
|
||||
color8lenght <- (map["color8lenght"], HexColorTransform(alphaToJSON: true))
|
||||
}
|
||||
}
|
||||
|
|
@ -1,71 +0,0 @@
|
|||
//
|
||||
// NSDataTransformTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Yagrushkin, Evgeny on 8/30/16.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class DataTransformTests: XCTestCase {
|
||||
|
||||
let mapper = Mapper<DataType>()
|
||||
|
||||
func testDataTransform() {
|
||||
|
||||
let dataLength = 20
|
||||
let bytes = malloc(dataLength)
|
||||
|
||||
let data = Data(bytes: bytes!, count: dataLength)
|
||||
let dataString = data.base64EncodedString()
|
||||
let JSONString = "{\"data\" : \"\(dataString)\"}"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.stringData, dataString)
|
||||
XCTAssertEqual(mappedObject?.data, data)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class DataType: Mappable {
|
||||
|
||||
var data: Data?
|
||||
var stringData: String?
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
stringData <- map["data"]
|
||||
data <- (map["data"], DataTransform())
|
||||
}
|
||||
}
|
|
@ -1,110 +0,0 @@
|
|||
//
|
||||
// DictionaryTransformTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Milen Halachev on 7/20/16.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class DictionaryTransformTests: XCTestCase {
|
||||
|
||||
func testDictionaryTransform() {
|
||||
|
||||
let JSON = "{\"dictionary\":{\"1\":{\"foo\":\"uno\",\"bar\":1},\"two\":{\"foo\":\"dve\",\"bar\":2},\"bar\":{\"foo\":\"bar\",\"bar\":777}}}"
|
||||
|
||||
guard let result = DictionaryTransformTestsObject(JSONString: JSON) else {
|
||||
|
||||
XCTFail("Unable to parse the JSON")
|
||||
return
|
||||
}
|
||||
|
||||
XCTAssertEqual(result.dictionary.count, 3)
|
||||
|
||||
XCTAssertEqual(result.dictionary[.One]?.foo, "uno")
|
||||
XCTAssertEqual(result.dictionary[.One]?.bar, 1)
|
||||
|
||||
XCTAssertEqual(result.dictionary[.Two]?.foo, "dve")
|
||||
XCTAssertEqual(result.dictionary[.Two]?.bar, 2)
|
||||
|
||||
XCTAssertEqual(result.dictionary[.Foo]?.foo, "bar")
|
||||
XCTAssertEqual(result.dictionary[.Foo]?.bar, 777)
|
||||
}
|
||||
}
|
||||
|
||||
class DictionaryTransformTestsObject: Mappable {
|
||||
|
||||
var dictionary: [MyKey: MyValue] = [:]
|
||||
|
||||
required init?(map: Map) {
|
||||
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
|
||||
self.dictionary <- (map["dictionary"], DictionaryTransform<MyKey, MyValue>())
|
||||
}
|
||||
}
|
||||
|
||||
extension DictionaryTransformTestsObject {
|
||||
|
||||
enum MyKey: String {
|
||||
|
||||
case One = "1"
|
||||
case Two = "two"
|
||||
case Foo = "bar"
|
||||
}
|
||||
}
|
||||
|
||||
extension DictionaryTransformTestsObject {
|
||||
|
||||
class MyValue: Mappable {
|
||||
|
||||
var foo: String
|
||||
var bar: Int
|
||||
|
||||
required init?(map: Map) {
|
||||
|
||||
self.foo = "__foo"
|
||||
self.bar = self.foo.hash
|
||||
|
||||
self.mapping(map: map)
|
||||
|
||||
guard self.foo != "__foo" && self.bar != self.foo.hash else {
|
||||
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
|
||||
self.foo <- map["foo"]
|
||||
self.bar <- map["bar"]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -1,204 +0,0 @@
|
|||
//
|
||||
// GenericObjectsTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2016-09-26.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class GenericObjectsTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testSubclass() {
|
||||
let object = Subclass()
|
||||
object.base = "base var"
|
||||
object.sub = "sub var"
|
||||
|
||||
let json = Mapper().toJSON(object)
|
||||
let parsedObject = Mapper<Subclass>().map(JSON: json)
|
||||
|
||||
XCTAssertEqual(object.base, parsedObject?.base)
|
||||
XCTAssertEqual(object.sub, parsedObject?.sub)
|
||||
}
|
||||
|
||||
func testGenericSubclass() {
|
||||
let object = GenericSubclass<String>()
|
||||
object.base = "base var"
|
||||
object.sub = "sub var"
|
||||
|
||||
let json = Mapper().toJSON(object)
|
||||
let parsedObject = Mapper<GenericSubclass<String>>().map(JSON: json)
|
||||
|
||||
XCTAssertEqual(object.base, parsedObject?.base)
|
||||
XCTAssertEqual(object.sub, parsedObject?.sub)
|
||||
}
|
||||
|
||||
func testSubclassWithGenericArrayInSuperclass() {
|
||||
let JSONString = "{\"genericItems\":[{\"value\":\"value0\"}, {\"value\":\"value1\"}]}"
|
||||
|
||||
let parsedObject = Mapper<SubclassWithGenericArrayInSuperclass<AnyObject>>().map(JSONString: JSONString)
|
||||
|
||||
let genericItems = parsedObject?.genericItems
|
||||
|
||||
XCTAssertNotNil(genericItems)
|
||||
XCTAssertEqual(genericItems?[0].value, "value0")
|
||||
XCTAssertEqual(genericItems?[1].value, "value1")
|
||||
}
|
||||
|
||||
|
||||
func testMappingAGenericObject(){
|
||||
let code: Int = 22
|
||||
let JSONString = "{\"result\":{\"code\":\(code)}}"
|
||||
|
||||
let response = Mapper<Response<Status>>().map(JSONString: JSONString)
|
||||
|
||||
let status = response?.result?.status
|
||||
|
||||
XCTAssertNotNil(status)
|
||||
XCTAssertEqual(status, code)
|
||||
}
|
||||
|
||||
|
||||
func testMappingAGenericObjectViaMappableExtension(){
|
||||
let code: Int = 22
|
||||
let JSONString = "{\"result\":{\"code\":\(code)}}"
|
||||
|
||||
let response = Response<Status>(JSONString: JSONString)
|
||||
|
||||
let status = response?.result?.status
|
||||
|
||||
XCTAssertNotNil(status)
|
||||
XCTAssertEqual(status, code)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class Base: Mappable {
|
||||
|
||||
var base: String?
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
base <- map["base"]
|
||||
}
|
||||
}
|
||||
|
||||
class Subclass: Base {
|
||||
|
||||
var sub: String?
|
||||
|
||||
override init(){
|
||||
super.init()
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
super.init(map: map)
|
||||
}
|
||||
|
||||
override func mapping(map: Map) {
|
||||
super.mapping(map: map)
|
||||
|
||||
sub <- map["sub"]
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
class GenericSubclass<T>: Base {
|
||||
|
||||
var sub: String?
|
||||
|
||||
override init(){
|
||||
super.init()
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
super.init(map: map)
|
||||
}
|
||||
|
||||
override func mapping(map: Map) {
|
||||
super.mapping(map: map)
|
||||
|
||||
sub <- map["sub"]
|
||||
}
|
||||
}
|
||||
|
||||
class WithGenericArray<T: Mappable>: Mappable {
|
||||
var genericItems: [T]?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
genericItems <- map["genericItems"]
|
||||
}
|
||||
}
|
||||
|
||||
class ConcreteItem: Mappable {
|
||||
var value: String?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
value <- map["value"]
|
||||
}
|
||||
}
|
||||
|
||||
class SubclassWithGenericArrayInSuperclass<Unused>: WithGenericArray<ConcreteItem> {
|
||||
required init?(map: Map){
|
||||
super.init(map: map)
|
||||
}
|
||||
}
|
||||
|
||||
class Response<T: Mappable>: Mappable {
|
||||
var result: T?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
result <- map["result"]
|
||||
}
|
||||
}
|
|
@ -1,79 +0,0 @@
|
|||
//
|
||||
// IgnoreNilTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2016-06-06.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class IgnoreNilTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testIgnoreNullField(){
|
||||
let name = "Tristan"
|
||||
var user = User()
|
||||
user.name = name
|
||||
|
||||
let JSON = "{\"name\" : null}"
|
||||
user = Mapper<User>().map(JSONString: JSON, toObject: user)
|
||||
|
||||
XCTAssertEqual(user.name, name)
|
||||
}
|
||||
|
||||
func testIgnoreNilField(){
|
||||
let name = "Tristan"
|
||||
var user = User()
|
||||
user.name = name
|
||||
|
||||
let JSON = "{\"name\" : nil}"
|
||||
user = Mapper<User>().map(JSONString: JSON, toObject: user)
|
||||
|
||||
XCTAssertEqual(user.name, name)
|
||||
}
|
||||
|
||||
private class User: Mappable {
|
||||
var name: String?
|
||||
|
||||
init(){}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map){
|
||||
name <- map["name", ignoreNil: true]
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,642 +0,0 @@
|
|||
//
|
||||
// ImmutableTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Suyeol Jeon on 23/09/2016.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class ImmutableObjectTests: XCTestCase {
|
||||
let JSON: [String: Any] = [
|
||||
|
||||
// Basic types
|
||||
"prop1": "Immutable!",
|
||||
"prop2": 255,
|
||||
"prop3": true,
|
||||
// prop4 has a default value
|
||||
|
||||
// String
|
||||
"prop5": "prop5",
|
||||
"prop6": "prop6",
|
||||
"prop7": "prop7",
|
||||
|
||||
// [String]
|
||||
"prop8": ["prop8"],
|
||||
"prop9": ["prop9"],
|
||||
"prop10": ["prop10"],
|
||||
|
||||
// [String: String]
|
||||
"prop11": ["key": "prop11"],
|
||||
"prop12": ["key": "prop12"],
|
||||
"prop13": ["key": "prop13"],
|
||||
|
||||
// Base
|
||||
"prop14": ["base": "prop14"],
|
||||
"prop15": ["base": "prop15"],
|
||||
"prop16": ["base": "prop16"],
|
||||
|
||||
// [Base]
|
||||
"prop17": [["base": "prop17"]],
|
||||
"prop18": [["base": "prop18"]],
|
||||
"prop19": [["base": "prop19"]],
|
||||
|
||||
// [String: Base]
|
||||
"prop20": ["key": ["base": "prop20"]],
|
||||
"prop21": ["key": ["base": "prop21"]],
|
||||
"prop22": ["key": ["base": "prop22"]],
|
||||
|
||||
// Optional with immutables
|
||||
"prop23": "Optional",
|
||||
"prop24": 255,
|
||||
"prop25": true,
|
||||
"prop26": 255.0,
|
||||
|
||||
// RawRepresentable
|
||||
"prop27a": NSNumber(value: 0),
|
||||
"prop27b": NSNumber(value: 1000),
|
||||
"prop27c": [NSNumber(value: 0), NSNumber(value: 1000)],
|
||||
|
||||
"prop28a": Int(0),
|
||||
"prop28b": Int(255),
|
||||
"prop28c": [Int(0), Int(255)],
|
||||
|
||||
"prop29a": Double(0),
|
||||
"prop29b": Double(100),
|
||||
"prop29c": [Double(0), Double(100)],
|
||||
|
||||
"prop30a": Float(0),
|
||||
"prop30b": Float(100),
|
||||
"prop30c": [Float(0), Float(100)],
|
||||
|
||||
"prop31a": "String A",
|
||||
"prop31b": "String B",
|
||||
"prop31c": ["String A", "String B"],
|
||||
|
||||
// [[String]]
|
||||
"prop32": [["prop32"]],
|
||||
"prop33": [["prop33"]],
|
||||
"prop34": [["prop34"]],
|
||||
|
||||
// [[Base]]
|
||||
"prop35": [[["base": "prop35"]]],
|
||||
"prop36": [[["base": "prop36"]]],
|
||||
"prop37": [[["base": "prop37"]]],
|
||||
|
||||
"non.nested->key": "string",
|
||||
"nested": [
|
||||
"int": 123,
|
||||
"string": "hello",
|
||||
"array": ["a", "b", "c"],
|
||||
"dictionary": ["a": 10, "b": 20, "c": 30],
|
||||
],
|
||||
"com.tristanhimmelman.ObjectMapper.nested": [
|
||||
"com.tristanhimmelman.ObjectMapper.int": 123,
|
||||
"com.tristanhimmelman.ObjectMapper.string": "hello",
|
||||
"array": ["a", "b", "c"],
|
||||
"dictionary": ["a": 10, "b": 20, "c": 30],
|
||||
]
|
||||
]
|
||||
|
||||
func testImmutableMappable() {
|
||||
let mapper = Mapper<Struct>()
|
||||
|
||||
let immutable: Struct = try! mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(immutable)
|
||||
XCTAssertEqual(immutable.prop1, "Immutable!")
|
||||
XCTAssertEqual(immutable.prop2, 255)
|
||||
XCTAssertEqual(immutable.prop3, true)
|
||||
XCTAssertEqual(immutable.prop4, .greatestFiniteMagnitude)
|
||||
|
||||
XCTAssertEqual(immutable.prop5, "prop5_TRANSFORMED")
|
||||
XCTAssertEqual(immutable.prop6, "prop6_TRANSFORMED")
|
||||
XCTAssertEqual(immutable.prop7, "prop7_TRANSFORMED")
|
||||
|
||||
XCTAssertEqual(immutable.prop8, ["prop8_TRANSFORMED"])
|
||||
XCTAssertEqual(immutable.prop9!, ["prop9_TRANSFORMED"])
|
||||
XCTAssertEqual(immutable.prop10, ["prop10_TRANSFORMED"])
|
||||
|
||||
XCTAssertEqual(immutable.prop11, ["key": "prop11_TRANSFORMED"])
|
||||
XCTAssertEqual(immutable.prop12!, ["key": "prop12_TRANSFORMED"])
|
||||
XCTAssertEqual(immutable.prop13, ["key": "prop13_TRANSFORMED"])
|
||||
|
||||
XCTAssertEqual(immutable.prop14.base, "prop14")
|
||||
XCTAssertEqual(immutable.prop15?.base, "prop15")
|
||||
XCTAssertEqual(immutable.prop16.base, "prop16")
|
||||
|
||||
XCTAssertEqual(immutable.prop17[0].base, "prop17")
|
||||
XCTAssertEqual(immutable.prop18![0].base, "prop18")
|
||||
XCTAssertEqual(immutable.prop19[0].base, "prop19")
|
||||
|
||||
XCTAssertEqual(immutable.prop20["key"]!.base, "prop20")
|
||||
XCTAssertEqual(immutable.prop21!["key"]!.base, "prop21")
|
||||
XCTAssertEqual(immutable.prop22["key"]!.base, "prop22")
|
||||
|
||||
XCTAssertEqual(immutable.prop23!, "Optional")
|
||||
XCTAssertEqual(immutable.prop24!, 255)
|
||||
XCTAssertEqual(immutable.prop25!, true)
|
||||
XCTAssertEqual(immutable.prop26!, 255.0)
|
||||
|
||||
XCTAssertEqual(immutable.prop27a.rawValue, Int64Enum.a.rawValue)
|
||||
XCTAssertEqual(immutable.prop27b.rawValue, Int64Enum.b.rawValue)
|
||||
XCTAssertEqual(immutable.prop27c, [Int64Enum.a, Int64Enum.b])
|
||||
|
||||
XCTAssertEqual(immutable.prop28a.rawValue, IntEnum.a.rawValue)
|
||||
XCTAssertEqual(immutable.prop28b.rawValue, IntEnum.b.rawValue)
|
||||
XCTAssertEqual(immutable.prop28c, [IntEnum.a, IntEnum.b])
|
||||
|
||||
XCTAssertEqual(immutable.prop29a.rawValue, DoubleEnum.a.rawValue)
|
||||
XCTAssertEqual(immutable.prop29b.rawValue, DoubleEnum.b.rawValue)
|
||||
XCTAssertEqual(immutable.prop29c, [DoubleEnum.a, DoubleEnum.b])
|
||||
|
||||
XCTAssertEqual(immutable.prop30a.rawValue, FloatEnum.a.rawValue)
|
||||
XCTAssertEqual(immutable.prop30b.rawValue, FloatEnum.b.rawValue)
|
||||
XCTAssertEqual(immutable.prop30c, [FloatEnum.a, FloatEnum.b])
|
||||
|
||||
XCTAssertEqual(immutable.prop31a.rawValue, StringEnum.A.rawValue)
|
||||
XCTAssertEqual(immutable.prop31b.rawValue, StringEnum.B.rawValue)
|
||||
XCTAssertEqual(immutable.prop31c, [StringEnum.A, StringEnum.B])
|
||||
|
||||
XCTAssertEqual(immutable.prop32[0][0], "prop32_TRANSFORMED")
|
||||
XCTAssertEqual(immutable.prop33![0][0], "prop33_TRANSFORMED")
|
||||
XCTAssertEqual(immutable.prop34[0][0], "prop34_TRANSFORMED")
|
||||
|
||||
XCTAssertEqual(immutable.prop35[0][0].base, "prop35")
|
||||
XCTAssertEqual(immutable.prop36![0][0].base, "prop36")
|
||||
XCTAssertEqual(immutable.prop37[0][0].base, "prop37")
|
||||
|
||||
XCTAssertEqual(immutable.nonnestedString, "string")
|
||||
|
||||
XCTAssertEqual(immutable.nestedInt, 123)
|
||||
XCTAssertEqual(immutable.nestedString, "hello")
|
||||
XCTAssertEqual(immutable.nestedArray, ["a", "b", "c"])
|
||||
XCTAssertEqual(immutable.nestedDictionary, ["a": 10, "b": 20, "c": 30])
|
||||
|
||||
XCTAssertEqual(immutable.delimiterNestedInt, 123)
|
||||
XCTAssertEqual(immutable.delimiterNestedString, "hello")
|
||||
XCTAssertEqual(immutable.delimiterNestedArray, ["a", "b", "c"])
|
||||
XCTAssertEqual(immutable.delimiterNestedDictionary, ["a": 10, "b": 20, "c": 30])
|
||||
|
||||
let JSON2: [String: Any] = [ "prop1": "prop1", "prop2": NSNull() ]
|
||||
let immutable2 = try? mapper.map(JSON: JSON2)
|
||||
XCTAssertNil(immutable2)
|
||||
|
||||
// TODO: ImmutableMappable to JSON
|
||||
let JSONFromObject = mapper.toJSON(immutable)
|
||||
let objectFromJSON = try? mapper.map(JSON: JSONFromObject)
|
||||
XCTAssertNotNil(objectFromJSON)
|
||||
assertImmutableObjectsEqual(objectFromJSON!, immutable)
|
||||
}
|
||||
|
||||
func testMappingFromArray() {
|
||||
let JSONArray: [[String: Any]] = [JSON]
|
||||
|
||||
let array: [Struct] = try! Mapper<Struct>().mapArray(JSONArray: JSONArray)
|
||||
XCTAssertNotNil(array.first)
|
||||
}
|
||||
|
||||
func testMappingFromDictionary() {
|
||||
let JSONDictionary: [String: [String: Any]] = [
|
||||
"key1": JSON,
|
||||
"key2": JSON,
|
||||
]
|
||||
|
||||
let dictionary: [String: Struct] = try! Mapper<Struct>().mapDictionary(JSON: JSONDictionary)
|
||||
XCTAssertNotNil(dictionary.first)
|
||||
XCTAssertEqual(dictionary.count, 2)
|
||||
XCTAssertEqual(Set(dictionary.keys), Set(["key1", "key2"]))
|
||||
}
|
||||
|
||||
func testMappingFromDictionary_empty() {
|
||||
let JSONDictionary: [String: [String: Any]] = [:]
|
||||
|
||||
let dictionary: [String: Struct] = try! Mapper<Struct>().mapDictionary(JSON: JSONDictionary)
|
||||
XCTAssertTrue(dictionary.isEmpty)
|
||||
}
|
||||
|
||||
func testMappingFromDictionary_throws() {
|
||||
let JSONDictionary: [String: [String: Any]] = [
|
||||
"key1": JSON,
|
||||
"key2": ["invalid": "dictionary"],
|
||||
]
|
||||
|
||||
XCTAssertThrowsError(try Mapper<Struct>().mapDictionary(JSON: JSONDictionary))
|
||||
}
|
||||
|
||||
func testMappingFromDictionaryOfArrays() {
|
||||
let JSONDictionary: [String: [[String: Any]]] = [
|
||||
"key1": [JSON, JSON],
|
||||
"key2": [JSON],
|
||||
"key3": [],
|
||||
]
|
||||
|
||||
let dictionary: [String: [Struct]] = try! Mapper<Struct>().mapDictionaryOfArrays(JSON: JSONDictionary)
|
||||
XCTAssertNotNil(dictionary.first)
|
||||
XCTAssertEqual(dictionary.count, 3)
|
||||
XCTAssertEqual(Set(dictionary.keys), Set(["key1", "key2", "key3"]))
|
||||
XCTAssertEqual(dictionary["key1"]?.count, 2)
|
||||
XCTAssertEqual(dictionary["key2"]?.count, 1)
|
||||
XCTAssertEqual(dictionary["key3"]?.count, 0)
|
||||
}
|
||||
|
||||
func testMappingFromDictionaryOfArrays_empty() {
|
||||
let JSONDictionary: [String: [[String: Any]]] = [:]
|
||||
|
||||
let dictionary: [String: [Struct]] = try! Mapper<Struct>().mapDictionaryOfArrays(JSON: JSONDictionary)
|
||||
XCTAssertTrue(dictionary.isEmpty)
|
||||
}
|
||||
|
||||
func testMappingFromDictionaryOfArrays_throws() {
|
||||
let JSONDictionary: [String: [[String: Any]]] = [
|
||||
"key1": [JSON],
|
||||
"key2": [["invalid": "dictionary"]],
|
||||
]
|
||||
|
||||
XCTAssertThrowsError(try Mapper<Struct>().mapDictionaryOfArrays(JSON: JSONDictionary))
|
||||
}
|
||||
|
||||
func testMappingArrayOfArrays() {
|
||||
let JSONArray: [[[String: Any]]] = [
|
||||
[JSON, JSON],
|
||||
[JSON],
|
||||
[],
|
||||
]
|
||||
let array: [[Struct]] = try! Mapper<Struct>().mapArrayOfArrays(JSONObject: JSONArray)
|
||||
XCTAssertNotNil(array.first)
|
||||
XCTAssertEqual(array.count, 3)
|
||||
XCTAssertEqual(array[0].count, 2)
|
||||
XCTAssertEqual(array[1].count, 1)
|
||||
XCTAssertEqual(array[2].count, 0)
|
||||
}
|
||||
|
||||
func testMappingArrayOfArrays_empty() {
|
||||
let JSONArray: [[[String: Any]]] = []
|
||||
let array: [[Struct]] = try! Mapper<Struct>().mapArrayOfArrays(JSONObject: JSONArray)
|
||||
XCTAssertTrue(array.isEmpty)
|
||||
}
|
||||
|
||||
func testMappingArrayOfArrays_throws() {
|
||||
let JSONArray: [[[String: Any]]] = [
|
||||
[JSON],
|
||||
[["invalid": "dictionary"]],
|
||||
]
|
||||
XCTAssertThrowsError(try Mapper<Struct>().mapArrayOfArrays(JSONObject: JSONArray))
|
||||
}
|
||||
|
||||
func testAsPropertyOfMappable() {
|
||||
struct ImmutableObject: ImmutableMappable {
|
||||
let value: String
|
||||
init(map: Map) throws {
|
||||
self.value = try map.value("value")
|
||||
}
|
||||
}
|
||||
|
||||
struct Object: Mappable {
|
||||
var immutable: ImmutableObject!
|
||||
init?(map: Map) {}
|
||||
mutating func mapping(map: Map) {
|
||||
self.immutable <- map["immutable"]
|
||||
}
|
||||
}
|
||||
|
||||
let json: [String: Any] = [
|
||||
"immutable": [
|
||||
"value": "Hello"
|
||||
]
|
||||
]
|
||||
let object = Mapper<Object>().map(JSON: json)
|
||||
XCTAssertEqual(object?.immutable?.value, "Hello")
|
||||
}
|
||||
|
||||
func testAsPropertyOfOptionalImmutableMappable() {
|
||||
struct ImmutableObject: ImmutableMappable {
|
||||
let value: String?
|
||||
init(map: Map) throws {
|
||||
self.value = try map.value("value")
|
||||
}
|
||||
}
|
||||
|
||||
enum RawRepresentableEnum: String {
|
||||
case world
|
||||
}
|
||||
struct Object: ImmutableMappable {
|
||||
let immutable: ImmutableObject?
|
||||
let enumValue: RawRepresentableEnum?
|
||||
init(map: Map) throws {
|
||||
self.immutable = try map.value("immutable")
|
||||
self.enumValue = try map.value("enum")
|
||||
}
|
||||
}
|
||||
|
||||
let json: [String: Any] = [
|
||||
"immutable": [
|
||||
"value": "Hello"
|
||||
],
|
||||
"enum": "world"
|
||||
]
|
||||
do {
|
||||
let object = try Mapper<Object>().map(JSON: json)
|
||||
XCTAssertEqual(object.immutable?.value, "Hello")
|
||||
XCTAssertEqual(object.enumValue, .world)
|
||||
} catch {
|
||||
XCTFail()
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
struct Struct {
|
||||
let prop1: String
|
||||
let prop2: Int
|
||||
let prop3: Bool
|
||||
let prop4: Double
|
||||
|
||||
let prop5: String
|
||||
let prop6: String?
|
||||
let prop7: String!
|
||||
|
||||
let prop8: [String]
|
||||
let prop9: [String]?
|
||||
let prop10: [String]!
|
||||
|
||||
let prop11: [String: String]
|
||||
let prop12: [String: String]?
|
||||
let prop13: [String: String]!
|
||||
|
||||
let prop14: Base
|
||||
let prop15: Base?
|
||||
let prop16: Base!
|
||||
|
||||
let prop17: [Base]
|
||||
let prop18: [Base]?
|
||||
let prop19: [Base]!
|
||||
|
||||
let prop20: [String: Base]
|
||||
let prop21: [String: Base]?
|
||||
let prop22: [String: Base]!
|
||||
|
||||
// Optionals
|
||||
var prop23: String?
|
||||
var prop24: Int?
|
||||
var prop25: Bool?
|
||||
var prop26: Double?
|
||||
|
||||
// RawRepresentable
|
||||
let prop27a: Int64Enum
|
||||
let prop27b: Int64Enum
|
||||
let prop27c: [Int64Enum]
|
||||
|
||||
let prop28a: IntEnum
|
||||
let prop28b: IntEnum
|
||||
let prop28c: [IntEnum]
|
||||
|
||||
let prop29a: DoubleEnum
|
||||
let prop29b: DoubleEnum
|
||||
let prop29c: [DoubleEnum]
|
||||
|
||||
let prop30a: FloatEnum
|
||||
let prop30b: FloatEnum
|
||||
let prop30c: [FloatEnum]
|
||||
|
||||
let prop31a: StringEnum
|
||||
let prop31b: StringEnum
|
||||
let prop31c: [StringEnum]
|
||||
|
||||
let prop32: [[String]]
|
||||
let prop33: [[String]]?
|
||||
let prop34: [[String]]!
|
||||
|
||||
let prop35: [[Base]]
|
||||
let prop36: [[Base]]?
|
||||
let prop37: [[Base]]!
|
||||
|
||||
var nonnestedString: String
|
||||
var nestedInt: Int
|
||||
var nestedString: String
|
||||
var nestedArray: [String]
|
||||
var nestedDictionary: [String: Int]
|
||||
|
||||
var delimiterNestedInt: Int
|
||||
var delimiterNestedString: String
|
||||
var delimiterNestedArray: [String]
|
||||
var delimiterNestedDictionary: [String: Int]
|
||||
}
|
||||
|
||||
extension Struct: ImmutableMappable {
|
||||
init(map: Map) throws {
|
||||
prop1 = try map.value("prop1")
|
||||
prop2 = try map.value("prop2")
|
||||
prop3 = try map.value("prop3")
|
||||
prop4 = (try? map.value("prop4")) ?? .greatestFiniteMagnitude
|
||||
|
||||
prop5 = try map.value("prop5", using: stringTransform)
|
||||
prop6 = try? map.value("prop6", using: stringTransform)
|
||||
prop7 = try? map.value("prop7", using: stringTransform)
|
||||
|
||||
prop8 = try map.value("prop8", using: stringTransform)
|
||||
prop9 = try? map.value("prop9", using: stringTransform)
|
||||
prop10 = try? map.value("prop10", using: stringTransform)
|
||||
|
||||
prop11 = try map.value("prop11", using: stringTransform)
|
||||
prop12 = try? map.value("prop12", using: stringTransform)
|
||||
prop13 = try? map.value("prop13", using: stringTransform)
|
||||
|
||||
prop14 = try map.value("prop14")
|
||||
prop15 = try? map.value("prop15")
|
||||
prop16 = try? map.value("prop16")
|
||||
|
||||
prop17 = try map.value("prop17")
|
||||
prop18 = try? map.value("prop18")
|
||||
prop19 = try? map.value("prop19")
|
||||
|
||||
prop20 = try map.value("prop20")
|
||||
prop21 = try? map.value("prop21")
|
||||
prop22 = try? map.value("prop22")
|
||||
|
||||
prop27a = try map.value("prop27a")
|
||||
prop27b = try map.value("prop27b")
|
||||
prop27c = try map.value("prop27c")
|
||||
|
||||
prop28a = try map.value("prop28a")
|
||||
prop28b = try map.value("prop28b")
|
||||
prop28c = try map.value("prop28c")
|
||||
|
||||
prop29a = try map.value("prop29a")
|
||||
prop29b = try map.value("prop29b")
|
||||
prop29c = try map.value("prop29c")
|
||||
|
||||
prop30a = try map.value("prop30a")
|
||||
prop30b = try map.value("prop30b")
|
||||
prop30c = try map.value("prop30c")
|
||||
|
||||
prop31a = try map.value("prop31a")
|
||||
prop31b = try map.value("prop31b")
|
||||
prop31c = try map.value("prop31c")
|
||||
|
||||
prop32 = try map.value("prop32", using: stringTransform)
|
||||
prop33 = try? map.value("prop33", using: stringTransform)
|
||||
prop34 = try? map.value("prop34", using: stringTransform)
|
||||
|
||||
prop35 = try map.value("prop35")
|
||||
prop36 = try? map.value("prop36")
|
||||
prop37 = try? map.value("prop37")
|
||||
|
||||
nonnestedString = try map.value("non.nested->key", nested: false)
|
||||
|
||||
nestedInt = try map.value("nested.int")
|
||||
nestedString = try map.value("nested.string")
|
||||
nestedArray = try map.value("nested.array")
|
||||
nestedDictionary = try map.value("nested.dictionary")
|
||||
|
||||
delimiterNestedInt = try map.value("com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.int", delimiter: "->")
|
||||
delimiterNestedString = try map.value("com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.string", delimiter: "->")
|
||||
delimiterNestedArray = try map.value("com.tristanhimmelman.ObjectMapper.nested->array", delimiter: "->")
|
||||
delimiterNestedDictionary = try map.value("com.tristanhimmelman.ObjectMapper.nested->dictionary", delimiter: "->")
|
||||
}
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
prop1 >>> map["prop1"]
|
||||
prop2 >>> map["prop2"]
|
||||
prop3 >>> map["prop3"]
|
||||
prop4 >>> map["prop4"]
|
||||
|
||||
prop5 >>> (map["prop5"], stringTransform)
|
||||
prop6 >>> (map["prop6"], stringTransform)
|
||||
prop7 >>> (map["prop7"], stringTransform)
|
||||
|
||||
prop8 >>> (map["prop8"], stringTransform)
|
||||
prop9 >>> (map["prop9"], stringTransform)
|
||||
prop10 >>> (map["prop10"], stringTransform)
|
||||
|
||||
prop11 >>> (map["prop11"], stringTransform)
|
||||
prop12 >>> (map["prop12"], stringTransform)
|
||||
prop13 >>> (map["prop13"], stringTransform)
|
||||
|
||||
prop14 >>> map["prop14"]
|
||||
prop15 >>> map["prop15"]
|
||||
prop16 >>> map["prop16"]
|
||||
|
||||
prop17 >>> map["prop17"]
|
||||
prop18 >>> map["prop18"]
|
||||
prop19 >>> map["prop19"]
|
||||
|
||||
prop20 >>> map["prop20"]
|
||||
prop21 >>> map["prop21"]
|
||||
prop22 >>> map["prop22"]
|
||||
|
||||
prop23 <- map["prop23"]
|
||||
prop24 <- map["prop24"]
|
||||
prop25 <- map["prop25"]
|
||||
prop26 <- map["prop26"]
|
||||
|
||||
prop27a >>> map["prop27a"]
|
||||
prop27b >>> map["prop27b"]
|
||||
prop27c >>> map["prop27c"]
|
||||
|
||||
prop28a >>> map["prop28a"]
|
||||
prop28b >>> map["prop28b"]
|
||||
prop28c >>> map["prop28c"]
|
||||
|
||||
prop29a >>> map["prop29a"]
|
||||
prop29b >>> map["prop29b"]
|
||||
prop29c >>> map["prop29c"]
|
||||
|
||||
prop30a >>> map["prop30a"]
|
||||
prop30b >>> map["prop30b"]
|
||||
prop30c >>> map["prop30c"]
|
||||
|
||||
prop31a >>> map["prop31a"]
|
||||
prop31b >>> map["prop31b"]
|
||||
prop31c >>> map["prop31c"]
|
||||
|
||||
prop32 >>> (map["prop32"], stringTransform)
|
||||
prop33 >>> (map["prop33"], stringTransform)
|
||||
prop34 >>> (map["prop34"], stringTransform)
|
||||
|
||||
prop35 >>> map["prop35"]
|
||||
prop36 >>> map["prop36"]
|
||||
prop37 >>> map["prop37"]
|
||||
|
||||
nonnestedString >>> map["non.nested->key", nested: false]
|
||||
|
||||
nestedInt >>> map["nested.int"]
|
||||
nestedString >>> map["nested.string"]
|
||||
nestedArray >>> map["nested.array"]
|
||||
nestedDictionary >>> map["nested.dictionary"]
|
||||
|
||||
delimiterNestedInt >>> map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.int", delimiter: "->"]
|
||||
delimiterNestedString >>> map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.string", delimiter: "->"]
|
||||
delimiterNestedArray >>> map["com.tristanhimmelman.ObjectMapper.nested->array", delimiter: "->"]
|
||||
delimiterNestedDictionary >>> map["com.tristanhimmelman.ObjectMapper.nested->dictionary", delimiter: "->"]
|
||||
}
|
||||
}
|
||||
|
||||
let stringTransform = TransformOf<String, String>(
|
||||
fromJSON: { (str: String?) -> String? in
|
||||
guard let str = str else {
|
||||
return nil
|
||||
}
|
||||
return "\(str)_TRANSFORMED"
|
||||
},
|
||||
toJSON: { (str: String?) -> String? in
|
||||
return str?.replacingOccurrences(of: "_TRANSFORMED", with: "")
|
||||
}
|
||||
)
|
||||
|
||||
private func assertImmutableObjectsEqual(_ lhs: Struct, _ rhs: Struct) {
|
||||
XCTAssertEqual(lhs.prop1, rhs.prop1)
|
||||
XCTAssertEqual(lhs.prop2, rhs.prop2)
|
||||
XCTAssertEqual(lhs.prop3, rhs.prop3)
|
||||
XCTAssertEqual(lhs.prop4, rhs.prop4)
|
||||
XCTAssertEqual(lhs.prop5, rhs.prop5)
|
||||
XCTAssertEqual(lhs.prop6, rhs.prop6)
|
||||
XCTAssertEqual(lhs.prop7, rhs.prop7)
|
||||
XCTAssertEqual(lhs.prop8, rhs.prop8)
|
||||
XCTAssertEqual(lhs.prop23, rhs.prop23)
|
||||
|
||||
// @hack: compare arrays and objects with their string representation.
|
||||
XCTAssertEqual("\(lhs.prop9 as Optional)", "\(rhs.prop9 as Optional)")
|
||||
XCTAssertEqual("\(String(describing: lhs.prop10))", "\(String(describing: rhs.prop10))")
|
||||
XCTAssertEqual("\(lhs.prop11)", "\(rhs.prop11)")
|
||||
XCTAssertEqual("\(lhs.prop12 as Optional)", "\(rhs.prop12 as Optional)")
|
||||
XCTAssertEqual("\(String(describing: lhs.prop13))", "\(String(describing: rhs.prop13))")
|
||||
XCTAssertEqual("\(lhs.prop14)", "\(rhs.prop14)")
|
||||
XCTAssertEqual("\(lhs.prop15 as Optional)", "\(rhs.prop15 as Optional)")
|
||||
XCTAssertEqual("\(String(describing: lhs.prop16))", "\(String(describing: rhs.prop16))")
|
||||
XCTAssertEqual("\(lhs.prop17)", "\(rhs.prop17)")
|
||||
XCTAssertEqual("\(lhs.prop18 as Optional)", "\(rhs.prop18 as Optional)")
|
||||
XCTAssertEqual("\(String(describing: lhs.prop19))", "\(String(describing: rhs.prop19))")
|
||||
XCTAssertEqual("\(lhs.prop20)", "\(rhs.prop20)")
|
||||
XCTAssertEqual("\(lhs.prop21 as Optional)", "\(rhs.prop21 as Optional)")
|
||||
XCTAssertEqual("\(String(describing: lhs.prop22))", "\(String(describing: rhs.prop22))")
|
||||
XCTAssertEqual("\(lhs.prop32)", "\(rhs.prop32)")
|
||||
XCTAssertEqual("\(lhs.prop33 as Optional)", "\(rhs.prop33 as Optional)")
|
||||
XCTAssertEqual("\(String(describing: lhs.prop34))", "\(String(describing: rhs.prop34))")
|
||||
XCTAssertEqual("\(lhs.prop35)", "\(rhs.prop35)")
|
||||
XCTAssertEqual("\(lhs.prop36 as Optional)", "\(rhs.prop36 as Optional)")
|
||||
XCTAssertEqual("\(String(describing: lhs.prop37))", "\(String(describing: rhs.prop37))")
|
||||
}
|
||||
|
|
@ -1,362 +0,0 @@
|
|||
//
|
||||
// MapContextTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2016-05-10.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class MapContextTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
// MARK: - BaseMappable
|
||||
// MARK: Single
|
||||
func testMappingWithContext() {
|
||||
let JSON = ["name": "Tristan"]
|
||||
let context = Context(shouldMap: true)
|
||||
|
||||
let person = Mapper<Person>(context: context).map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
XCTAssertNotNil(person?.name)
|
||||
}
|
||||
|
||||
func testMappingWithContextViaMappableExtension() {
|
||||
let JSON = ["name": "Tristan"]
|
||||
let context = Context(shouldMap: true)
|
||||
|
||||
let person = Person(JSON: JSON, context: context)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
XCTAssertNotNil(person?.name)
|
||||
}
|
||||
|
||||
func testMappingWithoutContext() {
|
||||
let JSON = ["name": "Tristan"]
|
||||
|
||||
let person = Mapper<Person>().map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
XCTAssertNil(person?.name)
|
||||
}
|
||||
|
||||
// MARK: Nested
|
||||
func testNestedMappingWithContext() {
|
||||
let JSON = ["person": ["name": "Tristan"]]
|
||||
let context = Context(shouldMap: true)
|
||||
|
||||
let nestedPerson = Mapper<NestedPerson>(context: context).map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(nestedPerson)
|
||||
XCTAssertNotNil(nestedPerson?.person?.name)
|
||||
}
|
||||
|
||||
func testNestedMappingWithContextViaMappableExtension() {
|
||||
let JSON = ["person": ["name": "Tristan"]]
|
||||
let context = Context(shouldMap: true)
|
||||
|
||||
let nestedPerson = NestedPerson(JSON: JSON, context: context)
|
||||
|
||||
XCTAssertNotNil(nestedPerson)
|
||||
XCTAssertNotNil(nestedPerson?.person?.name)
|
||||
}
|
||||
|
||||
func testNestedMappingWithoutContext() {
|
||||
let JSON = ["person": ["name": "Tristan"]]
|
||||
|
||||
let nestedPerson = Mapper<NestedPerson>().map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(nestedPerson)
|
||||
XCTAssertNil(nestedPerson?.person?.name)
|
||||
}
|
||||
|
||||
// MARK: Array
|
||||
func testArrayMappingWithContext() {
|
||||
let JSON = ["persons": [["name": "Tristan"], ["name": "Anton"]]]
|
||||
let context = Context(shouldMap: true)
|
||||
|
||||
let person = Mapper<PersonList>(context: context).map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
XCTAssertNotNil(person?.persons)
|
||||
}
|
||||
|
||||
func testArrayMappingWithContextViaMappableExtension() {
|
||||
let JSON = ["persons": [["name": "Tristan"], ["name": "Anton"]]]
|
||||
let context = Context(shouldMap: true)
|
||||
|
||||
let person = PersonList(JSON: JSON, context: context)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
XCTAssertNotNil(person?.persons)
|
||||
}
|
||||
|
||||
func testArrayMappingWithoutContext() {
|
||||
let JSON = ["persons": [["name": "Tristan"], ["name": "Anton"]]]
|
||||
|
||||
let person = Mapper<PersonList>().map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
XCTAssertNil(person?.persons)
|
||||
}
|
||||
|
||||
// MARK: ImmutableMappable
|
||||
// MARK: Single
|
||||
func testImmutableMappingWithContext() {
|
||||
let JSON = ["name": "Anton"]
|
||||
let context = ImmutableContext(isDeveloper: true)
|
||||
|
||||
let person = try? Mapper<ImmutablePerson>(context: context).map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
|
||||
XCTAssertEqual(person?.isDeveloper ?? !context.isDeveloper, context.isDeveloper)
|
||||
}
|
||||
|
||||
func testImmutableMappingWithContextViaMappableExtension() {
|
||||
let JSON = ["name": "Anton"]
|
||||
let context = ImmutableContext(isDeveloper: true)
|
||||
|
||||
let person = try? ImmutablePerson(JSON: JSON, context: context)
|
||||
|
||||
XCTAssertNotNil(person)
|
||||
XCTAssertEqual(person?.isDeveloper ?? !context.isDeveloper, context.isDeveloper)
|
||||
}
|
||||
|
||||
func testImmutableMappingWithoutContext() {
|
||||
let JSON = ["name": "Anton"]
|
||||
|
||||
do {
|
||||
let _ = try Mapper<ImmutablePerson>().map(JSON: JSON)
|
||||
} catch ImmutablePersonMappingError.contextAbsense {
|
||||
// Empty
|
||||
} catch {
|
||||
XCTFail()
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: Nested
|
||||
func testNestedImmutableMappingWithContext() {
|
||||
let JSON = ["person": ["name": "Anton"]]
|
||||
let context = ImmutableContext(isDeveloper: true)
|
||||
|
||||
let nestedPerson = try? Mapper<ImmutableNestedPerson>(context: context).map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(nestedPerson)
|
||||
XCTAssertEqual(nestedPerson?.person.isDeveloper ?? !context.isDeveloper, context.isDeveloper)
|
||||
}
|
||||
|
||||
func testNestedImmutableMappingWithContextViaMappableExtension() {
|
||||
let JSON = ["person": ["name": "Anton"]]
|
||||
let context = ImmutableContext(isDeveloper: true)
|
||||
|
||||
let nestedPerson = try? ImmutableNestedPerson(JSON: JSON, context: context)
|
||||
|
||||
XCTAssertNotNil(nestedPerson)
|
||||
XCTAssertEqual(nestedPerson?.person.isDeveloper ?? !context.isDeveloper, context.isDeveloper)
|
||||
}
|
||||
|
||||
func testNestedImmutableMappingWithoutContext() {
|
||||
let JSON = ["person": ["name": "Anton"]]
|
||||
|
||||
do {
|
||||
let _ = try Mapper<ImmutableNestedPerson>().map(JSON: JSON)
|
||||
} catch ImmutablePersonMappingError.contextAbsense {
|
||||
return
|
||||
} catch {
|
||||
XCTFail()
|
||||
}
|
||||
|
||||
XCTFail()
|
||||
}
|
||||
|
||||
// MARK: Array
|
||||
func testArrayImmutableMappingWithContext() {
|
||||
let JSON = ["persons": [["name": "Tristan"], ["name": "Anton"]]]
|
||||
let context = ImmutableContext(isDeveloper: true)
|
||||
|
||||
let personList = try? Mapper<ImmutablePersonList>(context: context).map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(personList)
|
||||
|
||||
personList?.persons.forEach { person in
|
||||
XCTAssertEqual(person.isDeveloper, context.isDeveloper)
|
||||
}
|
||||
}
|
||||
|
||||
func testArrayImmutableMappingWithContextViaMappableExtension() {
|
||||
let JSON = ["persons": [["name": "Tristan"], ["name": "Anton"]]]
|
||||
let context = ImmutableContext(isDeveloper: true)
|
||||
|
||||
let personList = try? ImmutablePersonList(JSON: JSON, context: context)
|
||||
|
||||
XCTAssertNotNil(personList)
|
||||
|
||||
personList?.persons.forEach { person in
|
||||
XCTAssertEqual(person.isDeveloper, context.isDeveloper)
|
||||
}
|
||||
}
|
||||
|
||||
func testArrayImmutableMappingWithoutContext() {
|
||||
let JSON = ["persons": [["name": "Tristan"], ["name": "Anton"]]]
|
||||
|
||||
do {
|
||||
let _ = try Mapper<ImmutablePersonList>().map(JSON: JSON)
|
||||
} catch ImmutablePersonMappingError.contextAbsense {
|
||||
return
|
||||
} catch {
|
||||
XCTFail()
|
||||
}
|
||||
|
||||
XCTFail()
|
||||
}
|
||||
|
||||
func testDefaultArgumentWithoutValue() {
|
||||
let JSON: [String: Any] = [:]
|
||||
let dog = try? Mapper<ImmutableDog>().map(JSON: JSON) as ImmutableDog
|
||||
|
||||
XCTAssertNotNil(dog)
|
||||
XCTAssertTrue(dog!.name == "Sasha")
|
||||
}
|
||||
|
||||
func testDefaultArgumentWithValue() {
|
||||
let JSON = ["name": "Sofie"]
|
||||
let dog = try? Mapper<ImmutableDog>().map(JSON: JSON) as ImmutableDog
|
||||
|
||||
XCTAssertNotNil(dog)
|
||||
XCTAssertTrue(dog!.name == "Sofie")
|
||||
}
|
||||
|
||||
// MARK: - Default Argument
|
||||
public struct ImmutableDog: ImmutableMappable {
|
||||
public let name: String
|
||||
|
||||
/// Define `default` value to use if it is nothing to parse in `name`
|
||||
public init(map: Map) throws {
|
||||
name = try map.value("name", default: "Sasha")
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Nested Types
|
||||
// MARK: BaseMappable
|
||||
struct Context: MapContext {
|
||||
var shouldMap = false
|
||||
|
||||
init(shouldMap: Bool){
|
||||
self.shouldMap = shouldMap
|
||||
}
|
||||
}
|
||||
|
||||
class Person: Mappable {
|
||||
var name: String?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
if (map.context as? Context)?.shouldMap == true {
|
||||
name <- map["name"]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class NestedPerson: Mappable {
|
||||
var person: Person?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
if (map.context as? Context)?.shouldMap == true {
|
||||
person <- map["person"]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class PersonList: Mappable {
|
||||
var persons: [Person]?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
if (map.context as? Context)?.shouldMap == true {
|
||||
persons <- map["persons"]
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: ImmutableMappable
|
||||
struct ImmutableContext: MapContext {
|
||||
let isDeveloper: Bool
|
||||
}
|
||||
|
||||
enum ImmutablePersonMappingError: Error {
|
||||
case contextAbsense
|
||||
}
|
||||
|
||||
struct ImmutablePerson: ImmutableMappable {
|
||||
let name: String
|
||||
let isDeveloper: Bool
|
||||
|
||||
init(map: Map) throws {
|
||||
guard let context = map.context as? ImmutableContext else {
|
||||
throw ImmutablePersonMappingError.contextAbsense
|
||||
}
|
||||
|
||||
name = try map.value("name")
|
||||
isDeveloper = context.isDeveloper
|
||||
}
|
||||
}
|
||||
|
||||
struct ImmutableNestedPerson: ImmutableMappable {
|
||||
let person: ImmutablePerson
|
||||
|
||||
init(map: Map) throws {
|
||||
person = try map.value("person")
|
||||
}
|
||||
}
|
||||
|
||||
struct ImmutablePersonList: ImmutableMappable {
|
||||
let persons: [ImmutablePerson]
|
||||
|
||||
init(map: Map) throws {
|
||||
persons = try map.value("persons")
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,105 +0,0 @@
|
|||
//
|
||||
// MappableExtensionsTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Scott Hoyt on 10/25/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
struct TestMappable: Mappable, Equatable, Hashable {
|
||||
static let valueForString = "This string should work"
|
||||
static let workingJSONString = "{ \"value\" : \"\(valueForString)\" }"
|
||||
static let workingJSON: [String: Any] = ["value": valueForString]
|
||||
static let workingJSONArrayString = "[\(workingJSONString)]"
|
||||
|
||||
var value: String?
|
||||
|
||||
init() {}
|
||||
init?(map: Map) { }
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
value <- map["value"]
|
||||
}
|
||||
|
||||
var hashValue: Int {
|
||||
if let value = value {
|
||||
return value.hashValue
|
||||
}
|
||||
return NSIntegerMax
|
||||
}
|
||||
}
|
||||
|
||||
func ==(lhs: TestMappable, rhs: TestMappable) -> Bool {
|
||||
return lhs.value == rhs.value
|
||||
}
|
||||
|
||||
class MappableExtensionsTests: XCTestCase {
|
||||
|
||||
var testMappable: TestMappable!
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
testMappable = TestMappable()
|
||||
testMappable.value = TestMappable.valueForString
|
||||
}
|
||||
|
||||
func testInitFromString() {
|
||||
let mapped = TestMappable(JSONString: TestMappable.workingJSONString)
|
||||
|
||||
XCTAssertNotNil(mapped)
|
||||
XCTAssertEqual(mapped?.value, TestMappable.valueForString)
|
||||
}
|
||||
|
||||
func testToJSONAndBack() {
|
||||
let mapped = TestMappable(JSON: testMappable.toJSON())
|
||||
XCTAssertEqual(mapped, testMappable)
|
||||
}
|
||||
|
||||
func testArrayFromString() {
|
||||
let mapped = [TestMappable](JSONString: TestMappable.workingJSONArrayString)!
|
||||
XCTAssertEqual(mapped, [testMappable])
|
||||
}
|
||||
|
||||
func testArrayToJSONAndBack() {
|
||||
let mapped = [TestMappable](JSONArray: [testMappable].toJSON())
|
||||
XCTAssertEqual(mapped, [testMappable])
|
||||
}
|
||||
|
||||
func testSetInitFailsWithEmptyString() {
|
||||
XCTAssertNil(Set<TestMappable>(JSONString: ""))
|
||||
}
|
||||
|
||||
func testSetFromString() {
|
||||
let mapped = Set<TestMappable>(JSONString: TestMappable.workingJSONArrayString)!
|
||||
XCTAssertEqual(mapped, Set<TestMappable>([testMappable]))
|
||||
}
|
||||
|
||||
func testSetToJSONAndBack() {
|
||||
let mapped = Set<TestMappable>(JSONArray: Set([testMappable]).toJSON())
|
||||
XCTAssertEqual(mapped, [testMappable])
|
||||
}
|
||||
}
|
|
@ -1,343 +0,0 @@
|
|||
//
|
||||
// MappableTypesWithTransformsTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Paddy O'Brien on 2015-12-04.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
|
||||
class MappableTypesWithTransformsTests: XCTestCase {
|
||||
// This is a func so that it can be collapsed
|
||||
func JSONPayload() -> [String: Any] {
|
||||
return [
|
||||
"teams": [[
|
||||
"api_uri": "/teams/8",
|
||||
"full_name": "Team Secret",
|
||||
"short_name": "Secret",
|
||||
"players": ["/players/1", "/players/2", "/players/3", "/players/4", "/players/5"]
|
||||
], [
|
||||
"api_uri": "/teams/43",
|
||||
"full_name": "Mineski",
|
||||
"short_name": "Mski",
|
||||
"players": ["/players/6", "/players/7", "/players/8", "/players/9", "/players/10"]
|
||||
]],
|
||||
"game": [
|
||||
"api_uri": "/games/2723",
|
||||
"game_time": "33:49",
|
||||
"players": [
|
||||
["/players/1", "/players/2", "/players/3", "/players/4", "/players/5"],
|
||||
["/players/6", "/players/7", "/players/8", "/players/9", "/players/10"]
|
||||
],
|
||||
"team1_lineup": [
|
||||
"top": "/players/1",
|
||||
"mid": "/players/2",
|
||||
"bottom": "/players/3",
|
||||
"support": "/players/4",
|
||||
"carry": "/players/5"
|
||||
],
|
||||
"team2_lineup": [
|
||||
"top": "/players/6",
|
||||
"mid": "/players/7",
|
||||
"bottom": "/players/8",
|
||||
"support": "/players/9",
|
||||
"carry": "/players/10"
|
||||
],
|
||||
"head_to_head": [
|
||||
"top": ["/players/1", "/players/6"],
|
||||
"mid": ["/players/2", "/players/7"],
|
||||
"bottom": ["/players/3", "/players/8"],
|
||||
"support": ["/players/4", "/players/9"],
|
||||
"carry": ["/players/5", "/players/10"]
|
||||
],
|
||||
"teams": ["/teams/43", "/teams/8"],
|
||||
"winning_team_url": "/teams/8"
|
||||
]
|
||||
]
|
||||
}
|
||||
|
||||
|
||||
// MARK: - Non-Optional Tests
|
||||
func testParsingSingleInstanceWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotEqual(game!.winner.URI, "FAKE")
|
||||
}
|
||||
|
||||
func testParsingArrayOfObjectsWithTransform() {
|
||||
let teams = Mapper<Team>().mapArray(JSONObject: JSONPayload()["teams"])
|
||||
|
||||
XCTAssertNotNil(teams)
|
||||
XCTAssertNotEqual(teams!.count, 0)
|
||||
|
||||
XCTAssertNotEqual(teams!.first!.players.count, 0)
|
||||
}
|
||||
|
||||
func testParsing2DimensionalArrayOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotEqual(game!.players.count, 0)
|
||||
XCTAssertNotEqual(game!.players.first!.count, 0)
|
||||
XCTAssertNotEqual(game!.players.last!.count, 0)
|
||||
}
|
||||
|
||||
func testParsingDictionaryOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotEqual(game!.team1Lineup.count, 0)
|
||||
XCTAssertNotEqual(game!.team2Lineup.count, 0)
|
||||
}
|
||||
|
||||
func testParsingDictionaryOfArrayOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
for (position, players) in game!.headToHead {
|
||||
XCTAssertNotEqual(players.count, 0, "No players were mapped for \(position)")
|
||||
}
|
||||
}
|
||||
|
||||
func testParsingSetOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotEqual(game!.teams.count, 0)
|
||||
}
|
||||
|
||||
|
||||
// MARK: - Optional Tests
|
||||
func testParsingOptionalSingleInstanceWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.O_winner)
|
||||
}
|
||||
|
||||
func testParsingOptionalArrayOfObjectsWithTransform() {
|
||||
let teams = Mapper<Team>().mapArray(JSONObject: JSONPayload()["teams"])
|
||||
|
||||
XCTAssertNotNil(teams)
|
||||
XCTAssertNotEqual(teams!.count, 0)
|
||||
|
||||
XCTAssertNotNil(teams!.first!.O_players)
|
||||
XCTAssertNotEqual(teams!.first!.O_players!.count, 0)
|
||||
}
|
||||
|
||||
func testParsingOptional2DimensionalArrayOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.O_players)
|
||||
XCTAssertNotEqual(game!.O_players!.count, 0)
|
||||
XCTAssertNotEqual(game!.O_players!.first!.count, 0)
|
||||
XCTAssertNotEqual(game!.O_players!.last!.count, 0)
|
||||
}
|
||||
|
||||
func testParsingOptionalDictionaryOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.O_team1Lineup)
|
||||
XCTAssertNotEqual(game!.O_team1Lineup!.count, 0)
|
||||
XCTAssertNotNil(game!.O_team2Lineup)
|
||||
XCTAssertNotEqual(game!.O_team2Lineup!.count, 0)
|
||||
}
|
||||
|
||||
func testParsingOptionalDictionaryOfArrayOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.O_headToHead)
|
||||
for (position, players) in game!.O_headToHead! {
|
||||
XCTAssertNotEqual(players.count, 0, "No players were mapped for \(position)")
|
||||
}
|
||||
}
|
||||
|
||||
func testParsingOptionalSetOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.O_teams)
|
||||
XCTAssertNotEqual(game!.O_teams!.count, 0)
|
||||
}
|
||||
|
||||
// MARK: - Implicitly Unwrapped Optional Tests
|
||||
func testParsingImplicitlyUnwrappedSingleInstanceWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.I_winner)
|
||||
}
|
||||
|
||||
func testParsingImplicitlyUnwrappedArrayOfObjectsWithTransform() {
|
||||
let teams = Mapper<Team>().mapArray(JSONObject: JSONPayload()["teams"])
|
||||
|
||||
XCTAssertNotNil(teams)
|
||||
XCTAssertNotEqual(teams!.count, 0)
|
||||
|
||||
XCTAssertNotNil(teams!.first!.I_players)
|
||||
XCTAssertNotEqual(teams!.first!.I_players!.count, 0)
|
||||
}
|
||||
|
||||
func testParsingImplicitlyUnwrapped2DimensionalArrayOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.I_players)
|
||||
XCTAssertNotEqual(game!.I_players!.count, 0)
|
||||
XCTAssertNotEqual(game!.I_players!.first!.count, 0)
|
||||
XCTAssertNotEqual(game!.I_players!.last!.count, 0)
|
||||
}
|
||||
|
||||
func testParsingImplicitlyUnwrappedDictionaryOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.I_team1Lineup)
|
||||
XCTAssertNotEqual(game!.I_team1Lineup!.count, 0)
|
||||
XCTAssertNotNil(game!.I_team2Lineup)
|
||||
XCTAssertNotEqual(game!.I_team2Lineup!.count, 0)
|
||||
}
|
||||
|
||||
func testParsingImplicitlyUnwrappedDictionaryOfArrayOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.I_headToHead)
|
||||
for (position, players) in game!.I_headToHead! {
|
||||
XCTAssertNotEqual(players.count, 0, "No players were mapped for \(position)")
|
||||
}
|
||||
}
|
||||
|
||||
func testParsingImplicitlyUnwrappedSetOfObjectsWithTransform() {
|
||||
let game = Mapper<Game>().map(JSONObject: JSONPayload()["game"])
|
||||
|
||||
XCTAssertNotNil(game)
|
||||
XCTAssertNotNil(game!.I_teams)
|
||||
XCTAssertNotEqual(game!.I_teams!.count, 0)
|
||||
}
|
||||
|
||||
// MARK: - Internal classes for testing
|
||||
class Game: Mappable, URIInitiable {
|
||||
var URI: String?
|
||||
var players: [[Player]] = [[]]
|
||||
var team1Lineup: [String: Player] = [:]
|
||||
var team2Lineup: [String: Player] = [:]
|
||||
var headToHead: [String: [Player]] = [:]
|
||||
var teams: Set<Team> = []
|
||||
var winner: Team = Team(URI: "FAKE")
|
||||
|
||||
// Optional
|
||||
var O_players: [[Player]]?
|
||||
var O_team1Lineup: [String: Player]?
|
||||
var O_team2Lineup: [String: Player]?
|
||||
var O_headToHead: [String: [Player]]?
|
||||
var O_teams: Set<Team>?
|
||||
var O_winner: Team?
|
||||
|
||||
// Implicitly Unwrapped
|
||||
var I_players: [[Player]]!
|
||||
var I_team1Lineup: [String: Player]!
|
||||
var I_team2Lineup: [String: Player]!
|
||||
var I_headToHead: [String: [Player]]!
|
||||
var I_teams: Set<Team>!
|
||||
var I_winner: Team!
|
||||
|
||||
required init(URI: String) { self.URI = URI }
|
||||
required init?(map: Map) {}
|
||||
|
||||
func mapping(map: Map) {
|
||||
players <- (map["players"], RelationshipTransform<Player>()) // 2D Array with transform
|
||||
team1Lineup <- (map["team1_lineup"], RelationshipTransform<Player>()) // Dictionary with transform
|
||||
team2Lineup <- (map["team1_lineup"], RelationshipTransform<Player>())
|
||||
headToHead <- (map["head_to_head"], RelationshipTransform<Player>()) // Dictionary of arrays with transform
|
||||
teams <- (map["teams"], RelationshipTransform<Team>()) // Set with transform
|
||||
winner <- (map["winning_team_url"], RelationshipTransform<Team>()) // Single instance with transform
|
||||
|
||||
// Optional
|
||||
O_players <- (map["players"], RelationshipTransform<Player>())
|
||||
O_team1Lineup <- (map["team1_lineup"], RelationshipTransform<Player>())
|
||||
O_team2Lineup <- (map["team1_lineup"], RelationshipTransform<Player>())
|
||||
O_headToHead <- (map["head_to_head"], RelationshipTransform<Player>())
|
||||
O_teams <- (map["teams"], RelationshipTransform<Team>())
|
||||
O_winner <- (map["winning_team_url"], RelationshipTransform<Team>())
|
||||
|
||||
// Implicitly Unwrapped
|
||||
I_players <- (map["players"], RelationshipTransform<Player>())
|
||||
I_team1Lineup <- (map["team1_lineup"], RelationshipTransform<Player>())
|
||||
I_team2Lineup <- (map["team1_lineup"], RelationshipTransform<Player>())
|
||||
I_headToHead <- (map["head_to_head"], RelationshipTransform<Player>())
|
||||
I_teams <- (map["teams"], RelationshipTransform<Team>())
|
||||
I_winner <- (map["winning_team_url"], RelationshipTransform<Team>())
|
||||
}
|
||||
}
|
||||
|
||||
class Team: NSObject, Mappable, URIInitiable {
|
||||
var URI: String?
|
||||
var players: [Player] = []
|
||||
var O_players: [Player]?
|
||||
var I_players: [Player]?
|
||||
|
||||
required init(URI: String) { self.URI = URI }
|
||||
required init?(map: Map) {}
|
||||
|
||||
func mapping(map: Map) {
|
||||
players <- (map["players"], RelationshipTransform<Player>())
|
||||
O_players <- (map["players"], RelationshipTransform<Player>())
|
||||
I_players <- (map["players"], RelationshipTransform<Player>())
|
||||
}
|
||||
}
|
||||
|
||||
class Player: Mappable, URIInitiable {
|
||||
required init(URI: String) {}
|
||||
required init?(map: Map) {}
|
||||
|
||||
func mapping(map: Map) {}
|
||||
}
|
||||
}
|
||||
|
||||
protocol URIInitiable {
|
||||
init(URI: String)
|
||||
}
|
||||
|
||||
class RelationshipTransform<ObjectType>: TransformType where ObjectType: Mappable & URIInitiable {
|
||||
typealias Object = ObjectType
|
||||
typealias JSON = [String: AnyObject]
|
||||
|
||||
func transformFromJSON(_ value: Any?) -> Object? {
|
||||
guard let URI = value as? String else { return nil }
|
||||
let relation = ObjectType(URI: URI)
|
||||
|
||||
return relation
|
||||
}
|
||||
|
||||
func transformToJSON(_ value: Object?) -> JSON? {
|
||||
return nil
|
||||
}
|
||||
}
|
|
@ -1,86 +0,0 @@
|
|||
//
|
||||
// NestedArrayTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 10/21/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class NSDecimalNumberTransformTests: XCTestCase {
|
||||
|
||||
let mapper = Mapper<NSDecimalNumberType>()
|
||||
|
||||
func testNSDecimalNumberTransform() {
|
||||
let int: Int = 11
|
||||
let double: Double = 11.11
|
||||
/* Cannot use a float literal (eg: `let decimal: Decimal = 1.66`) as this transforms the value from 1.66 to 1.6599999999999995904 */
|
||||
let decimal = Decimal(string: "1.66")!
|
||||
let intString = "11"
|
||||
let doubleString = "11.11"
|
||||
let decimalString = "1.66"
|
||||
let JSONString = "{\"double\" : \(doubleString), \"int\" : \(intString), \"decimal\" : \(decimalString), \"intString\" : \"\(intString)\", \"doubleString\" : \"\(doubleString)\", \"decimalString\" : \"\(decimalString)\"}"
|
||||
|
||||
let mappedObject = mapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.int, NSDecimalNumber(value: int))
|
||||
XCTAssertEqual(mappedObject?.double, NSDecimalNumber(value: double))
|
||||
XCTAssertEqual(mappedObject?.decimal, NSDecimalNumber(decimal: decimal))
|
||||
XCTAssertEqual(mappedObject?.intString, NSDecimalNumber(string: intString))
|
||||
XCTAssertEqual(mappedObject?.doubleString, NSDecimalNumber(string: doubleString))
|
||||
XCTAssertEqual(mappedObject?.decimalString, NSDecimalNumber(string: decimalString))
|
||||
XCTAssertEqual(mappedObject?.int?.stringValue, intString)
|
||||
XCTAssertEqual(mappedObject?.double?.stringValue, doubleString)
|
||||
XCTAssertEqual(mappedObject?.decimal?.stringValue, decimalString)
|
||||
}
|
||||
}
|
||||
|
||||
class NSDecimalNumberType: Mappable {
|
||||
|
||||
var int: NSDecimalNumber?
|
||||
var double: NSDecimalNumber?
|
||||
var decimal: NSDecimalNumber?
|
||||
var intString: NSDecimalNumber?
|
||||
var doubleString: NSDecimalNumber?
|
||||
var decimalString: NSDecimalNumber?
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
int <- (map["int"], NSDecimalNumberTransform())
|
||||
double <- (map["double"], NSDecimalNumberTransform())
|
||||
decimal <- (map["decimal"], NSDecimalNumberTransform())
|
||||
intString <- (map["intString"], NSDecimalNumberTransform())
|
||||
doubleString <- (map["doubleString"], NSDecimalNumberTransform())
|
||||
decimalString <- (map["decimalString"], NSDecimalNumberTransform())
|
||||
}
|
||||
}
|
|
@ -1,105 +0,0 @@
|
|||
//
|
||||
// NestedArrayTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Ruben Samsonyan on 10/21/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class NestedArrayTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testNestedArray() {
|
||||
let JSON: [String: Any] = [ "nested": [ ["value": 123], ["value": 456] ] ]
|
||||
|
||||
let mapper = Mapper<NestedArray>()
|
||||
|
||||
let value: NestedArray! = mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(value)
|
||||
|
||||
let JSONFromValue = mapper.toJSON(value)
|
||||
let valueFromParsedJSON: NestedArray! = mapper.map(JSON: JSONFromValue)
|
||||
XCTAssertNotNil(valueFromParsedJSON)
|
||||
|
||||
XCTAssertEqual(value.value_0, valueFromParsedJSON.value_0)
|
||||
XCTAssertEqual(value.value_1, valueFromParsedJSON.value_1)
|
||||
}
|
||||
|
||||
func testNestedObjectArray() {
|
||||
let value = 456
|
||||
let JSON: [String: Any] = [ "nested": [ ["value": 123], ["value": value] ] ]
|
||||
|
||||
let mapper = Mapper<NestedArray>()
|
||||
|
||||
let mappedObject: NestedArray! = mapper.map(JSON: JSON)
|
||||
XCTAssertNotNil(mappedObject)
|
||||
|
||||
XCTAssertEqual(mappedObject.nestedObject!.value, value)
|
||||
XCTAssertEqual(mappedObject.nestedObjectValue, value)
|
||||
}
|
||||
}
|
||||
|
||||
class NestedArray: Mappable {
|
||||
|
||||
var value_0: Int?
|
||||
var value_1: Int?
|
||||
|
||||
var nestedObject: NestedObject?
|
||||
|
||||
var nestedObjectValue: Int?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
value_0 <- map["nested.0.value"]
|
||||
value_1 <- map["nested.1.value"]
|
||||
|
||||
nestedObject <- map["nested.1"]
|
||||
nestedObjectValue <- map["nested.1.value"]
|
||||
}
|
||||
}
|
||||
|
||||
class NestedObject: Mappable {
|
||||
var value: Int?
|
||||
|
||||
required init?(map: Map){}
|
||||
|
||||
func mapping(map: Map) {
|
||||
value <- map["value"]
|
||||
}
|
||||
}
|
|
@ -1,401 +0,0 @@
|
|||
//
|
||||
// NestedKeysTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Syo Ikeda on 3/10/15.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class NestedKeysTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testNestedKeys() {
|
||||
let JSON: [String: Any] = [
|
||||
"non.nested.key": "string",
|
||||
"nested": [
|
||||
"int64": NSNumber(value: INT64_MAX),
|
||||
"bool": true,
|
||||
"int": 255,
|
||||
"double": 100.0 as Double,
|
||||
"float": 50.0 as Float,
|
||||
"string": "String!",
|
||||
|
||||
"nested": [
|
||||
"int64Array": [NSNumber(value: INT64_MAX), NSNumber(value: INT64_MAX - 1), NSNumber(value: INT64_MAX - 10)],
|
||||
"boolArray": [false, true, false],
|
||||
"intArray": [1, 2, 3],
|
||||
"doubleArray": [1.0, 2.0, 3.0],
|
||||
"floatArray": [1.0 as Float, 2.0 as Float, 3.0 as Float],
|
||||
"stringArray": ["123", "ABC"],
|
||||
|
||||
"int64Dict": ["1": NSNumber(value: INT64_MAX)],
|
||||
"boolDict": ["2": true],
|
||||
"intDict": ["3": 999],
|
||||
"doubleDict": ["4": 999.999],
|
||||
"floatDict": ["5": 123.456 as Float],
|
||||
"stringDict": ["6": "InDict"],
|
||||
|
||||
"int64Enum": 1000,
|
||||
"intEnum": 255,
|
||||
"doubleEnum": 100.0,
|
||||
"floatEnum": 100.0,
|
||||
"stringEnum": "String B",
|
||||
|
||||
"nested": [
|
||||
"object": ["value": 987],
|
||||
"objectArray": [ ["value": 123], ["value": 456] ],
|
||||
"objectDict": ["key": ["value": 999]]
|
||||
]
|
||||
]
|
||||
]
|
||||
]
|
||||
|
||||
let mapper = Mapper<NestedKeys>()
|
||||
|
||||
let value: NestedKeys! = mapper.map(JSONObject: JSON)
|
||||
XCTAssertNotNil(value)
|
||||
|
||||
let JSONFromValue = mapper.toJSON(value)
|
||||
let valueFromParsedJSON: NestedKeys! = mapper.map(JSON: JSONFromValue)
|
||||
XCTAssertNotNil(valueFromParsedJSON)
|
||||
|
||||
XCTAssertEqual(value.nonNestedString, valueFromParsedJSON.nonNestedString)
|
||||
|
||||
XCTAssertEqual(value.int64, valueFromParsedJSON.int64)
|
||||
XCTAssertEqual(value.bool, valueFromParsedJSON.bool)
|
||||
XCTAssertEqual(value.int, valueFromParsedJSON.int)
|
||||
XCTAssertEqual(value.double, valueFromParsedJSON.double)
|
||||
XCTAssertEqual(value.float, valueFromParsedJSON.float)
|
||||
XCTAssertEqual(value.string, valueFromParsedJSON.string)
|
||||
|
||||
XCTAssertEqual(value.int64Array, valueFromParsedJSON.int64Array)
|
||||
XCTAssertEqual(value.boolArray, valueFromParsedJSON.boolArray)
|
||||
XCTAssertEqual(value.intArray, valueFromParsedJSON.intArray)
|
||||
XCTAssertEqual(value.doubleArray, valueFromParsedJSON.doubleArray)
|
||||
XCTAssertEqual(value.floatArray, valueFromParsedJSON.floatArray)
|
||||
XCTAssertEqual(value.stringArray, valueFromParsedJSON.stringArray)
|
||||
|
||||
XCTAssertEqual(value.int64Dict, valueFromParsedJSON.int64Dict)
|
||||
XCTAssertEqual(value.boolDict, valueFromParsedJSON.boolDict)
|
||||
XCTAssertEqual(value.intDict, valueFromParsedJSON.intDict)
|
||||
XCTAssertEqual(value.doubleDict, valueFromParsedJSON.doubleDict)
|
||||
XCTAssertEqual(value.floatDict, valueFromParsedJSON.floatDict)
|
||||
XCTAssertEqual(value.stringDict, valueFromParsedJSON.stringDict)
|
||||
|
||||
XCTAssertEqual(value.int64Enum, valueFromParsedJSON.int64Enum)
|
||||
XCTAssertEqual(value.intEnum, valueFromParsedJSON.intEnum)
|
||||
XCTAssertEqual(value.doubleEnum, valueFromParsedJSON.doubleEnum)
|
||||
XCTAssertEqual(value.floatEnum, valueFromParsedJSON.floatEnum)
|
||||
XCTAssertEqual(value.stringEnum, valueFromParsedJSON.stringEnum)
|
||||
|
||||
XCTAssertEqual(value.object, valueFromParsedJSON.object)
|
||||
XCTAssertEqual(value.objectArray, valueFromParsedJSON.objectArray)
|
||||
XCTAssertEqual(value.objectDict, valueFromParsedJSON.objectDict)
|
||||
}
|
||||
|
||||
func testNestedKeysWithDelimiter() {
|
||||
let JSON: [String: Any] = [
|
||||
"non.nested->key": "string",
|
||||
"com.tristanhimmelman.ObjectMapper.nested": [
|
||||
"com.tristanhimmelman.ObjectMapper.int64": NSNumber(value: INT64_MAX),
|
||||
"com.tristanhimmelman.ObjectMapper.bool": true,
|
||||
"com.tristanhimmelman.ObjectMapper.int": 255,
|
||||
"com.tristanhimmelman.ObjectMapper.double": 100.0 as Double,
|
||||
"com.tristanhimmelman.ObjectMapper.float": 50.0 as Float,
|
||||
"com.tristanhimmelman.ObjectMapper.string": "String!",
|
||||
|
||||
"com.tristanhimmelman.ObjectMapper.nested": [
|
||||
"int64Array": [NSNumber(value: INT64_MAX), NSNumber(value: INT64_MAX - 1), NSNumber(value: INT64_MAX - 10)],
|
||||
"boolArray": [false, true, false],
|
||||
"intArray": [1, 2, 3],
|
||||
"doubleArray": [1.0, 2.0, 3.0],
|
||||
"floatArray": [1.0 as Float, 2.0 as Float, 3.0 as Float],
|
||||
"stringArray": ["123", "ABC"],
|
||||
|
||||
"int64Dict": ["1": NSNumber(value: INT64_MAX)],
|
||||
"boolDict": ["2": true],
|
||||
"intDict": ["3": 999],
|
||||
"doubleDict": ["4": 999.999],
|
||||
"floatDict": ["5": 123.456 as Float],
|
||||
"stringDict": ["6": "InDict"],
|
||||
|
||||
"int64Enum": 1000,
|
||||
"intEnum": 255,
|
||||
"doubleEnum": 100.0,
|
||||
"floatEnum": 100.0,
|
||||
"stringEnum": "String B",
|
||||
|
||||
"com.tristanhimmelman.ObjectMapper.nested": [
|
||||
"object": ["value": 987],
|
||||
"objectArray": [ ["value": 123], ["value": 456] ],
|
||||
"objectDict": ["key": ["value": 999]]
|
||||
]
|
||||
]
|
||||
]
|
||||
]
|
||||
|
||||
let mapper = Mapper<DelimiterNestedKeys>()
|
||||
|
||||
let value: DelimiterNestedKeys! = mapper.map(JSONObject: JSON)
|
||||
XCTAssertNotNil(value)
|
||||
|
||||
XCTAssertEqual(value.nonNestedString, "string")
|
||||
|
||||
XCTAssertEqual(value.int64, NSNumber(value: INT64_MAX))
|
||||
XCTAssertEqual(value.bool, true)
|
||||
XCTAssertEqual(value.int, 255)
|
||||
XCTAssertEqual(value.double, 100.0 as Double)
|
||||
XCTAssertEqual(value.float, 50.0 as Float)
|
||||
XCTAssertEqual(value.string, "String!")
|
||||
|
||||
let int64Array = [NSNumber(value: INT64_MAX), NSNumber(value: INT64_MAX - 1), NSNumber(value: INT64_MAX - 10)]
|
||||
XCTAssertEqual(value.int64Array, int64Array)
|
||||
XCTAssertEqual(value.boolArray, [false, true, false])
|
||||
XCTAssertEqual(value.intArray, [1, 2, 3])
|
||||
XCTAssertEqual(value.doubleArray, [1.0, 2.0, 3.0])
|
||||
XCTAssertEqual(value.floatArray, [1.0 as Float, 2.0 as Float, 3.0 as Float])
|
||||
XCTAssertEqual(value.stringArray, ["123", "ABC"])
|
||||
|
||||
XCTAssertEqual(value.int64Dict, ["1": NSNumber(value: INT64_MAX)])
|
||||
XCTAssertEqual(value.boolDict, ["2": true])
|
||||
XCTAssertEqual(value.intDict, ["3": 999])
|
||||
XCTAssertEqual(value.doubleDict, ["4": 999.999])
|
||||
XCTAssertEqual(value.floatDict, ["5": 123.456 as Float])
|
||||
XCTAssertEqual(value.stringDict, ["6": "InDict"])
|
||||
|
||||
XCTAssertEqual(value.int64Enum, Int64Enum.b)
|
||||
XCTAssertEqual(value.intEnum, IntEnum.b)
|
||||
// Skip tests due to float issue - #591
|
||||
// XCTAssertEqual(value.doubleEnum, DoubleEnum.b)
|
||||
// XCTAssertEqual(value.floatEnum, FloatEnum.b)
|
||||
XCTAssertEqual(value.stringEnum, StringEnum.B)
|
||||
|
||||
XCTAssertEqual(value.object?.value, 987)
|
||||
XCTAssertEqual(value.objectArray.map { $0.value }, [123, 456])
|
||||
XCTAssertEqual(value.objectDict["key"]?.value, 999)
|
||||
|
||||
let JSONFromValue = mapper.toJSON(value)
|
||||
let valueFromParsedJSON: DelimiterNestedKeys! = mapper.map(JSON: JSONFromValue)
|
||||
XCTAssertNotNil(valueFromParsedJSON)
|
||||
|
||||
XCTAssertEqual(value.nonNestedString, valueFromParsedJSON.nonNestedString)
|
||||
|
||||
XCTAssertEqual(value.int64, valueFromParsedJSON.int64)
|
||||
XCTAssertEqual(value.bool, valueFromParsedJSON.bool)
|
||||
XCTAssertEqual(value.int, valueFromParsedJSON.int)
|
||||
XCTAssertEqual(value.double, valueFromParsedJSON.double)
|
||||
XCTAssertEqual(value.float, valueFromParsedJSON.float)
|
||||
XCTAssertEqual(value.string, valueFromParsedJSON.string)
|
||||
|
||||
XCTAssertEqual(value.int64Array, valueFromParsedJSON.int64Array)
|
||||
XCTAssertEqual(value.boolArray, valueFromParsedJSON.boolArray)
|
||||
XCTAssertEqual(value.intArray, valueFromParsedJSON.intArray)
|
||||
XCTAssertEqual(value.doubleArray, valueFromParsedJSON.doubleArray)
|
||||
XCTAssertEqual(value.floatArray, valueFromParsedJSON.floatArray)
|
||||
XCTAssertEqual(value.stringArray, valueFromParsedJSON.stringArray)
|
||||
|
||||
XCTAssertEqual(value.int64Dict, valueFromParsedJSON.int64Dict)
|
||||
XCTAssertEqual(value.boolDict, valueFromParsedJSON.boolDict)
|
||||
XCTAssertEqual(value.intDict, valueFromParsedJSON.intDict)
|
||||
XCTAssertEqual(value.doubleDict, valueFromParsedJSON.doubleDict)
|
||||
XCTAssertEqual(value.floatDict, valueFromParsedJSON.floatDict)
|
||||
XCTAssertEqual(value.stringDict, valueFromParsedJSON.stringDict)
|
||||
|
||||
XCTAssertEqual(value.int64Enum, valueFromParsedJSON.int64Enum)
|
||||
XCTAssertEqual(value.intEnum, valueFromParsedJSON.intEnum)
|
||||
XCTAssertEqual(value.doubleEnum, valueFromParsedJSON.doubleEnum)
|
||||
XCTAssertEqual(value.floatEnum, valueFromParsedJSON.floatEnum)
|
||||
XCTAssertEqual(value.stringEnum, valueFromParsedJSON.stringEnum)
|
||||
|
||||
XCTAssertEqual(value.object, valueFromParsedJSON.object)
|
||||
XCTAssertEqual(value.objectArray, valueFromParsedJSON.objectArray)
|
||||
XCTAssertEqual(value.objectDict, valueFromParsedJSON.objectDict)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class NestedKeys: Mappable {
|
||||
|
||||
var nonNestedString: String?
|
||||
|
||||
var int64: NSNumber?
|
||||
var bool: Bool?
|
||||
var int: Int?
|
||||
var double: Double?
|
||||
var float: Float?
|
||||
var string: String?
|
||||
|
||||
var int64Array: [NSNumber] = []
|
||||
var boolArray: [Bool] = []
|
||||
var intArray: [Int] = []
|
||||
var doubleArray: [Double] = []
|
||||
var floatArray: [Float] = []
|
||||
var stringArray: [String] = []
|
||||
|
||||
var int64Dict: [String: NSNumber] = [:]
|
||||
var boolDict: [String: Bool] = [:]
|
||||
var intDict: [String: Int] = [:]
|
||||
var doubleDict: [String: Double] = [:]
|
||||
var floatDict: [String: Float] = [:]
|
||||
var stringDict: [String: String] = [:]
|
||||
|
||||
var int64Enum: Int64Enum?
|
||||
var intEnum: IntEnum?
|
||||
var doubleEnum: DoubleEnum?
|
||||
var floatEnum: FloatEnum?
|
||||
var stringEnum: StringEnum?
|
||||
|
||||
var object: Object?
|
||||
var objectArray: [Object] = []
|
||||
var objectDict: [String: Object] = [:]
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
nonNestedString <- map["non.nested.key", nested: false]
|
||||
|
||||
int64 <- map["nested.int64"]
|
||||
bool <- map["nested.bool"]
|
||||
int <- map["nested.int"]
|
||||
double <- map["nested.double"]
|
||||
float <- map["nested.float"]
|
||||
string <- map["nested.string"]
|
||||
|
||||
int64Array <- map["nested.nested.int64Array"]
|
||||
boolArray <- map["nested.nested.boolArray"]
|
||||
intArray <- map["nested.nested.intArray"]
|
||||
doubleArray <- map["nested.nested.doubleArray"]
|
||||
floatArray <- map["nested.nested.floatArray"]
|
||||
stringArray <- map["nested.nested.stringArray"]
|
||||
|
||||
int64Dict <- map["nested.nested.int64Dict"]
|
||||
boolDict <- map["nested.nested.boolDict"]
|
||||
intDict <- map["nested.nested.intDict"]
|
||||
doubleDict <- map["nested.nested.doubleDict"]
|
||||
floatDict <- map["nested.nested.floatDict"]
|
||||
stringDict <- map["nested.nested.stringDict"]
|
||||
|
||||
int64Enum <- map["nested.nested.int64Enum"]
|
||||
intEnum <- map["nested.nested.intEnum"]
|
||||
doubleEnum <- map["nested.nested.doubleEnum"]
|
||||
floatEnum <- map["nested.nested.floatEnum"]
|
||||
stringEnum <- map["nested.nested.stringEnum"]
|
||||
|
||||
object <- map["nested.nested.nested.object"]
|
||||
objectArray <- map["nested.nested.nested.objectArray"]
|
||||
objectDict <- map["nested.nested.nested.objectDict"]
|
||||
}
|
||||
}
|
||||
|
||||
class DelimiterNestedKeys: NestedKeys {
|
||||
override func mapping(map: Map) {
|
||||
nonNestedString <- map["non.nested->key", nested: false, delimiter: "->"]
|
||||
|
||||
int64 <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.int64", delimiter: "->"]
|
||||
bool <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.bool", delimiter: "->"]
|
||||
int <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.int", delimiter: "->"]
|
||||
double <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.double", delimiter: "->"]
|
||||
float <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.float", delimiter: "->"]
|
||||
string <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.string", delimiter: "->"]
|
||||
|
||||
int64Array <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->int64Array", delimiter: "->"]
|
||||
boolArray <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->boolArray", delimiter: "->"]
|
||||
intArray <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->intArray", delimiter: "->"]
|
||||
doubleArray <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->doubleArray", delimiter: "->"]
|
||||
floatArray <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->floatArray", delimiter: "->"]
|
||||
stringArray <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->stringArray", delimiter: "->"]
|
||||
|
||||
int64Dict <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->int64Dict", delimiter: "->"]
|
||||
boolDict <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->boolDict", delimiter: "->"]
|
||||
intDict <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->intDict", delimiter: "->"]
|
||||
doubleDict <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->doubleDict", delimiter: "->"]
|
||||
floatDict <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->floatDict", delimiter: "->"]
|
||||
stringDict <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->stringDict", delimiter: "->"]
|
||||
|
||||
int64Enum <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->int64Enum", delimiter: "->"]
|
||||
intEnum <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->intEnum", delimiter: "->"]
|
||||
doubleEnum <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->doubleEnum", delimiter: "->"]
|
||||
floatEnum <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->floatEnum", delimiter: "->"]
|
||||
stringEnum <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->stringEnum", delimiter: "->"]
|
||||
|
||||
object <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->object", delimiter: "->"]
|
||||
objectArray <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->objectArray", delimiter: "->"]
|
||||
objectDict <- map["com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->com.tristanhimmelman.ObjectMapper.nested->objectDict", delimiter: "->"]
|
||||
}
|
||||
}
|
||||
|
||||
class Object: Mappable, Equatable {
|
||||
var value: Int = Int.min
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
value <- map["value"]
|
||||
}
|
||||
}
|
||||
|
||||
func == (lhs: Object, rhs: Object) -> Bool {
|
||||
return lhs.value == rhs.value
|
||||
}
|
||||
|
||||
enum Int64Enum: NSNumber {
|
||||
case a = 0
|
||||
case b = 1000
|
||||
}
|
||||
|
||||
enum IntEnum: Int {
|
||||
case a = 0
|
||||
case b = 255
|
||||
}
|
||||
|
||||
enum DoubleEnum: Double {
|
||||
case a = 0.0
|
||||
case b = 100.0
|
||||
}
|
||||
|
||||
enum FloatEnum: Float {
|
||||
case a = 0.0
|
||||
case b = 100.0
|
||||
}
|
||||
|
||||
enum StringEnum: String {
|
||||
case A = "String A"
|
||||
case B = "String B"
|
||||
}
|
|
@ -1,118 +0,0 @@
|
|||
//
|
||||
// NullableKeysFromJSONTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Fabio Teles on 3/22/16.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan HImmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class NullableKeysFromJSONTests: XCTestCase {
|
||||
|
||||
let fullJSONString = "{\"firstName\": \"John\", \"lastName\": \"Doe\", \"team\": \"Broncos\", \"age\": 25, \"address\": {\"street\": \"Nothing Ave\", \"number\": 101, \"city\": \"Los Angeles\"} }"
|
||||
let nullJSONString = "{\"firstName\": \"John\", \"lastName\": null, \"team\": \"Broncos\", \"age\": null, \"address\": {\"street\": \"Nothing Ave\", \"number\": 101, \"city\": null} }"
|
||||
let absentJSONString = "{\"firstName\": \"John\", \"team\": \"Broncos\", \"address\": {\"street\": \"Nothing Ave\", \"number\": 102} }"
|
||||
|
||||
let mapper = Mapper<Player>()
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
func testMapperNullifiesValues() {
|
||||
guard let player = mapper.map(JSONString: fullJSONString) else {
|
||||
XCTFail("Mapping failed")
|
||||
return
|
||||
}
|
||||
|
||||
XCTAssertNotNil(player.lastName)
|
||||
XCTAssertNotNil(player.age)
|
||||
XCTAssertNotNil(player.address?.city)
|
||||
|
||||
_ = mapper.map(JSONString: nullJSONString, toObject: player)
|
||||
|
||||
XCTAssertNotNil(player.firstName)
|
||||
XCTAssertNil(player.lastName)
|
||||
XCTAssertNil(player.age)
|
||||
XCTAssertNil(player.address?.city)
|
||||
}
|
||||
|
||||
func testMapperAbsentValues() {
|
||||
guard let player = mapper.map(JSONString: fullJSONString) else {
|
||||
XCTFail("Mapping failed")
|
||||
return
|
||||
}
|
||||
|
||||
XCTAssertNotNil(player.lastName)
|
||||
XCTAssertNotNil(player.age)
|
||||
XCTAssertNotNil(player.address?.city)
|
||||
|
||||
_ = mapper.map(JSONString: absentJSONString, toObject: player)
|
||||
|
||||
XCTAssertNotNil(player.firstName)
|
||||
XCTAssertNotNil(player.lastName)
|
||||
XCTAssertNotNil(player.age)
|
||||
XCTAssertNotNil(player.address?.city)
|
||||
XCTAssertEqual(player.address?.number, 102)
|
||||
}
|
||||
}
|
||||
|
||||
class Player: Mappable {
|
||||
var firstName: String?
|
||||
var lastName: String?
|
||||
var team: String?
|
||||
var age: Int?
|
||||
var address: Address?
|
||||
|
||||
required init?(map: Map){
|
||||
mapping(map: map)
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
firstName <- map["firstName"]
|
||||
lastName <- map["lastName"]
|
||||
team <- map["team"]
|
||||
age <- map["age"]
|
||||
address <- map["address"]
|
||||
}
|
||||
}
|
||||
|
||||
class Address: Mappable {
|
||||
var street: String?
|
||||
var number: Int?
|
||||
var city: String?
|
||||
|
||||
required init?(map: Map){
|
||||
mapping(map: map)
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
street <- map["street"]
|
||||
number <- map["number"]
|
||||
city <- map["city"]
|
||||
}
|
||||
}
|
|
@ -1,668 +0,0 @@
|
|||
//
|
||||
// ObjectMapperTests.swift
|
||||
// ObjectMapperTests
|
||||
//
|
||||
// Created by Tristan Himmelman on 2014-10-16.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class ObjectMapperTests: XCTestCase {
|
||||
|
||||
let userMapper = Mapper<User>()
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testBasicParsing() {
|
||||
let username = "John Doe"
|
||||
let identifier = "user8723"
|
||||
let photoCount = 13
|
||||
let age = 1227
|
||||
let weight = 123.23
|
||||
let float: Float = 123.231
|
||||
let drinker = true
|
||||
let smoker = false
|
||||
let sex: Sex = .Female
|
||||
let canDrive = true
|
||||
let subUserJSON = "{\"identifier\" : \"user8723\", \"drinker\" : true, \"age\": 17, \"username\" : \"sub user\", \"canDrive\": \(canDrive) }"
|
||||
|
||||
let userJSONString = "{\"username\":\"\(username)\",\"identifier\":\"\(identifier)\",\"photoCount\":\(photoCount),\"age\":\(age),\"drinker\":\(drinker),\"smoker\":\(smoker), \"sex\":\"\(sex.rawValue)\", \"canDrive\": \(canDrive), \"arr\":[ \"bla\", true, 42 ], \"dict\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 }, \"arrOpt\":[ \"bla\", true, 42 ], \"dictOpt\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 }, \"weight\": \(weight), \"float\": \(float), \"friend\": \(subUserJSON), \"friendDictionary\":{ \"bestFriend\": \(subUserJSON)}, \"friends\": [\(subUserJSON), \(subUserJSON)]}"
|
||||
|
||||
guard let user = userMapper.map(JSONString: userJSONString) else {
|
||||
XCTFail()
|
||||
return
|
||||
}
|
||||
|
||||
XCTAssertNotNil(user)
|
||||
XCTAssertEqual(username, user.username)
|
||||
XCTAssertEqual(identifier, user.identifier)
|
||||
XCTAssertEqual(photoCount, user.photoCount)
|
||||
XCTAssertEqual(age, user.age)
|
||||
XCTAssertEqual(weight, user.weight)
|
||||
XCTAssertEqual(float, user.float)
|
||||
XCTAssertEqual(drinker, user.drinker)
|
||||
XCTAssertEqual(smoker, user.smoker)
|
||||
XCTAssertEqual(sex, user.sex)
|
||||
XCTAssertEqual(canDrive, user.canDrive)
|
||||
XCTAssertNotNil(user.friends)
|
||||
XCTAssertEqual(user.friends?.count, 2)
|
||||
XCTAssertEqual(user.friends?[1].canDrive, canDrive)
|
||||
|
||||
//print(Mapper().toJSONString(user, prettyPrint: true))
|
||||
}
|
||||
|
||||
func testOptionalStringParsing() {
|
||||
let username = "John Doe"
|
||||
let identifier = "user8723"
|
||||
let photoCount = 13
|
||||
let age = 1227
|
||||
let weight = 123.23
|
||||
let float: Float = 123.231
|
||||
let drinker = true
|
||||
let smoker = false
|
||||
let sex: Sex = .Female
|
||||
let subUserJSON = "{\"identifier\" : \"user8723\", \"drinker\" : true, \"age\": 17, \"username\" : \"sub user\" }"
|
||||
|
||||
let userJSONString = "{\"username\":\"\(username)\",\"identifier\":\"\(identifier)\",\"photoCount\":\(photoCount),\"age\":\(age),\"drinker\":\(drinker),\"smoker\":\(smoker), \"sex\":\"\(sex.rawValue)\", \"arr\":[ \"bla\", true, 42 ], \"dict\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 }, \"arrOpt\":[ \"bla\", true, 42 ], \"dictOpt\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 }, \"weight\": \(weight), \"float\": \(float), \"friend\": \(subUserJSON), \"friendDictionary\":{ \"bestFriend\": \(subUserJSON)}}"
|
||||
|
||||
let user = userMapper.map(JSONString: userJSONString)!
|
||||
|
||||
XCTAssertNotNil(user)
|
||||
XCTAssertEqual(username, user.username)
|
||||
XCTAssertEqual(identifier, user.identifier)
|
||||
XCTAssertEqual(photoCount, user.photoCount)
|
||||
XCTAssertEqual(age, user.age)
|
||||
XCTAssertEqual(weight, user.weight)
|
||||
XCTAssertEqual(float, user.float)
|
||||
XCTAssertEqual(drinker, user.drinker)
|
||||
XCTAssertEqual(smoker, user.smoker)
|
||||
XCTAssertEqual(sex, user.sex)
|
||||
}
|
||||
|
||||
func testInstanceParsing() {
|
||||
let username = "John Doe"
|
||||
let identifier = "user8723"
|
||||
let photoCount = 13
|
||||
let age = 1227
|
||||
let weight = 180.51
|
||||
let float: Float = 123.231
|
||||
let drinker = true
|
||||
let smoker = false
|
||||
let sex: Sex = .Female
|
||||
let subUserJSON = "{\"identifier\" : \"user8723\", \"drinker\" : true, \"age\": 17, \"username\" : \"sub user\" }"
|
||||
|
||||
let userJSONString = "{\"username\":\"\(username)\",\"identifier\":\"\(identifier)\",\"photoCount\":\(photoCount),\"age\":\(age),\"drinker\":\(drinker),\"smoker\":\(smoker), \"sex\":\"\(sex.rawValue)\", \"arr\":[ \"bla\", true, 42 ], \"dict\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 }, \"arrOpt\":[ \"bla\", true, 42 ], \"dictOpt\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 },\"weight\": \(weight), \"float\": \(float), \"friend\": \(subUserJSON), \"friendDictionary\":{ \"bestFriend\": \(subUserJSON)}}"
|
||||
|
||||
let user = Mapper().map(JSONString: userJSONString, toObject: User())
|
||||
|
||||
XCTAssertEqual(username, user.username)
|
||||
XCTAssertEqual(identifier, user.identifier)
|
||||
XCTAssertEqual(photoCount, user.photoCount)
|
||||
XCTAssertEqual(age, user.age)
|
||||
XCTAssertEqual(weight, user.weight)
|
||||
XCTAssertEqual(float, user.float)
|
||||
XCTAssertEqual(drinker, user.drinker)
|
||||
XCTAssertEqual(smoker, user.smoker)
|
||||
XCTAssertEqual(sex, user.sex)
|
||||
//print(Mapper().toJSONString(user, prettyPrint: true))
|
||||
}
|
||||
|
||||
func testDictionaryParsing() {
|
||||
let name: String = "Genghis khan"
|
||||
let UUID: String = "12345"
|
||||
let major: Int = 99
|
||||
let minor: Int = 1
|
||||
let json: [String: Any] = ["name": name, "UUID": UUID, "major": major]
|
||||
|
||||
//test that the sematics of value types works as expected. the resulting maped student
|
||||
//should have the correct minor property set even thoug it's not mapped
|
||||
var s = Student()
|
||||
s.minor = minor
|
||||
let student = Mapper().map(JSON: json, toObject: s)
|
||||
|
||||
XCTAssertEqual(name, student.name)
|
||||
XCTAssertEqual(UUID, student.UUID)
|
||||
XCTAssertEqual(major, student.major)
|
||||
XCTAssertEqual(minor, student.minor)
|
||||
|
||||
//Test that mapping a reference type works as expected while not relying on the return value
|
||||
let username: String = "Barack Obama"
|
||||
let identifier: String = "Political"
|
||||
let photoCount: Int = 1000000000
|
||||
|
||||
let json2: [String: Any] = ["username": username, "identifier": identifier, "photoCount": photoCount]
|
||||
let user = User()
|
||||
_ = Mapper().map(JSON: json2, toObject: user)
|
||||
|
||||
XCTAssertEqual(username, user.username)
|
||||
XCTAssertEqual(identifier, user.identifier)
|
||||
XCTAssertEqual(photoCount, user.photoCount)
|
||||
}
|
||||
|
||||
func testNullObject() {
|
||||
let JSONString = "{\"username\":\"bob\"}"
|
||||
|
||||
let user = userMapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(user)
|
||||
XCTAssertNil(user?.age)
|
||||
}
|
||||
|
||||
func testToJSONAndBack(){
|
||||
let user = User()
|
||||
user.username = "tristan_him"
|
||||
user.identifier = "tristan_him_identifier"
|
||||
user.photoCount = 0
|
||||
user.age = 28
|
||||
user.weight = 150
|
||||
user.drinker = true
|
||||
user.smoker = false
|
||||
user.sex = .Female
|
||||
user.arr = ["cheese", 11234]
|
||||
|
||||
let JSONString = Mapper().toJSONString(user, prettyPrint: true)
|
||||
//print(JSONString)
|
||||
|
||||
let parsedUser = userMapper.map(JSONString: JSONString!)!
|
||||
|
||||
XCTAssertNotNil(parsedUser)
|
||||
XCTAssertEqual(user.identifier, parsedUser.identifier)
|
||||
XCTAssertEqual(user.photoCount, parsedUser.photoCount)
|
||||
XCTAssertEqual(user.age, parsedUser.age)
|
||||
XCTAssertEqual(user.weight, parsedUser.weight)
|
||||
XCTAssertEqual(user.drinker, parsedUser.drinker)
|
||||
XCTAssertEqual(user.smoker, parsedUser.smoker)
|
||||
XCTAssertEqual(user.sex, parsedUser.sex)
|
||||
}
|
||||
|
||||
func testToJSONArrayAndBack(){
|
||||
let user = User()
|
||||
user.username = "tristan_him"
|
||||
user.identifier = "tristan_him_identifier"
|
||||
user.photoCount = 0
|
||||
user.age = 28
|
||||
user.weight = 150
|
||||
user.drinker = true
|
||||
user.smoker = false
|
||||
user.sex = .Female
|
||||
user.arr = ["cheese", 11234]
|
||||
let users = [user, user, user]
|
||||
|
||||
//print(JSONString)
|
||||
let JSONString = Mapper().toJSONString(users)
|
||||
let parsedUsers = userMapper.mapArray(JSONString: JSONString!)
|
||||
|
||||
XCTAssertNotNil(parsedUsers)
|
||||
XCTAssertTrue(parsedUsers?.count == 3)
|
||||
XCTAssertEqual(user.identifier, parsedUsers?[0].identifier)
|
||||
XCTAssertEqual(user.photoCount, parsedUsers?[0].photoCount)
|
||||
XCTAssertEqual(user.age, parsedUsers?[0].age)
|
||||
XCTAssertEqual(user.weight, parsedUsers?[0].weight)
|
||||
XCTAssertEqual(user.drinker, parsedUsers?[0].drinker)
|
||||
XCTAssertEqual(user.smoker, parsedUsers?[0].smoker)
|
||||
XCTAssertEqual(user.sex, parsedUsers?[0].sex)
|
||||
}
|
||||
|
||||
func testUnknownPropertiesIgnored() {
|
||||
let JSONString = "{\"username\":\"bob\",\"identifier\":\"bob1987\", \"foo\" : \"bar\", \"fooArr\" : [ 1, 2, 3], \"fooObj\" : { \"baz\" : \"qux\" } }"
|
||||
|
||||
let user = userMapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(user)
|
||||
}
|
||||
|
||||
func testInvalidJsonResultsInNilObject() {
|
||||
let JSONString = "{\"username\":\"bob\",\"identifier\":\"bob1987\"" // missing ending brace
|
||||
|
||||
let user = userMapper.map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNil(user)
|
||||
}
|
||||
|
||||
func testMapArrayJSON(){
|
||||
let name1 = "Bob"
|
||||
let name2 = "Jane"
|
||||
|
||||
let JSONString = "[{\"name\": \"\(name1)\", \"UUID\": \"3C074D4B-FC8C-4CA2-82A9-6E9367BBC875\", \"major\": 541, \"minor\": 123},{ \"name\": \"\(name2)\", \"UUID\": \"3C074D4B-FC8C-4CA2-82A9-6E9367BBC876\", \"major\": 54321,\"minor\": 13 }]"
|
||||
|
||||
let students = Mapper<Student>().mapArray(JSONString: JSONString)
|
||||
|
||||
XCTAssertTrue(students?.count ?? 0 > 0)
|
||||
XCTAssertTrue(students?.count == 2)
|
||||
XCTAssertEqual(students?[0].name, name1)
|
||||
XCTAssertEqual(students?[1].name, name2)
|
||||
}
|
||||
|
||||
// test mapArray() with JSON string that is not an array form
|
||||
// should return a collection with one item
|
||||
func testMapArrayJSONWithNoArray(){
|
||||
let name1 = "Bob"
|
||||
|
||||
let JSONString = "{\"name\": \"\(name1)\", \"UUID\": \"3C074D4B-FC8C-4CA2-82A9-6E9367BBC875\", \"major\": 541, \"minor\": 123}"
|
||||
|
||||
let students = Mapper<Student>().mapArray(JSONString: JSONString)
|
||||
|
||||
XCTAssertTrue(students?.count ?? 0 > 0)
|
||||
XCTAssertTrue(students?.count == 1)
|
||||
XCTAssertEqual(students?[0].name, name1)
|
||||
}
|
||||
|
||||
func testMapArrayJSONWithEmptyArray() {
|
||||
let JSONString = "[]"
|
||||
|
||||
let students = Mapper<Student>().mapArray(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(students)
|
||||
XCTAssertTrue(students?.count == 0)
|
||||
}
|
||||
|
||||
func testArrayOfCustomObjects(){
|
||||
let percentage1: Double = 0.1
|
||||
let percentage2: Double = 1792.41
|
||||
|
||||
let JSONString = "{ \"tasks\": [{\"taskId\":103,\"percentage\":\(percentage1)},{\"taskId\":108,\"percentage\":\(percentage2)}] }"
|
||||
|
||||
let plan = Mapper<Plan>().map(JSONString: JSONString)
|
||||
|
||||
let tasks = plan?.tasks
|
||||
|
||||
XCTAssertNotNil(tasks)
|
||||
XCTAssertEqual(tasks?[0].percentage, percentage1)
|
||||
XCTAssertEqual(tasks?[1].percentage, percentage2)
|
||||
}
|
||||
|
||||
func testDictionaryOfArrayOfCustomObjects(){
|
||||
let percentage1: Double = 0.1
|
||||
let percentage2: Double = 1792.41
|
||||
|
||||
let JSONString = "{ \"dictionaryOfTasks\": { \"mondayTasks\" :[{\"taskId\":103,\"percentage\":\(percentage1)},{\"taskId\":108,\"percentage\":\(percentage2)}] } }"
|
||||
|
||||
let plan = Mapper<Plan>().map(JSONString: JSONString)
|
||||
|
||||
let dictionaryOfTasks = plan?.dictionaryOfTasks
|
||||
XCTAssertNotNil(dictionaryOfTasks)
|
||||
XCTAssertEqual(dictionaryOfTasks?["mondayTasks"]?[0].percentage, percentage1)
|
||||
XCTAssertEqual(dictionaryOfTasks?["mondayTasks"]?[1].percentage, percentage2)
|
||||
|
||||
let planToJSON = Mapper().toJSONString(plan!, prettyPrint: true)
|
||||
//print(planToJSON!)
|
||||
let planFromJSON = Mapper<Plan>().map(JSONString: planToJSON!)
|
||||
|
||||
let dictionaryOfTasks2 = planFromJSON?.dictionaryOfTasks
|
||||
XCTAssertNotNil(dictionaryOfTasks2)
|
||||
XCTAssertEqual(dictionaryOfTasks2?["mondayTasks"]?[0].percentage, percentage1)
|
||||
XCTAssertEqual(dictionaryOfTasks2?["mondayTasks"]?[1].percentage, percentage2)
|
||||
}
|
||||
|
||||
func testArrayOfEnumObjects(){
|
||||
let a: ExampleEnum = .a
|
||||
let b: ExampleEnum = .b
|
||||
let c: ExampleEnum = .c
|
||||
|
||||
let JSONString = "{ \"enums\": [\(a.rawValue), \(b.rawValue), \(c.rawValue)] }"
|
||||
|
||||
let enumArray = Mapper<ExampleEnumArray>().map(JSONString: JSONString)
|
||||
let enums = enumArray?.enums
|
||||
|
||||
XCTAssertNotNil(enums)
|
||||
XCTAssertTrue(enums?.count == 3)
|
||||
XCTAssertEqual(enums?[0], a)
|
||||
XCTAssertEqual(enums?[1], b)
|
||||
XCTAssertEqual(enums?[2], c)
|
||||
}
|
||||
|
||||
func testDictionaryOfCustomObjects(){
|
||||
let percentage1: Double = 0.1
|
||||
let percentage2: Double = 1792.41
|
||||
|
||||
let JSONString = "{\"tasks\": { \"task1\": {\"taskId\":103,\"percentage\":\(percentage1)}, \"task2\": {\"taskId\":108,\"percentage\":\(percentage2)}}}"
|
||||
|
||||
let taskDict = Mapper<TaskDictionary>().map(JSONString: JSONString)
|
||||
|
||||
let task = taskDict?.tasks?["task1"]
|
||||
XCTAssertNotNil(task)
|
||||
XCTAssertEqual(task?.percentage, percentage1)
|
||||
}
|
||||
|
||||
func testDictionryOfEnumObjects(){
|
||||
let a: ExampleEnum = .a
|
||||
let b: ExampleEnum = .b
|
||||
let c: ExampleEnum = .c
|
||||
|
||||
let JSONString = "{ \"enums\": {\"A\": \(a.rawValue), \"B\": \(b.rawValue), \"C\": \(c.rawValue)} }"
|
||||
|
||||
let enumDict = Mapper<ExampleEnumDictionary>().map(JSONString: JSONString)
|
||||
let enums = enumDict?.enums
|
||||
|
||||
XCTAssertNotNil(enums)
|
||||
XCTAssertTrue(enums?.count == 3)
|
||||
}
|
||||
|
||||
func testDoubleParsing(){
|
||||
let percentage1: Double = 1792.41
|
||||
|
||||
let JSONString = "{\"taskId\":103,\"percentage\":\(percentage1)}"
|
||||
|
||||
let task = Mapper<Task>().map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(task)
|
||||
XCTAssertEqual(task?.percentage, percentage1)
|
||||
}
|
||||
|
||||
func testToJSONArray(){
|
||||
let task1 = Task()
|
||||
task1.taskId = 1
|
||||
task1.percentage = 11.1
|
||||
let task2 = Task()
|
||||
task2.taskId = 2
|
||||
task2.percentage = 22.2
|
||||
let task3 = Task()
|
||||
task3.taskId = 3
|
||||
task3.percentage = 33.3
|
||||
|
||||
let taskArray = [task1, task2, task3]
|
||||
|
||||
let JSONArray = Mapper().toJSONArray(taskArray)
|
||||
|
||||
let taskId1 = JSONArray[0]["taskId"] as? Int
|
||||
let percentage1 = JSONArray[0]["percentage"] as? Double
|
||||
|
||||
XCTAssertEqual(taskId1, task1.taskId)
|
||||
XCTAssertEqual(percentage1, task1.percentage)
|
||||
|
||||
let taskId2 = JSONArray[1]["taskId"] as? Int
|
||||
let percentage2 = JSONArray[1]["percentage"] as? Double
|
||||
|
||||
XCTAssertEqual(taskId2, task2.taskId)
|
||||
XCTAssertEqual(percentage2, task2.percentage)
|
||||
|
||||
let taskId3 = JSONArray[2]["taskId"] as? Int
|
||||
let percentage3 = JSONArray[2]["percentage"] as? Double
|
||||
|
||||
XCTAssertEqual(taskId3, task3.taskId)
|
||||
XCTAssertEqual(percentage3, task3.percentage)
|
||||
}
|
||||
|
||||
func testArrayOfArrayOfMappable() {
|
||||
let base1 = "1"
|
||||
let base2 = "2"
|
||||
let base3 = "3"
|
||||
let base4 = "4"
|
||||
|
||||
let array1 = [["base": base1], ["base": base2], ["base": base3]]
|
||||
let array2 = [["base": base4]]
|
||||
let JSON = ["twoDimensionalArray":[array1, array2]]
|
||||
|
||||
let arrayTest = Mapper<ArrayTest>().map(JSON: JSON)
|
||||
|
||||
XCTAssertNotNil(arrayTest)
|
||||
XCTAssertEqual(arrayTest?.twoDimensionalArray?[0][0].base, base1)
|
||||
XCTAssertEqual(arrayTest?.twoDimensionalArray?[0][1].base, base2)
|
||||
XCTAssertEqual(arrayTest?.twoDimensionalArray?[0][2].base, base3)
|
||||
XCTAssertEqual(arrayTest?.twoDimensionalArray?[1][0].base, base4)
|
||||
|
||||
XCTAssertEqual(arrayTest?.twoDimensionalArray?[0].count, array1.count)
|
||||
XCTAssertEqual(arrayTest?.twoDimensionalArray?[1].count, array2.count)
|
||||
|
||||
let backToJSON = Mapper<ArrayTest>().toJSON(arrayTest!)
|
||||
XCTAssertNotNil(backToJSON)
|
||||
|
||||
let arrayTest2 = Mapper<ArrayTest>().map(JSON: backToJSON)
|
||||
XCTAssertNotNil(arrayTest2)
|
||||
XCTAssertEqual(arrayTest2?.twoDimensionalArray?[0][0].base, arrayTest?.twoDimensionalArray?[0][0].base)
|
||||
XCTAssertEqual(arrayTest2?.twoDimensionalArray?[0][1].base, arrayTest?.twoDimensionalArray?[0][1].base)
|
||||
}
|
||||
|
||||
func testShouldPreventOverwritingMappableProperty() {
|
||||
let json: [String: Any] = [
|
||||
"name": "Entry 1",
|
||||
"bigList": [["name": "item 1"], ["name": "item 2"], ["name": "item 3"]]
|
||||
]
|
||||
let model = CachedModel()
|
||||
_ = Mapper().map(JSON: json, toObject: model)
|
||||
|
||||
XCTAssertEqual(model.name, "Entry 1")
|
||||
XCTAssertEqual(model.bigList?.count, 3)
|
||||
|
||||
let json2: [String: Any] = ["name": "Entry 1"]
|
||||
_ = Mapper().map(JSON: json2, toObject: model)
|
||||
|
||||
XCTAssertEqual(model.name, "Entry 1")
|
||||
XCTAssertEqual(model.bigList?.count, 3)
|
||||
}
|
||||
}
|
||||
|
||||
class Status: Mappable {
|
||||
var status: Int?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
status <- map["code"]
|
||||
}
|
||||
}
|
||||
|
||||
class Plan: Mappable {
|
||||
var tasks: [Task]?
|
||||
var dictionaryOfTasks: [String: [Task]]?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
tasks <- map["tasks"]
|
||||
dictionaryOfTasks <- map["dictionaryOfTasks"]
|
||||
}
|
||||
}
|
||||
|
||||
class Task: Mappable {
|
||||
var taskId: Int?
|
||||
var percentage: Double?
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
taskId <- map["taskId"]
|
||||
percentage <- map["percentage"]
|
||||
}
|
||||
}
|
||||
|
||||
class TaskDictionary: Mappable {
|
||||
var test: String?
|
||||
var tasks: [String : Task]?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
test <- map["test"]
|
||||
tasks <- map["tasks"]
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Confirm that struct can conform to `Mappable`
|
||||
struct Student: Mappable {
|
||||
var name: String?
|
||||
var UUID: String?
|
||||
var major: Int?
|
||||
var minor: Int?
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
name <- map["name"]
|
||||
UUID <- map["UUID"]
|
||||
major <- map["major"]
|
||||
minor <- map["minor"]
|
||||
}
|
||||
}
|
||||
|
||||
enum Sex: String {
|
||||
case Male = "Male"
|
||||
case Female = "Female"
|
||||
}
|
||||
|
||||
class User: Mappable {
|
||||
|
||||
var username: String = ""
|
||||
var identifier: String?
|
||||
var photoCount: Int = 0
|
||||
var age: Int?
|
||||
var weight: Double?
|
||||
var float: Float?
|
||||
var drinker: Bool = false
|
||||
var smoker: Bool?
|
||||
var sex: Sex?
|
||||
var canDrive: Bool?
|
||||
var arr: [Any] = []
|
||||
var arrOptional: [Any]?
|
||||
var dict: [String : Any] = [:]
|
||||
var dictOptional: [String : Any]?
|
||||
var dictString: [String : String]?
|
||||
var friendDictionary: [String : User]?
|
||||
var friend: User?
|
||||
var friends: [User]? = []
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
username <- map["username"]
|
||||
identifier <- map["identifier"]
|
||||
photoCount <- map["photoCount"]
|
||||
age <- map["age"]
|
||||
weight <- map["weight"]
|
||||
float <- map["float"]
|
||||
drinker <- map["drinker"]
|
||||
smoker <- map["smoker"]
|
||||
sex <- map["sex"]
|
||||
canDrive <- map["canDrive"]
|
||||
arr <- map["arr"]
|
||||
arrOptional <- map["arrOpt"]
|
||||
dict <- map["dict"]
|
||||
dictOptional <- map["dictOpt"]
|
||||
friend <- map["friend"]
|
||||
friends <- map["friends"]
|
||||
friendDictionary <- map["friendDictionary"]
|
||||
dictString <- map["dictString"]
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
enum ExampleEnum: Int {
|
||||
case a
|
||||
case b
|
||||
case c
|
||||
}
|
||||
|
||||
class ExampleEnumArray: Mappable {
|
||||
var enums: [ExampleEnum] = []
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
enums <- map["enums"]
|
||||
}
|
||||
}
|
||||
|
||||
class ExampleEnumDictionary: Mappable {
|
||||
var enums: [String: ExampleEnum] = [:]
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
enums <- map["enums"]
|
||||
}
|
||||
}
|
||||
|
||||
class ArrayTest: Mappable {
|
||||
|
||||
var twoDimensionalArray: Array<Array<Base>>?
|
||||
|
||||
required init?(map: Map){}
|
||||
|
||||
func mapping(map: Map) {
|
||||
twoDimensionalArray <- map["twoDimensionalArray"]
|
||||
}
|
||||
}
|
||||
|
||||
class CachedModel: Mappable {
|
||||
var name: String?
|
||||
var bigList: [CachedItem]?
|
||||
|
||||
init() {}
|
||||
|
||||
required init?(map: Map){}
|
||||
|
||||
func mapping(map: Map) {
|
||||
name <- map["name"]
|
||||
bigList <- map["bigList"]
|
||||
}
|
||||
}
|
||||
|
||||
struct CachedItem: Mappable {
|
||||
var name: String?
|
||||
|
||||
init?(map: Map){}
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
name <- map["name"]
|
||||
}
|
||||
}
|
|
@ -1,174 +0,0 @@
|
|||
//
|
||||
// PerformanceTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-09-21.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class PerformanceTests: XCTestCase {
|
||||
|
||||
let JSONTestString: String = {
|
||||
let subObjectJSON = "{\"string\":\"This is a string\", \"int\": 12,\"double\":12.27,\"float\":12.3212, \"bool\":false, \"arr\":[ \"bla\", true, 42 ], \"dict\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 } }"
|
||||
|
||||
let objectJSONString = "{\"string\":\"This is a string\", \"int\": 12,\"double\":12.27,\"float\":12.3212, \"bool\":false, \"arr\":[ \"bla\", true, 42 ], \"dict\":{ \"key1\" : \"value1\", \"key2\" : false, \"key3\" : 142 }, \"object\": \(subObjectJSON), \"objects\":{ \"key1\": \(subObjectJSON), \"key2\": \(subObjectJSON)}}"
|
||||
|
||||
var JSONString = "["
|
||||
for _ in 0...1000 {
|
||||
JSONString += "\(objectJSONString),"
|
||||
}
|
||||
JSONString += "\(objectJSONString)]"
|
||||
return JSONString
|
||||
}()
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testPerformance() {
|
||||
self.measure {
|
||||
// Put the code you want to measure the time of here.
|
||||
_ = Mapper<PerformanceMappableObject>().mapArray(JSONString: self.JSONTestString)
|
||||
}
|
||||
}
|
||||
|
||||
func testPerformanceCluster() {
|
||||
self.measure {
|
||||
// Put the code you want to measure the time of here.
|
||||
_ = Mapper<PerformanceStaticMappableObject>().mapArray(JSONString: self.JSONTestString)
|
||||
}
|
||||
}
|
||||
|
||||
func testPerformanceImmutable() {
|
||||
self.measure {
|
||||
_ = try? Mapper<PerformanceImmutableMappableObject>().mapArray(JSONString: self.JSONTestString)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class PerformanceMappableObject: Mappable {
|
||||
|
||||
var string: String?
|
||||
var int: Int?
|
||||
var double: Double?
|
||||
var float: Float?
|
||||
var bool: Bool?
|
||||
var array: [Any]?
|
||||
var dictionary: [String: Any]?
|
||||
var object: PerformanceMappableObject?
|
||||
var objects: [PerformanceMappableObject]?
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
string <- map["string"]
|
||||
int <- map["int"]
|
||||
double <- map["double"]
|
||||
float <- map["float"]
|
||||
bool <- map["bool"]
|
||||
array <- map["array"]
|
||||
dictionary <- map["dictionary"]
|
||||
object <- map["object"]
|
||||
objects <- map["objects"]
|
||||
}
|
||||
}
|
||||
|
||||
class PerformanceStaticMappableObject: StaticMappable {
|
||||
|
||||
var string: String?
|
||||
var int: Int?
|
||||
var double: Double?
|
||||
var float: Float?
|
||||
var bool: Bool?
|
||||
var array: [Any]?
|
||||
var dictionary: [String: Any]?
|
||||
var object: PerformanceStaticMappableObject?
|
||||
var objects: [PerformanceStaticMappableObject]?
|
||||
|
||||
static func objectForMapping(map: Map) -> BaseMappable? {
|
||||
return PerformanceStaticMappableObject()
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
string <- map["string"]
|
||||
int <- map["int"]
|
||||
double <- map["double"]
|
||||
float <- map["float"]
|
||||
bool <- map["bool"]
|
||||
array <- map["array"]
|
||||
dictionary <- map["dictionary"]
|
||||
object <- map["object"]
|
||||
objects <- map["objects"]
|
||||
}
|
||||
}
|
||||
|
||||
class PerformanceImmutableMappableObject: ImmutableMappable {
|
||||
|
||||
let string: String?
|
||||
let int: Int?
|
||||
let double: Double?
|
||||
let float: Float?
|
||||
let bool: Bool?
|
||||
let array: [Any]?
|
||||
let dictionary: [String: Any]?
|
||||
let object: PerformanceImmutableMappableObject?
|
||||
let objects: [PerformanceImmutableMappableObject]?
|
||||
|
||||
required init(map: Map) throws {
|
||||
string = try map.value("string")
|
||||
int = try map.value("int")
|
||||
double = try map.value("double")
|
||||
float = try map.value("float")
|
||||
bool = try map.value("bool")
|
||||
array = try map.value("array")
|
||||
dictionary = try map.value("dictionary")
|
||||
object = try map.value("object")
|
||||
objects = try map.value("objects")
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
string >>> map["string"]
|
||||
int >>> map["int"]
|
||||
double >>> map["double"]
|
||||
float >>> map["float"]
|
||||
bool >>> map["bool"]
|
||||
array >>> map["array"]
|
||||
dictionary >>> map["dictionary"]
|
||||
object >>> map["object"]
|
||||
objects >>> map["objects"]
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1,207 +0,0 @@
|
|||
//
|
||||
// ReferenceTypesFromJSON.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by Tristan Himmelman on 2015-11-29.
|
||||
//
|
||||
// The MIT License (MIT)
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import Foundation
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class ToObjectTests: XCTestCase {
|
||||
|
||||
override func setUp() {
|
||||
super.setUp()
|
||||
// Put setup code here. This method is called before the invocation of each test method in the class.
|
||||
}
|
||||
|
||||
override func tearDown() {
|
||||
// Put teardown code here. This method is called after the invocation of each test method in the class.
|
||||
super.tearDown()
|
||||
}
|
||||
|
||||
func testMappingPersonFromJSON(){
|
||||
let name = "ASDF"
|
||||
let spouseName = "HJKL"
|
||||
let JSONString = "{\"name\" : \"\(name)\", \"spouse\" : {\"name\" : \"\(spouseName)\"}}"
|
||||
|
||||
let mappedObject = Mapper<Person>().map(JSONString: JSONString)
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertEqual(mappedObject?.name, name)
|
||||
XCTAssertEqual(mappedObject?.spouse?.name, spouseName)
|
||||
}
|
||||
|
||||
func testUpdatingChildObject(){
|
||||
let name = "ASDF"
|
||||
let initialSpouseName = "HJKL"
|
||||
let updatedSpouseName = "QWERTY"
|
||||
let initialJSONString = "{\"name\" : \"\(name)\", \"spouse\" : {\"name\" : \"\(initialSpouseName)\"}}"
|
||||
let updatedJSONString = "{\"name\" : \"\(name)\", \"spouse\" : {\"name\" : \"\(updatedSpouseName)\"}}"
|
||||
|
||||
let mappedObject = Mapper<Person>().map(JSONString: initialJSONString)
|
||||
let initialSpouse = mappedObject?.spouse
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
|
||||
let updatedObject = Mapper<Person>().map(JSONString: updatedJSONString, toObject: mappedObject!)
|
||||
|
||||
XCTAssert(initialSpouse === updatedObject.spouse, "Expected mapping to update the existing object not create a new one")
|
||||
XCTAssertEqual(updatedObject.spouse?.name, updatedSpouseName)
|
||||
XCTAssertEqual(initialSpouse?.name, updatedSpouseName)
|
||||
}
|
||||
|
||||
func testUpdatingChildDictionary(){
|
||||
let childKey = "child_1"
|
||||
let initialChildName = "HJKL"
|
||||
let updatedChildName = "QWERTY"
|
||||
let initialJSONString = "{\"children\" : {\"\(childKey)\" : {\"name\" : \"\(initialChildName)\"}}}"
|
||||
let updatedJSONString = "{\"children\" : {\"\(childKey)\" : {\"name\" : \"\(updatedChildName)\"}}}"
|
||||
|
||||
let mappedObject = Mapper<Person>().map(JSONString: initialJSONString)
|
||||
let initialChild = mappedObject?.children?[childKey]
|
||||
|
||||
XCTAssertNotNil(mappedObject)
|
||||
XCTAssertNotNil(initialChild)
|
||||
XCTAssertEqual(initialChild?.name, initialChildName)
|
||||
|
||||
_ = Mapper<Person>().map(JSONString: updatedJSONString, toObject: mappedObject!)
|
||||
|
||||
let updatedChild = mappedObject?.children?[childKey]
|
||||
XCTAssert(initialChild === updatedChild, "Expected mapping to update the existing object not create a new one")
|
||||
XCTAssertEqual(updatedChild?.name, updatedChildName)
|
||||
XCTAssertEqual(initialChild?.name, updatedChildName)
|
||||
}
|
||||
|
||||
func testToObjectFromString() {
|
||||
let username = "bob"
|
||||
let JSONString = "{\"username\":\"\(username)\"}"
|
||||
|
||||
let user = User()
|
||||
user.username = "Tristan"
|
||||
|
||||
_ = Mapper().map(JSONString: JSONString, toObject: user)
|
||||
|
||||
XCTAssertEqual(user.username, username)
|
||||
}
|
||||
|
||||
func testToObjectFromJSON() {
|
||||
let username = "bob"
|
||||
let JSON = ["username": username]
|
||||
|
||||
let user = User()
|
||||
user.username = "Tristan"
|
||||
|
||||
_ = Mapper().map(JSON: JSON, toObject: user)
|
||||
|
||||
XCTAssertEqual(username, user.username)
|
||||
}
|
||||
|
||||
func testToObjectFromAny() {
|
||||
let username = "bob"
|
||||
let userJSON = ["username": username]
|
||||
|
||||
let user = User()
|
||||
user.username = "Tristan"
|
||||
|
||||
_ = Mapper().map(JSONObject: userJSON as Any, toObject: user)
|
||||
|
||||
XCTAssertEqual(user.username, username)
|
||||
}
|
||||
|
||||
class Person: Mappable {
|
||||
var name: String?
|
||||
var spouse: Person?
|
||||
var children: [String: Person]?
|
||||
|
||||
required init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
name <- map["name"]
|
||||
spouse <- map["spouse"]
|
||||
children <- map["children"]
|
||||
}
|
||||
}
|
||||
|
||||
class User: Mappable {
|
||||
|
||||
var username: String = ""
|
||||
|
||||
init(){
|
||||
|
||||
}
|
||||
|
||||
required init?(map: Map){
|
||||
|
||||
}
|
||||
|
||||
func mapping(map: Map) {
|
||||
username <- map["username"]
|
||||
}
|
||||
}
|
||||
|
||||
struct HumanInfo: Mappable {
|
||||
var name: String?
|
||||
|
||||
init(name: String) {
|
||||
self.name = name
|
||||
}
|
||||
|
||||
init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
name <- map["name"]
|
||||
}
|
||||
}
|
||||
|
||||
struct Human: Mappable {
|
||||
var info: HumanInfo?
|
||||
|
||||
init(name: String) {
|
||||
info = HumanInfo(name: name)
|
||||
}
|
||||
|
||||
init?(map: Map) {
|
||||
|
||||
}
|
||||
|
||||
mutating func mapping(map: Map) {
|
||||
info <- map["info"]
|
||||
}
|
||||
}
|
||||
|
||||
func testConsume() {
|
||||
var human1 = Human(name: "QW") //has a with name "QW"
|
||||
let human2 = Human(name: "ER") //has a with name "ER"
|
||||
human1 = Mapper().map(JSON: human2.toJSON(), toObject: human1)
|
||||
|
||||
XCTAssertEqual(human1.info?.name, human2.info?.name)
|
||||
}
|
||||
}
|
||||
|
|
@ -1,49 +0,0 @@
|
|||
//
|
||||
// URLTransformTests.swift
|
||||
// ObjectMapper
|
||||
//
|
||||
// Created by pawel-rusin on 4/7/17.
|
||||
//
|
||||
// Copyright (c) 2014-2018 Tristan Himmelman
|
||||
//
|
||||
// Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
// of this software and associated documentation files (the "Software"), to deal
|
||||
// in the Software without restriction, including without limitation the rights
|
||||
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
// copies of the Software, and to permit persons to whom the Software is
|
||||
// furnished to do so, subject to the following conditions:
|
||||
//
|
||||
// The above copyright notice and this permission notice shall be included in
|
||||
// all copies or substantial portions of the Software.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
// THE SOFTWARE.
|
||||
|
||||
import XCTest
|
||||
import ObjectMapper
|
||||
|
||||
class URLTransformTests: XCTestCase {
|
||||
|
||||
func testUrlQueryAllowed() {
|
||||
let urlTransform = URLTransform()
|
||||
let input = "https://example.com/search?query=foo"
|
||||
let output = urlTransform.transformFromJSON(input)
|
||||
|
||||
XCTAssertEqual(output, URL(string: "https://example.com/search?query=foo"))
|
||||
}
|
||||
|
||||
func testCanPassInAllowedCharacterSet() {
|
||||
var characterSet = CharacterSet.urlQueryAllowed
|
||||
characterSet.insert(charactersIn: "%")
|
||||
let urlTransform = URLTransform(allowedCharacterSet: characterSet)
|
||||
let input = "https://example.com/%25"
|
||||
let output = urlTransform.transformFromJSON(input)
|
||||
|
||||
XCTAssertEqual(output, URL(string: "https://example.com/%25"))
|
||||
}
|
||||
}
|
Binary file not shown.
After Width: | Height: | Size: 78 B |
Binary file not shown.
After Width: | Height: | Size: 463 B |
Binary file not shown.
After Width: | Height: | Size: 216 B |
Binary file not shown.
After Width: | Height: | Size: 14 KiB |
|
@ -0,0 +1,136 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
|
||||
<head>
|
||||
<meta charset='utf-8'>
|
||||
<meta http-equiv="X-UA-Compatible" content="chrome=1">
|
||||
<meta name="description" content="ObjectMapper : JSON Object mapping written in Swift">
|
||||
|
||||
<link rel="stylesheet" type="text/css" media="screen" href="stylesheets/stylesheet.css">
|
||||
|
||||
<title>ObjectMapper</title>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
|
||||
<!-- HEADER -->
|
||||
<div id="header_wrap" class="outer">
|
||||
<header class="inner">
|
||||
<a id="forkme_banner" href="https://github.com/Hearst-DD/ObjectMapper">View on GitHub</a>
|
||||
|
||||
<h1 id="project_title">ObjectMapper</h1>
|
||||
<h2 id="project_tagline">JSON Object mapping written in Swift</h2>
|
||||
|
||||
<section id="downloads">
|
||||
<a class="zip_download_link" href="https://github.com/Hearst-DD/ObjectMapper/zipball/master">Download this project as a .zip file</a>
|
||||
<a class="tar_download_link" href="https://github.com/Hearst-DD/ObjectMapper/tarball/master">Download this project as a tar.gz file</a>
|
||||
</section>
|
||||
</header>
|
||||
</div>
|
||||
|
||||
<!-- MAIN CONTENT -->
|
||||
<div id="main_content_wrap" class="outer">
|
||||
<section id="main_content" class="inner">
|
||||
<p>ObjectMapper is a framework written in Swift that makes it easy for you to convert your Model objects to and from JSON. </p>
|
||||
|
||||
<p>Features:</p>
|
||||
|
||||
<ul>
|
||||
<li>Mapping JSON to objects</li>
|
||||
<li>Mapping objects to JSON</li>
|
||||
<li>Nested Objects (stand alone, in Arrays or in Dictionaries)</li>
|
||||
<li>Custom transformations during mapping</li>
|
||||
</ul>
|
||||
|
||||
<p>To support mapping, a class just needs to implement the MapperProtocol. ObjectMapper uses the "<=" operator to define how each member variable maps to and from JSON.</p>
|
||||
|
||||
<div class="highlight highlight-swift"><pre><span class="k">class</span> <span class="nl">User</span><span class="p">:</span> <span class="n">MapperProtocol</span> <span class="p">{</span>
|
||||
|
||||
<span class="k">var</span> <span class="nl">username</span><span class="p">:</span> <span class="n">String</span><span class="o">?</span>
|
||||
<span class="k">var</span> <span class="nl">age</span><span class="p">:</span> <span class="n">Int</span><span class="o">?</span>
|
||||
<span class="k">var</span> <span class="nl">weight</span><span class="p">:</span> <span class="n">Double</span><span class="o">?</span>
|
||||
<span class="k">var</span> <span class="nl">arr</span><span class="p">:</span> <span class="p">[</span><span class="n">AnyObject</span><span class="p">]</span><span class="o">?</span>
|
||||
<span class="k">var</span> <span class="nl">dict</span><span class="p">:</span> <span class="p">[</span><span class="nl">String</span> <span class="p">:</span> <span class="n">AnyObject</span><span class="p">]</span> <span class="o">=</span> <span class="p">[</span><span class="o">:</span><span class="p">]</span>
|
||||
<span class="k">var</span> <span class="nl">friend</span><span class="p">:</span> <span class="n">User</span><span class="o">?</span>
|
||||
<span class="k">var</span> <span class="nl">birthday</span><span class="p">:</span> <span class="bp">NSDate</span><span class="o">?</span>
|
||||
|
||||
<span class="c1">// MapperProtocol </span>
|
||||
<span class="k">class</span> <span class="k">func</span> <span class="n">map</span><span class="p">(</span><span class="nl">mapper</span><span class="p">:</span> <span class="n">Mapper</span><span class="p">,</span> <span class="nl">object</span><span class="p">:</span> <span class="n">User</span><span class="p">)</span> <span class="p">{</span>
|
||||
<span class="n">object</span><span class="p">.</span><span class="n">username</span> <span class="o"><=</span> <span class="n">mapper</span><span class="p">[</span><span class="s">"username"</span><span class="p">]</span>
|
||||
<span class="n">object</span><span class="p">.</span><span class="n">age</span> <span class="o"><=</span> <span class="n">mapper</span><span class="p">[</span><span class="s">"age"</span><span class="p">]</span>
|
||||
<span class="n">object</span><span class="p">.</span><span class="n">weight</span> <span class="o"><=</span> <span class="n">mapper</span><span class="p">[</span><span class="s">"weight"</span><span class="p">]</span>
|
||||
<span class="n">object</span><span class="p">.</span><span class="n">arr</span> <span class="o"><=</span> <span class="n">mapper</span><span class="p">[</span><span class="s">"arr"</span><span class="p">]</span>
|
||||
<span class="n">object</span><span class="p">.</span><span class="n">dict</span> <span class="o"><=</span> <span class="n">mapper</span><span class="p">[</span><span class="s">"dict"</span><span class="p">]</span>
|
||||
<span class="n">object</span><span class="p">.</span><span class="n">friend</span> <span class="o"><=</span> <span class="n">mapper</span><span class="p">[</span><span class="s">"friend"</span><span class="p">]</span>
|
||||
<span class="n">object</span><span class="p">.</span><span class="n">birthday</span> <span class="o"><=</span> <span class="p">(</span><span class="n">mapper</span><span class="p">[</span><span class="s">"birthday"</span><span class="p">],</span> <span class="n">DateTransform</span><span class="o"><</span><span class="bp">NSDate</span><span class="p">,</span> <span class="n">Int</span><span class="o">></span><span class="p">())</span>
|
||||
<span class="p">}</span>
|
||||
<span class="p">}</span>
|
||||
</pre></div>
|
||||
|
||||
<p>Once your class implements MapperProtocol, the Mapper class handles everything else for you:</p>
|
||||
|
||||
<p>Convert a JSON string to a model object:</p>
|
||||
|
||||
<div class="highlight highlight-swift"><pre><span class="k">let</span> <span class="n">user</span> <span class="o">=</span> <span class="n">Mapper</span><span class="p">().</span><span class="n">map</span><span class="p">(</span><span class="n">JSONString</span><span class="p">,</span> <span class="nl">to</span><span class="p">:</span> <span class="n">User</span><span class="p">.</span><span class="nb">self</span><span class="p">)</span>
|
||||
</pre></div>
|
||||
|
||||
<p>Convert a model object to a JSON string:</p>
|
||||
|
||||
<div class="highlight highlight-swift"><pre>
|
||||
<span class="k">let</span> <span class="n">JSONString</span> <span class="o">=</span> <span class="n">Mapper</span><span class="p">().</span><span class="n">toJSONString</span><span class="p">(</span><span class="n">user</span><span class="p">)</span>
|
||||
</pre></div>
|
||||
|
||||
<p>Object mapper can handle classes composed of the following types:</p>
|
||||
|
||||
<ul>
|
||||
<li>Int</li>
|
||||
<li>Bool</li>
|
||||
<li>Double</li>
|
||||
<li>Float</li>
|
||||
<li>String</li>
|
||||
<li>Array<AnyObject></li>
|
||||
<li>Dictionary<String, AnyObject></li>
|
||||
<li>Optionals of all the abovee</li>
|
||||
<li>Object<T: MapperProtocol></li>
|
||||
<li>Array<T: MapperProtocol></li>
|
||||
<li>Dictionary<String, T: MapperProtocol></li>
|
||||
</ul>
|
||||
|
||||
<p>ObjectMapper also supports Transforms that convert values during the mapping process. To use a transform, simply create a tuple with the mapper["field_name"] and the transform of choice on the right side of the '<=' operator:</p>
|
||||
|
||||
<div class="highlight highlight-swift"><pre><span class="n">object</span><span class="p">.</span><span class="n">birthday</span> <span class="o"><=</span> <span class="p">(</span><span class="n">mapper</span><span class="p">[</span><span class="s">"birthday"</span><span class="p">],</span> <span class="n">DateTransform</span><span class="o"><</span><span class="bp">NSDate</span><span class="p">,</span> <span class="n">Int</span><span class="o">></span><span class="p">())</span>
|
||||
</pre></div>
|
||||
|
||||
<p>The above transform will convert the JSON Int value to an NSDate when reading JSON and will convert the NSDate to an Int when converting objects to JSON.</p>
|
||||
|
||||
<p>You can easily create your own custom transforms by subclassing and overriding the methods in the MapperTransform class:</p>
|
||||
|
||||
<div class="highlight highlight-swift"><pre><span class="n">public</span> <span class="k">class</span> <span class="n">MapperTransform</span><span class="o"><</span><span class="n">ObjectType</span><span class="p">,</span> <span class="n">JSONType</span><span class="o">></span> <span class="p">{</span>
|
||||
<span class="k">init</span><span class="p">(){</span>
|
||||
|
||||
<span class="p">}</span>
|
||||
|
||||
<span class="k">func</span> <span class="n">transformFromJSON</span><span class="p">(</span><span class="nl">value</span><span class="p">:</span> <span class="n">AnyObject</span><span class="o">?</span><span class="p">)</span> <span class="o">-></span> <span class="n">ObjectType</span><span class="o">?</span> <span class="p">{</span>
|
||||
<span class="k">return</span> <span class="nb">nil</span>
|
||||
<span class="p">}</span>
|
||||
|
||||
<span class="k">func</span> <span class="n">transformToJSON</span><span class="p">(</span><span class="nl">value</span><span class="p">:</span> <span class="n">ObjectType</span><span class="o">?</span><span class="p">)</span> <span class="o">-></span> <span class="n">JSONType</span><span class="o">?</span> <span class="p">{</span>
|
||||
<span class="k">return</span> <span class="nb">nil</span>
|
||||
<span class="p">}</span>
|
||||
<span class="p">}</span>
|
||||
</pre></div>
|
||||
</section>
|
||||
</div>
|
||||
|
||||
<!-- FOOTER -->
|
||||
<div id="footer_wrap" class="outer">
|
||||
<footer class="inner">
|
||||
<p class="copyright">ObjectMapper maintained by <a href="https://github.com/Hearst-DD">Hearst-DD</a></p>
|
||||
<p>Published with <a href="http://pages.github.com">GitHub Pages</a></p>
|
||||
</footer>
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
</body>
|
||||
</html>
|
|
@ -0,0 +1 @@
|
|||
console.log('This would be the main JS file.');
|
|
@ -0,0 +1 @@
|
|||
{"name":"ObjectMapper","tagline":"JSON Object mapping written in Swift","body":"ObjectMapper is a framework written in Swift that makes it easy for you to convert your Model objects to and from JSON. \r\n\r\nFeatures:\r\n- Mapping JSON to objects\r\n- Mapping objects to JSON\r\n- Nested Objects (stand alone, in Arrays or in Dictionaries)\r\n- Custom transformations during mapping\r\n\r\nTo support mapping, a class just needs to implement the MapperProtocol. ObjectMapper uses the \"<=\" operator to define how each member variable maps to and from JSON.\r\n\r\n```swift\r\nclass User: MapperProtocol {\r\n\r\n var username: String?\r\n var age: Int?\r\n var weight: Double?\r\n var arr: [AnyObject]?\r\n var dict: [String : AnyObject] = [:]\r\n var friend: User?\r\n var birthday: NSDate?\r\n\r\n // MapperProtocol \r\n class func map(mapper: Mapper, object: User) {\r\n object.username <= mapper[\"username\"]\r\n object.age <= mapper[\"age\"]\r\n object.weight <= mapper[\"weight\"]\r\n object.arr <= mapper[\"arr\"]\r\n object.dict <= mapper[\"dict\"]\r\n object.friend <= mapper[\"friend\"]\r\n object.birthday <= (mapper[\"birthday\"], DateTransform<NSDate, Int>())\r\n }\r\n}\r\n```\r\n\r\nOnce your class implements MapperProtocol, the Mapper class handles everything else for you:\r\n\r\nConvert a JSON string to a model object:\r\n```swift\r\nlet user = Mapper().map(JSONString, to: User.self)\r\n```\r\n\r\nConvert a model object to a JSON string:\r\n```swift\r\n\r\nlet JSONString = Mapper().toJSONString(user)\r\n```\r\n\r\nObject mapper can handle classes composed of the following types:\r\n- Int\r\n- Bool\r\n- Double\r\n- Float\r\n- String\r\n- Array\\<AnyObject\\>\r\n- Dictionary\\<String, AnyObject\\>\r\n- Optionals of all the abovee\r\n- Object\\<T: MapperProtocol\\>\r\n- Array\\<T: MapperProtocol\\>\r\n- Dictionary\\<String, T: MapperProtocol\\>\r\n\r\nObjectMapper also supports Transforms that convert values during the mapping process. To use a transform, simply create a tuple with the mapper[\"field_name\"] and the transform of choice on the right side of the '<=' operator:\r\n```swift\r\nobject.birthday <= (mapper[\"birthday\"], DateTransform<NSDate, Int>())\r\n```\r\nThe above transform will convert the JSON Int value to an NSDate when reading JSON and will convert the NSDate to an Int when converting objects to JSON.\r\n\r\nYou can easily create your own custom transforms by subclassing and overriding the methods in the MapperTransform class:\r\n```swift\r\npublic class MapperTransform<ObjectType, JSONType> {\r\n init(){\r\n\r\n }\r\n\r\n func transformFromJSON(value: AnyObject?) -> ObjectType? {\r\n return nil\r\n }\r\n\r\n func transformToJSON(value: ObjectType?) -> JSONType? {\r\n return nil\r\n }\r\n}\r\n```\r\n\r\n","google":"","note":"Don't delete this file! It's used internally to help with page regeneration."}
|
|
@ -0,0 +1,70 @@
|
|||
.highlight .hll { background-color: #ffffcc }
|
||||
.highlight { background: #f0f3f3; }
|
||||
.highlight .c { color: #0099FF; font-style: italic } /* Comment */
|
||||
.highlight .err { color: #AA0000; background-color: #FFAAAA } /* Error */
|
||||
.highlight .k { color: #006699; font-weight: bold } /* Keyword */
|
||||
.highlight .o { color: #555555 } /* Operator */
|
||||
.highlight .cm { color: #0099FF; font-style: italic } /* Comment.Multiline */
|
||||
.highlight .cp { color: #009999 } /* Comment.Preproc */
|
||||
.highlight .c1 { color: #0099FF; font-style: italic } /* Comment.Single */
|
||||
.highlight .cs { color: #0099FF; font-weight: bold; font-style: italic } /* Comment.Special */
|
||||
.highlight .gd { background-color: #FFCCCC; border: 1px solid #CC0000 } /* Generic.Deleted */
|
||||
.highlight .ge { font-style: italic } /* Generic.Emph */
|
||||
.highlight .gr { color: #FF0000 } /* Generic.Error */
|
||||
.highlight .gh { color: #003300; font-weight: bold } /* Generic.Heading */
|
||||
.highlight .gi { background-color: #CCFFCC; border: 1px solid #00CC00 } /* Generic.Inserted */
|
||||
.highlight .go { color: #AAAAAA } /* Generic.Output */
|
||||
.highlight .gp { color: #000099; font-weight: bold } /* Generic.Prompt */
|
||||
.highlight .gs { font-weight: bold } /* Generic.Strong */
|
||||
.highlight .gu { color: #003300; font-weight: bold } /* Generic.Subheading */
|
||||
.highlight .gt { color: #99CC66 } /* Generic.Traceback */
|
||||
.highlight .kc { color: #006699; font-weight: bold } /* Keyword.Constant */
|
||||
.highlight .kd { color: #006699; font-weight: bold } /* Keyword.Declaration */
|
||||
.highlight .kn { color: #006699; font-weight: bold } /* Keyword.Namespace */
|
||||
.highlight .kp { color: #006699 } /* Keyword.Pseudo */
|
||||
.highlight .kr { color: #006699; font-weight: bold } /* Keyword.Reserved */
|
||||
.highlight .kt { color: #007788; font-weight: bold } /* Keyword.Type */
|
||||
.highlight .m { color: #FF6600 } /* Literal.Number */
|
||||
.highlight .s { color: #CC3300 } /* Literal.String */
|
||||
.highlight .na { color: #330099 } /* Name.Attribute */
|
||||
.highlight .nb { color: #336666 } /* Name.Builtin */
|
||||
.highlight .nc { color: #00AA88; font-weight: bold } /* Name.Class */
|
||||
.highlight .no { color: #336600 } /* Name.Constant */
|
||||
.highlight .nd { color: #9999FF } /* Name.Decorator */
|
||||
.highlight .ni { color: #999999; font-weight: bold } /* Name.Entity */
|
||||
.highlight .ne { color: #CC0000; font-weight: bold } /* Name.Exception */
|
||||
.highlight .nf { color: #CC00FF } /* Name.Function */
|
||||
.highlight .nl { color: #9999FF } /* Name.Label */
|
||||
.highlight .nn { color: #00CCFF; font-weight: bold } /* Name.Namespace */
|
||||
.highlight .nt { color: #330099; font-weight: bold } /* Name.Tag */
|
||||
.highlight .nv { color: #003333 } /* Name.Variable */
|
||||
.highlight .ow { color: #000000; font-weight: bold } /* Operator.Word */
|
||||
.highlight .w { color: #bbbbbb } /* Text.Whitespace */
|
||||
.highlight .mf { color: #FF6600 } /* Literal.Number.Float */
|
||||
.highlight .mh { color: #FF6600 } /* Literal.Number.Hex */
|
||||
.highlight .mi { color: #FF6600 } /* Literal.Number.Integer */
|
||||
.highlight .mo { color: #FF6600 } /* Literal.Number.Oct */
|
||||
.highlight .sb { color: #CC3300 } /* Literal.String.Backtick */
|
||||
.highlight .sc { color: #CC3300 } /* Literal.String.Char */
|
||||
.highlight .sd { color: #CC3300; font-style: italic } /* Literal.String.Doc */
|
||||
.highlight .s2 { color: #CC3300 } /* Literal.String.Double */
|
||||
.highlight .se { color: #CC3300; font-weight: bold } /* Literal.String.Escape */
|
||||
.highlight .sh { color: #CC3300 } /* Literal.String.Heredoc */
|
||||
.highlight .si { color: #AA0000 } /* Literal.String.Interpol */
|
||||
.highlight .sx { color: #CC3300 } /* Literal.String.Other */
|
||||
.highlight .sr { color: #33AAAA } /* Literal.String.Regex */
|
||||
.highlight .s1 { color: #CC3300 } /* Literal.String.Single */
|
||||
.highlight .ss { color: #FFCC33 } /* Literal.String.Symbol */
|
||||
.highlight .bp { color: #336666 } /* Name.Builtin.Pseudo */
|
||||
.highlight .vc { color: #003333 } /* Name.Variable.Class */
|
||||
.highlight .vg { color: #003333 } /* Name.Variable.Global */
|
||||
.highlight .vi { color: #003333 } /* Name.Variable.Instance */
|
||||
.highlight .il { color: #FF6600 } /* Literal.Number.Integer.Long */
|
||||
|
||||
.type-csharp .highlight .k { color: #0000FF }
|
||||
.type-csharp .highlight .kt { color: #0000FF }
|
||||
.type-csharp .highlight .nf { color: #000000; font-weight: normal }
|
||||
.type-csharp .highlight .nc { color: #2B91AF }
|
||||
.type-csharp .highlight .nn { color: #000000 }
|
||||
.type-csharp .highlight .s { color: #A31515 }
|
||||
.type-csharp .highlight .sc { color: #A31515 }
|
|
@ -0,0 +1,423 @@
|
|||
/*******************************************************************************
|
||||
Slate Theme for GitHub Pages
|
||||
by Jason Costello, @jsncostello
|
||||
*******************************************************************************/
|
||||
|
||||
@import url(pygment_trac.css);
|
||||
|
||||
/*******************************************************************************
|
||||
MeyerWeb Reset
|
||||
*******************************************************************************/
|
||||
|
||||
html, body, div, span, applet, object, iframe,
|
||||
h1, h2, h3, h4, h5, h6, p, blockquote, pre,
|
||||
a, abbr, acronym, address, big, cite, code,
|
||||
del, dfn, em, img, ins, kbd, q, s, samp,
|
||||
small, strike, strong, sub, sup, tt, var,
|
||||
b, u, i, center,
|
||||
dl, dt, dd, ol, ul, li,
|
||||
fieldset, form, label, legend,
|
||||
table, caption, tbody, tfoot, thead, tr, th, td,
|
||||
article, aside, canvas, details, embed,
|
||||
figure, figcaption, footer, header, hgroup,
|
||||
menu, nav, output, ruby, section, summary,
|
||||
time, mark, audio, video {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
border: 0;
|
||||
font: inherit;
|
||||
vertical-align: baseline;
|
||||
}
|
||||
|
||||
/* HTML5 display-role reset for older browsers */
|
||||
article, aside, details, figcaption, figure,
|
||||
footer, header, hgroup, menu, nav, section {
|
||||
display: block;
|
||||
}
|
||||
|
||||
ol, ul {
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
table {
|
||||
border-collapse: collapse;
|
||||
border-spacing: 0;
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
Theme Styles
|
||||
*******************************************************************************/
|
||||
|
||||
body {
|
||||
box-sizing: border-box;
|
||||
color:#373737;
|
||||
background: #212121;
|
||||
font-size: 16px;
|
||||
font-family: 'Myriad Pro', Calibri, Helvetica, Arial, sans-serif;
|
||||
line-height: 1.5;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
}
|
||||
|
||||
h1, h2, h3, h4, h5, h6 {
|
||||
margin: 10px 0;
|
||||
font-weight: 700;
|
||||
color:#222222;
|
||||
font-family: 'Lucida Grande', 'Calibri', Helvetica, Arial, sans-serif;
|
||||
letter-spacing: -1px;
|
||||
}
|
||||
|
||||
h1 {
|
||||
font-size: 36px;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
h2 {
|
||||
padding-bottom: 10px;
|
||||
font-size: 32px;
|
||||
background: url('../images/bg_hr.png') repeat-x bottom;
|
||||
}
|
||||
|
||||
h3 {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
h4 {
|
||||
font-size: 21px;
|
||||
}
|
||||
|
||||
h5 {
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
h6 {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
p {
|
||||
margin: 10px 0 15px 0;
|
||||
}
|
||||
|
||||
footer p {
|
||||
color: #f2f2f2;
|
||||
}
|
||||
|
||||
a {
|
||||
text-decoration: none;
|
||||
color: #007edf;
|
||||
text-shadow: none;
|
||||
|
||||
transition: color 0.5s ease;
|
||||
transition: text-shadow 0.5s ease;
|
||||
-webkit-transition: color 0.5s ease;
|
||||
-webkit-transition: text-shadow 0.5s ease;
|
||||
-moz-transition: color 0.5s ease;
|
||||
-moz-transition: text-shadow 0.5s ease;
|
||||
-o-transition: color 0.5s ease;
|
||||
-o-transition: text-shadow 0.5s ease;
|
||||
-ms-transition: color 0.5s ease;
|
||||
-ms-transition: text-shadow 0.5s ease;
|
||||
}
|
||||
|
||||
a:hover, a:focus {text-decoration: underline;}
|
||||
|
||||
footer a {
|
||||
color: #F2F2F2;
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
strong {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
img {
|
||||
position: relative;
|
||||
margin: 0 auto;
|
||||
max-width: 739px;
|
||||
padding: 5px;
|
||||
margin: 10px 0 10px 0;
|
||||
border: 1px solid #ebebeb;
|
||||
|
||||
box-shadow: 0 0 5px #ebebeb;
|
||||
-webkit-box-shadow: 0 0 5px #ebebeb;
|
||||
-moz-box-shadow: 0 0 5px #ebebeb;
|
||||
-o-box-shadow: 0 0 5px #ebebeb;
|
||||
-ms-box-shadow: 0 0 5px #ebebeb;
|
||||
}
|
||||
|
||||
p img {
|
||||
display: inline;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
vertical-align: middle;
|
||||
text-align: center;
|
||||
border: none;
|
||||
}
|
||||
|
||||
pre, code {
|
||||
width: 100%;
|
||||
color: #222;
|
||||
background-color: #fff;
|
||||
|
||||
font-family: Monaco, "Bitstream Vera Sans Mono", "Lucida Console", Terminal, monospace;
|
||||
font-size: 14px;
|
||||
|
||||
border-radius: 2px;
|
||||
-moz-border-radius: 2px;
|
||||
-webkit-border-radius: 2px;
|
||||
}
|
||||
|
||||
pre {
|
||||
width: 100%;
|
||||
padding: 10px;
|
||||
box-shadow: 0 0 10px rgba(0,0,0,.1);
|
||||
overflow: auto;
|
||||
}
|
||||
|
||||
code {
|
||||
padding: 3px;
|
||||
margin: 0 3px;
|
||||
box-shadow: 0 0 10px rgba(0,0,0,.1);
|
||||
}
|
||||
|
||||
pre code {
|
||||
display: block;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
blockquote {
|
||||
color: #666;
|
||||
margin-bottom: 20px;
|
||||
padding: 0 0 0 20px;
|
||||
border-left: 3px solid #bbb;
|
||||
}
|
||||
|
||||
|
||||
ul, ol, dl {
|
||||
margin-bottom: 15px
|
||||
}
|
||||
|
||||
ul {
|
||||
list-style: inside;
|
||||
padding-left: 20px;
|
||||
}
|
||||
|
||||
ol {
|
||||
list-style: decimal inside;
|
||||
padding-left: 20px;
|
||||
}
|
||||
|
||||
dl dt {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
dl dd {
|
||||
padding-left: 20px;
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
dl p {
|
||||
padding-left: 20px;
|
||||
font-style: italic;
|
||||
}
|
||||
|
||||
hr {
|
||||
height: 1px;
|
||||
margin-bottom: 5px;
|
||||
border: none;
|
||||
background: url('../images/bg_hr.png') repeat-x center;
|
||||
}
|
||||
|
||||
table {
|
||||
border: 1px solid #373737;
|
||||
margin-bottom: 20px;
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
th {
|
||||
font-family: 'Lucida Grande', 'Helvetica Neue', Helvetica, Arial, sans-serif;
|
||||
padding: 10px;
|
||||
background: #373737;
|
||||
color: #fff;
|
||||
}
|
||||
|
||||
td {
|
||||
padding: 10px;
|
||||
border: 1px solid #373737;
|
||||
}
|
||||
|
||||
form {
|
||||
background: #f2f2f2;
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
Full-Width Styles
|
||||
*******************************************************************************/
|
||||
|
||||
.outer {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.inner {
|
||||
position: relative;
|
||||
max-width: 640px;
|
||||
padding: 20px 10px;
|
||||
margin: 0 auto;
|
||||
}
|
||||
|
||||
#forkme_banner {
|
||||
display: block;
|
||||
position: absolute;
|
||||
top:0;
|
||||
right: 10px;
|
||||
z-index: 10;
|
||||
padding: 10px 50px 10px 10px;
|
||||
color: #fff;
|
||||
background: url('../images/blacktocat.png') #0090ff no-repeat 95% 50%;
|
||||
font-weight: 700;
|
||||
box-shadow: 0 0 10px rgba(0,0,0,.5);
|
||||
border-bottom-left-radius: 2px;
|
||||
border-bottom-right-radius: 2px;
|
||||
}
|
||||
|
||||
#header_wrap {
|
||||
background: #212121;
|
||||
background: -moz-linear-gradient(top, #373737, #212121);
|
||||
background: -webkit-linear-gradient(top, #373737, #212121);
|
||||
background: -ms-linear-gradient(top, #373737, #212121);
|
||||
background: -o-linear-gradient(top, #373737, #212121);
|
||||
background: linear-gradient(top, #373737, #212121);
|
||||
}
|
||||
|
||||
#header_wrap .inner {
|
||||
padding: 50px 10px 30px 10px;
|
||||
}
|
||||
|
||||
#project_title {
|
||||
margin: 0;
|
||||
color: #fff;
|
||||
font-size: 42px;
|
||||
font-weight: 700;
|
||||
text-shadow: #111 0px 0px 10px;
|
||||
}
|
||||
|
||||
#project_tagline {
|
||||
color: #fff;
|
||||
font-size: 24px;
|
||||
font-weight: 300;
|
||||
background: none;
|
||||
text-shadow: #111 0px 0px 10px;
|
||||
}
|
||||
|
||||
#downloads {
|
||||
position: absolute;
|
||||
width: 210px;
|
||||
z-index: 10;
|
||||
bottom: -40px;
|
||||
right: 0;
|
||||
height: 70px;
|
||||
background: url('../images/icon_download.png') no-repeat 0% 90%;
|
||||
}
|
||||
|
||||
.zip_download_link {
|
||||
display: block;
|
||||
float: right;
|
||||
width: 90px;
|
||||
height:70px;
|
||||
text-indent: -5000px;
|
||||
overflow: hidden;
|
||||
background: url(../images/sprite_download.png) no-repeat bottom left;
|
||||
}
|
||||
|
||||
.tar_download_link {
|
||||
display: block;
|
||||
float: right;
|
||||
width: 90px;
|
||||
height:70px;
|
||||
text-indent: -5000px;
|
||||
overflow: hidden;
|
||||
background: url(../images/sprite_download.png) no-repeat bottom right;
|
||||
margin-left: 10px;
|
||||
}
|
||||
|
||||
.zip_download_link:hover {
|
||||
background: url(../images/sprite_download.png) no-repeat top left;
|
||||
}
|
||||
|
||||
.tar_download_link:hover {
|
||||
background: url(../images/sprite_download.png) no-repeat top right;
|
||||
}
|
||||
|
||||
#main_content_wrap {
|
||||
background: #f2f2f2;
|
||||
border-top: 1px solid #111;
|
||||
border-bottom: 1px solid #111;
|
||||
}
|
||||
|
||||
#main_content {
|
||||
padding-top: 40px;
|
||||
}
|
||||
|
||||
#footer_wrap {
|
||||
background: #212121;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
Small Device Styles
|
||||
*******************************************************************************/
|
||||
|
||||
@media screen and (max-width: 480px) {
|
||||
body {
|
||||
font-size:14px;
|
||||
}
|
||||
|
||||
#downloads {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.inner {
|
||||
min-width: 320px;
|
||||
max-width: 480px;
|
||||
}
|
||||
|
||||
#project_title {
|
||||
font-size: 32px;
|
||||
}
|
||||
|
||||
h1 {
|
||||
font-size: 28px;
|
||||
}
|
||||
|
||||
h2 {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
h3 {
|
||||
font-size: 21px;
|
||||
}
|
||||
|
||||
h4 {
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
h5 {
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
h6 {
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
code, pre {
|
||||
min-width: 320px;
|
||||
max-width: 480px;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue