我正在学习使用ASP.NET核心创建API,为此我遇到了一个问题,我正在尝试使用我的API执行对外部API的请求,但我不知道如何执行请求并返回请求的JSON,有帮助吗?
应用程序的流程如下所示:
SPA-> AspNet Core WEB API->外部API
到目前为止我所做的:
[Route("api/[Controller]")]
public class RankingsController : Controller
{
private readonly IRankingRepository _rankingRepository;
public RankingsController(IRankingRepository rankingRepo)
{
_rankingRepository = rankingRepo;
}
[HttpGet("{id}", Name = "GetRanking")]
public IActionResult GetById(long id)
//Here is where I want to make the requisition
}
}
我需要为此API发出请求:
http://api.football-data.org/v1/competitions/ {id} / leagueTable
在ID位置,我需要传递一个来自我的API中的请求的参数;
对这个问题有帮助吗?
很抱歉,您回答的不是这么复杂。
谢谢!
答案 0 :(得分:3)
您可以使用HttpClient
实例来实现所需的功能。但是,我总是觉得更容易使用RestSharp。
这当然取决于您的约束,但是如果您在这种情况下没有约束,则可以使用 RestSharp 来调用外部API:
安装:
Install-Package RestSharp
用法:
using RestSharp;
[HttpGet("{id}", Name = "GetRanking")]
public IActionResult GetById(long id)
{
var client = new RestClient("http://api.football-
data.org/v1/competitions/445/leagueTable");
var request = new RestRequest(Method.GET);
IRestResponse response = client.Execute(request);
//TODO: transform the response here to suit your needs
return Ok(data);
}
要使用RestSharp的其余响应,必须使用response.Content
属性。
例如,您可以将其反序列化为Json,对其进行调整以适合您的需求,然后将所需的数据返回给API调用者。
示例:
假设我想获得2017/18英超联赛的排名(Id = 445):
下面,我将从传奇的Newtonsoft.Json包中获得很多帮助,并从jpath
语法中获得一些帮助,但是我假设您已经使用了这两种方法: )
创建几个模型来保存要返回给API调用者的值:
public class LeagueTableModel
{
public string LeagueCaption { get; set; }
public IEnumerable<StandingModel> Standings { get; set; }
}
public class StandingModel
{
public string TeamName { get; set; }
public int Position { get; set; }
}
在服务类中实现以下方法,该方法通过DI / IoC注入到您的控制器中,以避免耦合并提高可测试性(众所周知,我们应该做对吗?)。我假设您的示例中此类为RankingRepository
:
public RankingRepository: IRankingRepository
{
public LeagueTableModel GetRankings(long id)
{
var client = new RestClient($"http://api.football-data.org/v1/competitions/{id}/leagueTable");
var request = new RestRequest(Method.GET);
IRestResponse response = client.Execute(request);
if (response.IsSuccessful)
{
var content = JsonConvert.DeserializeObject<JToken>(response.Content);
//Get the league caption
var leagueCaption = content["leagueCaption"].Value<string>();
//Get the standings for the league.
var rankings = content.SelectTokens("standing[*]")
.Select(team => new StandingModel
{
TeamName = (string)team["teamName"],
Position = (int)team["position"]
})
.ToList();
//return the model to my caller.
return new LeagueTableModel
{
LeagueCaption = leagueCaption,
Standings = rankings
};
}
//TODO: log error, throw exception or do other stuffs for failed requests here.
Console.WriteLine(response.Content);
return null;
}
}
从控制器使用它:
[Route("api/[Controller]")]
public class RankingsController : Controller
{
private readonly IRankingRepository _rankingRepository;
public RankingsController(IRankingRepository rankingRepo)
{
_rankingRepository = rankingRepo;
}
[HttpGet("{id}", Name = "GetRanking")]
public IActionResult GetById(long id)
//Here is where I want to make the requisition
var model = _rankingRepository.GetRankings(id);
//Validate if null
if (model == null)
return NotFound(); //or any other error code accordingly. Bad request is a strong candidate also.
return Ok(model);
}
}
希望这会有所帮助!