Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/file/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Swift 结合URLSession和Json解码器AlphaVantage概览数据_Swift_Decode_Combine_Urlsession - Fatal编程技术网

Swift 结合URLSession和Json解码器AlphaVantage概览数据

Swift 结合URLSession和Json解码器AlphaVantage概览数据,swift,decode,combine,urlsession,Swift,Decode,Combine,Urlsession,我正在尝试使用combine、URLSession获取AlphaVantage股票数据并对其进行解码。我使用了如下的框架。我使用相同的框架成功获取了其他AlphaVantage数据,如损益表和现金流。但是,它不适用于概览数据。我找不到问题出在哪里。我已经为此奋斗了一段时间,如果有人能帮助我,我真的很感激 import Foundation import Combine var subscriptions = Set<AnyCancellable>() let pub1 = ge

我正在尝试使用combine、URLSession获取AlphaVantage股票数据并对其进行解码。我使用了如下的框架。我使用相同的框架成功获取了其他AlphaVantage数据,如损益表和现金流。但是,它不适用于概览数据。我找不到问题出在哪里。我已经为此奋斗了一段时间,如果有人能帮助我,我真的很感激

import Foundation
import Combine

var subscriptions = Set<AnyCancellable>()


let pub1 = getCompOverview()
    .sink(receiveCompletion: { completion in
        switch completion {
        case .finished:
            print(".sink completed")
            break
        case .failure(let anError):
            print("received error: ", anError)
        }
    }, receiveValue: { receivedValue in
        print(".sink() received \(receivedValue)")
    })
    .store(in: &subscriptions)

func getCompOverview() -> AnyPublisher<CompOverview, Error> {
    guard let url = URL(string: "https://www.alphavantage.co/query?function=OVERVIEW&symbol=IBM&apikey=demo") else {
        return Fail(error: FetchError.invalidURL).eraseToAnyPublisher()
    }
    return URLSession.shared.dataTaskPublisher(for: url)
        .retry(2)
        .tryMap { data, response in
            guard
                let httpURLResponse = response as? HTTPURLResponse,
                httpURLResponse.statusCode == 200
            else {
                throw URLError(.badServerResponse)
            }
            print("fetching data size = \(data)")
            return data
        }
        .decode(type: CompOverview.self, decoder: JSONDecoder())
        .receive(on: RunLoop.main)
        .eraseToAnyPublisher()
}


struct CompOverview: Codable {
    var symbol:                 String
    var name:                   String
    var description:            String
    var sector:                 String
    var industry:               String
    
    var peRatio:                String
    var pegRatio:               String
    var forwardPE:              String
    var eps:                    String
    
    var divPerShare:       String
    var divYield:          String
    var payoutRatio:            String
    
    var percentInsiders:        String
    var percentInstitutions:    String
    
    var priceToSalesRatioTTM:   String
    var marketCapitalization:   String
    var sharesOutstanding:      String
    
    enum CodingKeys: String, CodingKey {
        case symbol = "Symbol"
        case name = "Name"
        case description = "Description"
        case sector = "Sector"
        case industry = "Industry"
        case peRatio = "PERatio"
        case pegRatio = "PEGRatio"
        case forwardPE = "ForwardPE"
        case eps = "EPS"
        
        case divPerShare = "DividendPerShare"
        case divYield = "DividendYield"
        case payoutRatio = "PayoutRatio"
        
        case percentInsiders = "PercentInsiders"
        case percentInstitutions = "PercentInstitutions"
        
        case priceToSalesRatioTTM = "PriceToSalesRatioTTM"
        case marketCapitalization = "MarketCapitalization"
        case sharesOutstanding = "SharesOutstanding"
    }
    
}
enum FetchError: Error {
    case statusCode
    case decoding
    case invalidImage
    case invalidURL
    case other(Error)
    
    static func map(_ error: Error) -> FetchError {
        return (error as? FetchError) ?? .other(error)
    }
<代码>导入基础 进口联合收割机 var subscriptions=Set() 让pub1=getCompOverview() .sink(receiveCompletion:{completion in 交换完成{ 案例。完成: 打印(“水槽已完成”) 打破 案例。失败(让一个错误): 打印(“收到错误:,A错误) } },receiveValue:{receivedValue in 打印(“.sink()已接收\(receivedValue)”) }) .store(位于:&订阅中) func getCompOverview()->AnyPublisher{ guard let url=url(字符串:https://www.alphavantage.co/query?function=OVERVIEW&symbol=IBM&apikey=demo)其他{ 返回失败(错误:FetchError.invalidURL)。橡皮擦到任何发布者() } 返回URLSession.shared.dataTaskPublisher(用于:url) .重试(2) .tryMap{数据,以 警卫 让httpURLResponse=响应为?httpURLResponse, httpURLResponse.statusCode==200 否则{ 抛出URL错误(.badServerResponse) } 打印(“获取数据大小=\(数据)”) 返回数据 } .decode(类型:CompOverview.self,解码器:JSONDecoder()) .receive(打开:RunLoop.main) .删除任何发布者() } 结构组件视图:可编码{ 变量符号:字符串 变量名称:String 变量说明:字符串 var扇区:字符串 var行业:字符串 变量操作:字符串 var比率:字符串 var-forwardPE:String var-eps:String var divPerShare:字符串 var-divYield:String var payoutRatio:字符串 内部人员:字符串 变量:字符串 var priceToSalesRatioTTM:String var市值:字符串 var sharesOutstanding:String 枚举编码键:字符串,编码键{ case symbol=“symbol” case name=“name” 案例描述=“描述” 案例扇区=“扇区” 案例行业=“行业” 案例peRatio=“peRatio” 案例PEGRATION=“PEGRATION” case forwardPE=“forwardPE” 案例eps=“eps” case divPerShare=“DividendPerShare” case divYield=“DividendYield” 案例支付率=“支付率” 案例percentInsiders=“percentInsiders” 案例百分比机构=“百分比机构” 案例PriceToSalesratioTM=“PriceToSalesratioTM” 案例marketCapitalization=“marketCapitalization” 案例sharesOutstanding=“sharesOutstanding” } } 枚举获取错误:错误{ 案例状态代码 案例解码 案例无效图像 案例无效URL 案例其他(错误) 静态函数映射(error:error)->FetchError{ 返回(错误为?FetchError)??其他(错误) }
当我在操场上测试代码时,它在.tryMap闭包中打印了行。但是,.sink没有执行。

您需要存储订阅时返回的
anycancelable
实例,否则它将取消订阅。此外,您不需要手动实现
解码(from:)
-只需遵循
可解码的
就足够了。此外,我强烈建议您遵循Swift命名约定,使用camelCase命名属性,例如
var dividendPerShare:String
非常感谢您的建议。我添加了。存储,但仍然不起作用。这些名称是键控名称。有办法改变吗e键入的名称?是的。您可以定义一种策略,将密钥转换为camelCase,或手动定义密钥:这是谢谢!请检查如何使代码工作?我只是尝试解码JSON,但由于“EXC_BAD_ACCESS”而失败,它可能被Combine默默吞没。从
CompOverview
中删除属性子集修复了它。不确定为什么会发生这种情况-可能是JSON解码器的内部错误