Reputation: 431
{
"optionChain": {
"result": [
{
"underlyingSymbol": "AAPL",
"expirationDates": [
1606435200,
1655424000,
1663286400,
1674172800
],
"strikes": [
55,
60,
65,
70,
75,
80,
85,
90,
95,
96,
97,
98,
99,
100,
101,
102,
103,
104,
105,
106,
107,
108,
109,
110,
111,
112,
113,
114,
115,
116,
131,
132,
133,
155,
160,
165,
170,
175
],
"hasMiniOptions": false,
"quote": {
"language": "en-US",
"region": "US",
"quoteType": "EQUITY",
"quoteSourceName": "Nasdaq Real Time Price",
"triggerable": true,
"currency": "USD",
"firstTradeDateMilliseconds": 345479400000,
"priceHint": 2,
"regularMarketChange": -2.2599945,
"regularMarketChangePercent": -1.9260223,
"regularMarketTime": 1606152628,
"regularMarketPrice": 115.08,
"regularMarketDayHigh": 117.62,
"regularMarketDayRange": "113.8 - 117.62",
"regularMarketDayLow": 113.8,
"regularMarketVolume": 66403356,
"regularMarketPreviousClose": 117.34,
"bid": 114.79,
"ask": 114.78,
"bidSize": 9,
"askSize": 10,
"fullExchangeName": "NasdaqGS",
"financialCurrency": "USD",
"regularMarketOpen": 117.18,
"averageDailyVolume3Month": 150914918,
"averageDailyVolume10Day": 78477066,
"fiftyTwoWeekLowChange": 61.9275,
"fiftyTwoWeekLowChangePercent": 1.165091,
"fiftyTwoWeekRange": "53.1525 - 137.98",
"fiftyTwoWeekHighChange": -22.899994,
"fiftyTwoWeekHighChangePercent": -0.16596605,
"fiftyTwoWeekLow": 53.1525,
"fiftyTwoWeekHigh": 137.98,
"dividendDate": 1605139200,
"earningsTimestamp": 1603989000,
"earningsTimestampStart": 1611658740,
"earningsTimestampEnd": 1612180800,
"trailingAnnualDividendRate": 0.795,
"trailingPE": 35.085365,
"trailingAnnualDividendYield": 0.0067751836,
"epsTrailingTwelveMonths": 3.28,
"epsForward": 4.33,
"epsCurrentYear": 3.96,
"priceEpsCurrentYear": 29.060606,
"sharesOutstanding": 17102499840,
"bookValue": 3.849,
"fiftyDayAverage": 116.774574,
"fiftyDayAverageChange": -1.6945724,
"fiftyDayAverageChangePercent": -0.014511485,
"twoHundredDayAverage": 104.00763,
"twoHundredDayAverageChange": 11.072372,
"twoHundredDayAverageChangePercent": 0.10645731,
"marketCap": 1956567187456,
"forwardPE": 26.577368,
"priceToBook": 29.898676,
"sourceInterval": 15,
"exchangeDataDelayedBy": 0,
"tradeable": false,
"exchange": "NMS",
"shortName": "Apple Inc.",
"longName": "Apple Inc.",
"marketState": "REGULAR",
"messageBoardId": "finmb_24937",
"exchangeTimezoneName": "America/New_York",
"exchangeTimezoneShortName": "EST",
"gmtOffSetMilliseconds": -18000000,
"market": "us_market",
"esgPopulated": false,
"displayName": "Apple",
"symbol": "AAPL"
},
"options": [
{
"expirationDate": 1606435200,
"hasMiniOptions": false,
"calls": [
{
"contractSymbol": "AAPL201127C00165000",
"strike": 165,
"currency": "USD",
"lastPrice": 0.01,
"change": 0,
"percentChange": 0,
"volume": 1,
"openInterest": 156,
"bid": 0,
"ask": 0.01,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1605731100,
"impliedVolatility": 1.000005,
"inTheMoney": false
},
{
"contractSymbol": "AAPL201127C00170000",
"strike": 170,
"currency": "USD",
"lastPrice": 0.01,
"change": 0,
"percentChange": 0,
"volume": 11,
"openInterest": 353,
"bid": 0,
"ask": 0.01,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1605731115,
"impliedVolatility": 1.0625046875000002,
"inTheMoney": false
},
{
"contractSymbol": "AAPL201127C00175000",
"strike": 175,
"currency": "USD",
"lastPrice": 0.01,
"change": 0,
"percentChange": 0,
"volume": 5,
"openInterest": 259,
"bid": 0,
"ask": 0.01,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1606150652,
"impliedVolatility": 1.15625421875,
"inTheMoney": false
}
],
"puts": [
{
"contractSymbol": "AAPL201127P00134000",
"strike": 134,
"currency": "USD",
"lastPrice": 14.2,
"change": 0,
"percentChange": 0,
"volume": 4,
"openInterest": 133,
"bid": 19.1,
"ask": 19.35,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1605632020,
"impliedVolatility": 0.831056376953125,
"inTheMoney": true
},
{
"contractSymbol": "AAPL201127P00135000",
"strike": 135,
"currency": "USD",
"lastPrice": 21.05,
"change": 3.869999,
"percentChange": 22.526186,
"volume": 38,
"openInterest": 258,
"bid": 20.35,
"ask": 20.5,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1606148156,
"impliedVolatility": 0.96679720703125,
"inTheMoney": true
},
{
"contractSymbol": "AAPL201127P00138000",
"strike": 138,
"currency": "USD",
"lastPrice": 19.41,
"change": 0,
"percentChange": 0,
"openInterest": 1,
"bid": 23.1,
"ask": 23.25,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1605819053,
"impliedVolatility": 0.91992267578125,
"inTheMoney": true
},
{
"contractSymbol": "AAPL201127P00140000",
"strike": 140,
"currency": "USD",
"lastPrice": 21.19,
"change": 0,
"percentChange": 0,
"volume": 24,
"openInterest": 53,
"bid": 25.2,
"ask": 25.35,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1605818102,
"impliedVolatility": 1.0429735351562504,
"inTheMoney": true
},
{
"contractSymbol": "AAPL201127P00145000",
"strike": 145,
"currency": "USD",
"lastPrice": 26.85,
"change": 0,
"percentChange": 0,
"volume": 1,
"openInterest": 55,
"bid": 30.2,
"ask": 30.35,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1605892788,
"impliedVolatility": 1.185550947265625,
"inTheMoney": true
},
{
"contractSymbol": "AAPL201127P00175000",
"strike": 175,
"currency": "USD",
"lastPrice": 57.13,
"change": 0,
"percentChange": 0,
"volume": 2,
"openInterest": 2,
"bid": 60.15,
"ask": 60.25,
"contractSize": "REGULAR",
"expiration": 1606435200,
"lastTradeDate": 1605798274,
"impliedVolatility": 1.822266513671875,
"inTheMoney": true
}
]
}
]
}
],
"error": null
}}
Above is the API JSON response from my calls. Now below is the decodable written in swift.
struct Something: Decodable
{
let optionChain: OptionChain
let error: String
}
struct OptionChain: Decodable
{
let result: [ResultElement]
}
struct ResultElement: Decodable
{
let underlyingSymbol: String
let expirationDates: [Int]
let strikes: [Int]
let hasMiniOptions: Bool
let quote: [quoteElement]
let options: [optionsElement]
}
struct quoteElement: Decodable
{
let language: String
let region: String
let quoteType: String
let quoteSourceName: String
let triggerable: Bool
let currency: String
let firstTradeDateMilliseconds: Int
let priceHint: Int
let regularMarketChange: Int
let regularMarketChangePercent: Int
let regularMarketTime: Int
let regularMarketPrice: Int
let regularMarketDayHigh: Int
let regularMarketDayRange: String
let regularMarketDayLow: Int
let regularMarketVolume: Int
let regularMarketPreviousClose: Int
let bid: Int
let ask: Int
let bidSize: Int
let askSize: Int
let fullExchangeName: String
let financialCurrency: String
let regularMarketOpen: Int
let averageDailyVolume3Month: Int
let averageDailyVolume10Day: Int
let fiftyTwoWeekLowChange: Int
let fiftyTwoWeekLowChangePercent: Int
let fiftyTwoWeekRange: String
let fiftyTwoWeekHighChange: Int
let fiftyTwoWeekHighChangePercent: Int
let fiftyTwoWeekLow: Int
let fiftyTwoWeekHigh: Int
let dividendDate: Int
let earningsTimestamp: Int
let earningsTimestampStart: Int
let earningsTimestampEnd: Int
let trailingAnnualDividendRate: Int
let trailingPE: Int
let trailingAnnualDividendYield: Int
let epsTrailingTwelveMonths: Int
let epsForward: Int
let epsCurrentYear: Int
let priceEpsCurrentYear: Int
let sharesOutstanding: Int
let bookValue: Int
let fiftyDayAverage: Int
let fiftyDayAverageChange: Int
let fiftyDayAverageChangePercent: Int
let twoHundredDayAverage: Int
let twoHundredDayAverageChange: Int
let twoHundredDayAverageChangePercent: Int
let marketCap: Int
let forwardPE: Int
let priceToBook: Int
let sourceInterval: Int
let exchangeDataDelayedBy: Int
let tradeable: Bool
let exchange: String
let shortName: String
let longName: String
let marketState: String
let messageBoardId: String
let exchangeTimezoneName: String
let exchangeTimezoneShortName: String
let gmtOffSetMilliseconds: Int
let market: String
let esgPopulated: Bool
let displayName: String
let symbol: String
}
struct optionsElement: Decodable
{
let expirationDate: Int
let hasMiniOptions: Bool
let calls: [callPutElement]
let puts: [callPutElement]
}
struct callPutElement: Decodable
{
let contractSymbol: String
let strike: Int
let currency: String
let lastPrice: Int
let change: Int
let percentChange: Int
let volume: Int
let openInterest: Int
let bid: Int
let ask: Int
let contractSize: String
let expiration: Int
let lastTradeDate: Int
let impliedVolatility: Int
let inTheMoney: Bool
}
I call those decodables from this code below:
let request = NSMutableURLRequest(url: NSURL(string: urlTicker)! as URL,
cachePolicy: .useProtocolCachePolicy,
timeoutInterval: 10.0)
request.httpMethod = "GET"
request.allHTTPHeaderFields = headers
let session = URLSession.shared
let dataTask = session.dataTask(with: request as URLRequest, completionHandler: { (data, response, error) -> Void in
if (error != nil)
{
print(error)
}
else
{
let httpResponse = response as? HTTPURLResponse
do
{
let jsonString = "{...}"
let jsonData = jsonString.data(using: .utf8)!
let decoder = JSONDecoder()
let something = try decoder.decode(Something.self, from: jsonData)
print(something.optionChain.result.map { $0.underlyingSymbol })
//let myJSON = try JSONSerialization.jsonObject(with: data!, options: .allowFragments) as? [String:Any]
//let likes = myJSON!["optionChain"] as? Array<Dictionary<String, Any>>
}
catch
{
print("JSONSerialization error:", error)
}
//print(httpResponse)
//print(myJSON["strikes"] as! String)
}
})
dataTask.resume()
I get into the catch statement and the error is:
SONSerialization error: dataCorrupted(Swift.DecodingError.Context(codingPath: [], debugDescription: "The given data was not valid JSON.", underlyingError: Optional(Error Domain=NSCocoaErrorDomain Code=3840 "No string key for value in object around character 1." UserInfo={NSDebugDescription=No string key for value in object around character 1.})))
Am I using decodeables wrong?
Upvotes: 0
Views: 177
Reputation: 236568
The only issue I had to take care when decoding your data was to set the date decoding strategy. Just set your dateDecodingStrategy to .secondsSince1970
. try like this:
struct Root: Codable {
let optionChain: OptionChain
}
struct OptionChain: Codable {
let result: [Result]
}
struct Result: Codable {
let underlyingSymbol: String
let expirationDates: [Date]
let strikes: [Int]
let hasMiniOptions: Bool
let quote: Quote
let options: [Option]
}
struct Option: Codable {
let expirationDate: Date
let hasMiniOptions: Bool
let calls: [Call]
let puts: [Call]
}
struct Call: Codable {
let contractSymbol: String
let strike: Int
let currency: String
let lastPrice: Double
let change, percentChange: Double
let volume: Int?
let openInterest: Int
let bid, ask: Double
let contractSize: String
let expiration, lastTradeDate: Date
let impliedVolatility: Double
let inTheMoney: Bool
}
struct Quote: Codable {
let language,region, quoteType, quoteSourceName: String
let triggerable: Bool
let currency: String
let firstTradeDateMilliseconds, priceHint: Int
let regularMarketChange, regularMarketChangePercent: Double
let regularMarketTime: Int
let regularMarketPrice, regularMarketDayHigh: Double
let regularMarketDayRange: String
let regularMarketDayLow: Double
let regularMarketVolume: Int
let regularMarketPreviousClose, bid, ask: Double
let bidSize, askSize: Int
let fullExchangeName, financialCurrency: String
let regularMarketOpen: Double
let averageDailyVolume3Month, averageDailyVolume10Day: Int
let fiftyTwoWeekLowChange, fiftyTwoWeekLowChangePercent: Double
let fiftyTwoWeekRange: String
let fiftyTwoWeekHighChange, fiftyTwoWeekHighChangePercent: Double
let fiftyTwoWeekLow, fiftyTwoWeekHigh: Double
let dividendDate, earningsTimestamp, earningsTimestampStart, earningsTimestampEnd: Date
let trailingAnnualDividendRate, trailingPE, trailingAnnualDividendYield, epsTrailingTwelveMonths, epsForward, epsCurrentYear, priceEpsCurrentYear: Double
let sharesOutstanding: Int
let bookValue, fiftyDayAverage, fiftyDayAverageChange, fiftyDayAverageChangePercent, twoHundredDayAverage, twoHundredDayAverageChange, twoHundredDayAverageChangePercent: Double
let marketCap: Int
let forwardPE, priceToBook: Double
let sourceInterval, exchangeDataDelayedBy: Int
let tradeable: Bool
let exchange, shortName, longName, marketState, messageBoardId, exchangeTimezoneName, exchangeTimezoneShortName: String
let gmtOffSetMilliseconds: Int
let market: String
let esgPopulated: Bool
let displayName, symbol: String
}
playground testing
do {
let decoder = JSONDecoder()
decoder.dateDecodingStrategy = .secondsSince1970
let root = try decoder.decode(Root.self, from: .init(json.utf8))
print(root)
} catch {
print(error)
}
This will print
Root(optionChain: __lldb_expr_184.OptionChain(result: [__lldb_expr_184.Result(underlyingSymbol: "AAPL", expirationDates: [2020-11-27 00:00:00 +0000, 2022-06-17 00:00:00 +0000, 2022-09-16 00:00:00 +0000, 2023-01-20 00:00:00 +0000], strikes: [55, 60, 65, 70, 75, 80, 85, 90, 95, 96, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 131, 132, 133, 155, 160, 165, 170, 175], hasMiniOptions: false, quote: __lldb_expr_184.Quote(language: "en-US", region: "US", quoteType: "EQUITY", quoteSourceName: "Nasdaq Real Time Price", triggerable: true, currency: "USD", firstTradeDateMilliseconds: 345479400000, priceHint: 2, regularMarketChange: -2.2599945, regularMarketChangePercent: -1.9260223, regularMarketTime: 1606152628, regularMarketPrice: 115.08, regularMarketDayHigh: 117.62, regularMarketDayRange: "113.8 - 117.62", regularMarketDayLow: 113.8, regularMarketVolume: 66403356, regularMarketPreviousClose: 117.34, bid: 114.79, ask: 114.78, bidSize: 9, askSize: 10, fullExchangeName: "NasdaqGS", financialCurrency: "USD", regularMarketOpen: 117.18, averageDailyVolume3Month: 150914918, averageDailyVolume10Day: 78477066, fiftyTwoWeekLowChange: 61.9275, fiftyTwoWeekLowChangePercent: 1.165091, fiftyTwoWeekRange: "53.1525 - 137.98", fiftyTwoWeekHighChange: -22.899994, fiftyTwoWeekHighChangePercent: -0.16596605, fiftyTwoWeekLow: 53.1525, fiftyTwoWeekHigh: 137.98, dividendDate: 2020-11-12 00:00:00 +0000, earningsTimestamp: 2020-10-29 16:30:00 +0000, earningsTimestampStart: 2021-01-26 10:59:00 +0000, earningsTimestampEnd: 2021-02-01 12:00:00 +0000, trailingAnnualDividendRate: 0.795, trailingPE: 35.085365, trailingAnnualDividendYield: 0.0067751836, epsTrailingTwelveMonths: 3.28, epsForward: 4.33, epsCurrentYear: 3.96, priceEpsCurrentYear: 29.060606, sharesOutstanding: 17102499840, bookValue: 3.849, fiftyDayAverage: 116.774574, fiftyDayAverageChange: -1.6945724, fiftyDayAverageChangePercent: -0.014511485, twoHundredDayAverage: 104.00763, twoHundredDayAverageChange: 11.072372, twoHundredDayAverageChangePercent: 0.10645731, marketCap: 1956567187456, forwardPE: 26.577368, priceToBook: 29.898676, sourceInterval: 15, exchangeDataDelayedBy: 0, tradeable: false, exchange: "NMS", shortName: "Apple Inc.", longName: "Apple Inc.", marketState: "REGULAR", messageBoardId: "finmb_24937", exchangeTimezoneName: "America/New_York", exchangeTimezoneShortName: "EST", gmtOffSetMilliseconds: -18000000, market: "us_market", esgPopulated: false, displayName: "Apple", symbol: "AAPL"), options: [__lldb_expr_184.Option(expirationDate: 2020-11-27 00:00:00 +0000, hasMiniOptions: false, calls: [__lldb_expr_184.Call(contractSymbol: "AAPL201127C00165000", strike: 165, currency: "USD", lastPrice: 0.01, change: 0.0, percentChange: 0.0, volume: Optional(1), openInterest: 156, bid: 0.0, ask: 0.01, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-18 20:25:00 +0000, impliedVolatility: 1.000005, inTheMoney: false), __lldb_expr_184.Call(contractSymbol: "AAPL201127C00170000", strike: 170, currency: "USD", lastPrice: 0.01, change: 0.0, percentChange: 0.0, volume: Optional(11), openInterest: 353, bid: 0.0, ask: 0.01, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-18 20:25:15 +0000, impliedVolatility: 1.0625046875000002, inTheMoney: false), __lldb_expr_184.Call(contractSymbol: "AAPL201127C00175000", strike: 175, currency: "USD", lastPrice: 0.01, change: 0.0, percentChange: 0.0, volume: Optional(5), openInterest: 259, bid: 0.0, ask: 0.01, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-23 16:57:32 +0000, impliedVolatility: 1.15625421875, inTheMoney: false)], puts: [__lldb_expr_184.Call(contractSymbol: "AAPL201127P00134000", strike: 134, currency: "USD", lastPrice: 14.2, change: 0.0, percentChange: 0.0, volume: Optional(4), openInterest: 133, bid: 19.1, ask: 19.35, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-17 16:53:40 +0000, impliedVolatility: 0.831056376953125, inTheMoney: true), __lldb_expr_184.Call(contractSymbol: "AAPL201127P00135000", strike: 135, currency: "USD", lastPrice: 21.05, change: 3.869999, percentChange: 22.526186, volume: Optional(38), openInterest: 258, bid: 20.35, ask: 20.5, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-23 16:15:56 +0000, impliedVolatility: 0.96679720703125, inTheMoney: true), __lldb_expr_184.Call(contractSymbol: "AAPL201127P00138000", strike: 138, currency: "USD", lastPrice: 19.41, change: 0.0, percentChange: 0.0, volume: nil, openInterest: 1, bid: 23.1, ask: 23.25, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-19 20:50:53 +0000, impliedVolatility: 0.91992267578125, inTheMoney: true), __lldb_expr_184.Call(contractSymbol: "AAPL201127P00140000", strike: 140, currency: "USD", lastPrice: 21.19, change: 0.0, percentChange: 0.0, volume: Optional(24), openInterest: 53, bid: 25.2, ask: 25.35, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-19 20:35:02 +0000, impliedVolatility: 1.0429735351562504, inTheMoney: true), __lldb_expr_184.Call(contractSymbol: "AAPL201127P00145000", strike: 145, currency: "USD", lastPrice: 26.85, change: 0.0, percentChange: 0.0, volume: Optional(1), openInterest: 55, bid: 30.2, ask: 30.35, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-20 17:19:48 +0000, impliedVolatility: 1.185550947265625, inTheMoney: true), __lldb_expr_184.Call(contractSymbol: "AAPL201127P00175000", strike: 175, currency: "USD", lastPrice: 57.13, change: 0.0, percentChange: 0.0, volume: Optional(2), openInterest: 2, bid: 60.15, ask: 60.25, contractSize: "REGULAR", expiration: 2020-11-27 00:00:00 +0000, lastTradeDate: 2020-11-19 15:04:34 +0000, impliedVolatility: 1.822266513671875, inTheMoney: true)])])]))
Upvotes: 2