远程 json 的代理调用以避免 CORS 问题

Posted

技术标签:

【中文标题】远程 json 的代理调用以避免 CORS 问题【英文标题】:Proxy call for remote json to avoid CORS issue 【发布时间】:2018-10-28 02:20:29 【问题描述】:

我开发了一个 Angular 应用程序,它需要使用来自远程服务器的 json 数据。由于 CORS 问题,该应用程序无法直接从该服务器获取数据。我的解决方案是开发一个“代理”web api 来读取该 json 并将其返回到我的应用程序。目前,这是我正在做的方式:

public async Task<IActionResult> MyJson()

    const string jsonUrl = "url-of-remote-json";
    using (var client = new HttpClient())
    
        using (var result = await client.GetAsync(jsonUrl))
        
            if (result.IsSuccessStatusCode)
            
                return new ObjectResult(JsonConvert.DeserializeObject(await result.Content.ReadAsStringAsync()));
            
        
    

    return new ObjectResult(new  );

但是,我认为这远不是一种有效的方法,因为我必须将 json 作为字符串读取,然后使用 JsonConvert 包将其转换为对象以提供 web api 方法。因此,性能并不是很好。

我想知道是否有任何更简单/有效/更简单的方法来完成这项任务?

【问题讨论】:

需要将服务器的json响应转换为对象吗?如果没有特殊需要,您可以在收到回复时发送。 你能展示示例代码吗?谢谢。 一种选择是使用 JsonResult。可以参考答案***.com/questions/38788559/… @pradeep-kumar:JsonResult 需要一个对象(要转换为 json 格式)而不是字符串。我的代码将远程 json 作为字符串读取。 【参考方案1】:

只需通过远程服务器的响应。查看编辑后的示例。

public async Task MyJson()//void if not async

    string jsonUrl = "url-to-json";
    HttpContext.Response.ContentType = "application/json";
    using (var client = new System.Net.WebClient())
    
        try
        
            byte[] bytes = await client.DownloadDataTaskAsync(jsonUrl);
            //write to response stream aka Response.Body
            await HttpContext.Response.Body.WriteAsync(bytes, 0, bytes.Length);
        
        catch (Exception e)//404 or anything
        
            HttpContext.Response.StatusCode = 400;//BadRequest
        
        await HttpContext.Response.Body.FlushAsync();
        HttpContext.Response.Body.Close();
    

按预期工作。

【讨论】:

不起作用。返回 "System.Byte[]" 而不是 json。 示例来自工作代码。确保函数中没有return 我复制了您的整个代码并将链接更改为仅远程 json。 谢谢。这行得通。对于那些想使用 HttpClient 而不是 WebClient 的人,请参阅下面的修改代码。【参考方案2】:

这是@Alex的代码的修改版本,使用HttpClient而不是WebClient:

public async Task MyJson()//void if not async

    string jsonUrl = "url-to-json";
    HttpContext.Response.ContentType = "application/json";
    using (var client = new HttpClient())
    
        try
        
            byte[] bytes = await client.GetByteArrayAsync(jsonUrl);
            //write to response stream aka Response.Body
            await HttpContext.Response.Body.WriteAsync(bytes, 0, bytes.Length);
        
        catch (Exception e)//404 or anything
        
            HttpContext.Response.StatusCode = 400;//BadRequest
        
        await HttpContext.Response.Body.FlushAsync();
        HttpContext.Response.Body.Close();
    

这是我的实际代码:

    public async Task<IActionResult> MyJson()
    
        const string jsonUrl = "url-to-json";
        HttpContext.Response.ContentType = "application/json";
        using (var client = new HttpClient())
        
            try
            
                byte[] bytes = await client.GetByteArrayAsync(jsonUrl);
                //write to response stream aka Response.Body
                await HttpContext.Response.Body.WriteAsync(bytes, 0, bytes.Length);
                await HttpContext.Response.Body.FlushAsync();
                HttpContext.Response.Body.Close();
            
            catch (Exception e)
            
                return new BadRequestResult();
            
        

        return new BadRequestResult();
    

【讨论】:

主要思想是不要从函数中返回。你的版本总是返回BadRequestResult @Alex:我明白你的意思,这很好。但是,我的版本在没有引发异常时返回 json,仅在出现异常时返回 BadRequestResult。

以上是关于远程 json 的代理调用以避免 CORS 问题的主要内容,如果未能解决你的问题,请参考以下文章

如何构造循环API调用以使JSON结果可用?

需要帮助使用 Alamofire 进行 POST 调用以检索 XML

如何从 $.getJSON 调用以 print_r() 方式打印关联数组?

Angular:如何设置代理以避免 CORS 错误

渲染 ajax POST 调用以填充 DIV 的问题

调用以变量命名的 jQuery 函数