下面这个网站提供免费的api
调用服务,只需要在java
代码中构造简易的请求即可返回所需要的天气数据,直接进入该网站注册即可,每个用户免费的调用额度是3000
条
[易客云天气API免费天气API接口|天气预报接口|全球天气API接口|气象预警|空气质量](http://www.tianqiapi.com/)
contoller
package warren.femalepowersystem.Controller;
import com.fasterxml.jackson.databind.JsonNode;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import warren.femalepowersystem.R.R;
import warren.femalepowersystem.Service.WeatherService;
/**
* <p>
* 前端控制器
* </p>
* * @author * @since 2025-04-13 */@RestController
@RequestMapping("/weather")
public class WeatherController {
@Autowired
private WeatherService weatherService;
/**
* 根据城市获取天气
* @param city
* @return
*/ @GetMapping
public R<JsonNode> getWeather(@RequestParam String city) {
return R.success(weatherService.getWeatherByCity(city));
}
}
service
- 由于返回的原始天气数据格式很乱,我这里使用
JsonNode
进行了格式化,使得数据格式更加美观
package warren.femalepowersystem.Service;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.node.ObjectNode;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;
@Service
public class WeatherService {
//读取配置文件中的appid
@Value("${weather.appid}")
String appid ;
//读取配置文件中的appsecret
@Value("${weather.appsecret}")
String appsecret;
private final RestTemplate restTemplate = new RestTemplate();
// 建议使用单例模式管理 ObjectMapper private final ObjectMapper objectMapper = new ObjectMapper();
public JsonNode getWeatherByCity(String city) {
String url = String.format("http://v1.yiketianqi.com/api?unescape=1&version=v91&appid=%s&appsecret=%s&city=%s", appid, appsecret, city);
try {
// 获取原始 JSON 数据(外层是一个 JSON 对象,但 "data" 字段依然是一个字符串)
String response = restTemplate.getForObject(url, String.class);
// 将外层 JSON 字符串转换为 JsonNode JsonNode rootNode = objectMapper.readTree(response);
// 检查 "data" 字段是否为字符串且内容不为空
if (rootNode.has("data") && rootNode.get("data").isTextual()) {
String dataString = rootNode.get("data").asText();
// 再次解析 "data" 字段,使其成为一个 JSON 对象
JsonNode dataNode = objectMapper.readTree(dataString);
// 将解析后的 dataNode 设置回 rootNode 中,需要强制转换为 ObjectNode if (rootNode instanceof ObjectNode) {
((ObjectNode) rootNode).set("data", dataNode);
}
}
// 返回的 JsonNode 经过 Jackson 自动转换为格式化后的 JSON 字符串(前提是你已经在配置中启用了 Pretty Print,
// 或者调用 writerWithDefaultPrettyPrinter() 进行格式化)
return rootNode;
} catch (Exception e) {
// 出现异常时,输出日志并返回原始内容,以免影响程序继续执行
e.printStackTrace();
return objectMapper.createObjectNode().put("error", "数据处理异常");
}
}
}
返回示例
{
"code": 1,
"msg": null,
"data": {
"cityid": "101031100",
"city": "滨海新区",
"cityEn": "binhaixinqu",
"country": "中国",
"countryEn": "China",
"update_time": "2025-04-13 13:22:12",
"data": [
{
"day": "13日(星期日)",
"date": "2025-04-13",
"week": "星期日",
"wea": "多云",
"wea_img": "yun",
"wea_day": "多云",
"wea_day_img": "yun",
"wea_night": "多云",
"wea_night_img": "yun",
"tem": "12.9",
"tem1": "14",
"tem2": "9",
"humidity": "15%",
"visibility": "30km",
"pressure": "998",
"win": [
"西北风",
"西北风"
],
"win_speed": "5-6级",
"win_meter": "36km/h",
"sunrise": "05:35",
"sunset": "18:44",
"air": "86",
"air_level": "良",
"air_tips": "",
"phrase": "多云时有风",
"narrative": "少云有大风。 最高 13°C。 西北偏北 风 40 到 55 每 km / h 。",
"moonrise": "19:09",
"moonset": "05:26",
"moonPhrase": "满月",
"rain": "6",
"uvIndex": "6",
"uvDescription": "强",
"rain_pcpn": "0.0",
"alarm": []
},
{
"day": "14日(星期一)",
"date": "2025-04-14",
"week": "星期一",
"wea": "多云转晴",
"wea_img": "yun",
"wea_day": "多云",
"wea_day_img": "yun",
"wea_night": "晴",
"wea_night_img": "qing",
"tem": "20",
"tem1": "20",
"tem2": "10",
"humidity": "36%",
"visibility": "",
"pressure": "",
"win": [
"西北风",
"西南风"
],
"win_speed": "4-5级转<3级",
"win_meter": "",
"sunrise": "05:33",
"sunset": "18:45",
"air": "53",
"air_level": "良",
"air_tips": "",
"phrase": "多云时有风",
"narrative": "少云有大风。 最高 20°C。 西北偏北 风 30 到 50 每 km / h 。",
"moonrise": "20:10",
"moonset": "05:48",
"moonPhrase": "亏凸月",
"rain": "2",
"uvIndex": "7",
"uvDescription": "强",
"rain_pcpn": "0.0"
},
{
"day": "15日(星期二)",
"date": "2025-04-15",
"week": "星期二",
"wea": "晴",
"wea_img": "qing",
"wea_day": "晴",
"wea_day_img": "qing",
"wea_night": "晴",
"wea_night_img": "qing",
"tem": "28",
"tem1": "28",
"tem2": "15",
"humidity": "44%",
"visibility": "",
"pressure": "",
"win": [
"西南风",
"东北风"
],
"win_speed": "3-4级转4-5级",
"win_meter": "",
"sunrise": "05:32",
"sunset": "18:46",
"air": "62",
"air_level": "良",
"air_tips": "",
"phrase": "大部地区晴朗",
"narrative": "大部晴朗。 最高 22°C。 西 风转向为 南 风 15 到 30 每 km / h 。",
"moonrise": "21:12",
"moonset": "06:13",
"moonPhrase": "亏凸月",
"rain": "1",
"uvIndex": "7",
"uvDescription": "强",
"rain_pcpn": "0.0"
},
{
"day": "16日(星期三)",
"date": "2025-04-16",
"week": "星期三",
"wea": "多云转晴",
"wea_img": "yun",
"wea_day": "多云",
"wea_day_img": "yun",
"wea_night": "晴",
"wea_night_img": "qing",
"tem": "21",
"tem1": "21",
"tem2": "10",
"humidity": "59%",
"visibility": "",
"pressure": "",
"win": [
"东北风",
"东北风"
],
"win_speed": "4-5级",
"win_meter": "",
"sunrise": "05:30",
"sunset": "18:46",
"air": "62",
"air_level": "良",
"air_tips": "",
"phrase": "局部多云",
"narrative": "少云。 最高 17°C。 东 风 15 到 30 每 km / h 。",
"moonrise": "22:14",
"moonset": "06:44",
"moonPhrase": "亏凸月",
"rain": "2",
"uvIndex": "7",
"uvDescription": "强",
"rain_pcpn": "1.0"
},
{
"day": "17日(星期四)",
"date": "2025-04-17",
"week": "星期四",
"wea": "晴",
"wea_img": "qing",
"wea_day": "晴",
"wea_day_img": "qing",
"wea_night": "晴",
"wea_night_img": "qing",
"tem": "17",
"tem1": "17",
"tem2": "10",
"humidity": "66%",
"visibility": "",
"pressure": "",
"win": [
"西北风",
"东北风"
],
"win_speed": "3-4级",
"win_meter": "",
"sunrise": "05:29",
"sunset": "18:47",
"air": "61",
"air_level": "良",
"air_tips": "",
"phrase": "局部多云",
"narrative": "少云。 最高 16°C。 东 风 10 到 15 每 km / h 。",
"moonrise": "23:15",
"moonset": "07:21",
"moonPhrase": "亏凸月",
"rain": "17",
"uvIndex": "6",
"uvDescription": "强",
"rain_pcpn": "0.0"
},
{
"day": "18日(星期五)",
"date": "2025-04-18",
"week": "星期五",
"wea": "多云转阴",
"wea_img": "yun",
"wea_day": "多云",
"wea_day_img": "yun",
"wea_night": "阴",
"wea_night_img": "yin",
"tem": "17",
"tem1": "17",
"tem2": "10",
"humidity": "67%",
"visibility": "",
"pressure": "",
"win": [
"南风",
"南风"
],
"win_speed": "3-4级转<3级",
"win_meter": "",
"sunrise": "05:28",
"sunset": "18:48",
"air": "47",
"air_level": "优",
"air_tips": "",
"phrase": "局部多云",
"narrative": "少云。 最高 17°C。 东 风 15 到 30 每 km / h 。",
"moonrise": "",
"moonset": "08:06",
"moonPhrase": "亏凸月",
"rain": "24",
"uvIndex": "6",
"uvDescription": "强",
"rain_pcpn": "0.0"
},
{
"day": "19日(星期六)",
"date": "2025-04-19",
"week": "星期六",
"wea": "晴",
"wea_img": "qing",
"wea_day": "晴",
"wea_day_img": "qing",
"wea_night": "晴",
"wea_night_img": "qing",
"tem": "16",
"tem1": "16",
"tem2": "13",
"humidity": "64%",
"visibility": "",
"pressure": "",
"win": [
"无持续风向",
"无持续风向"
],
"win_speed": "<3级",
"win_meter": "",
"sunrise": "05:26",
"sunset": "18:49",
"air": "57",
"air_level": "良",
"air_tips": "",
"phrase": "局部多云",
"narrative": "少云。 最高 17°C。 西北 风转向为 东南 风 15 到 25 每 km / h 。",
"moonrise": "00:11",
"moonset": "08:59",
"moonPhrase": "亏凸月",
"rain": "24",
"uvIndex": "7",
"uvDescription": "强",
"rain_pcpn": "0.0"
}
],
"nums": 0,
"aqi": {
"update_time": "13:09",
"cityid": "101031100",
"city": "",
"cityEn": "",
"country": "",
"countryEn": "",
"air": "40",
"air_level": "优",
"air_tips": "各类人群可多参加户外活动,多呼吸一下清新的空气。",
"pm25": "16",
"pm25_desc": "优",
"pm10": "40",
"pm10_desc": "优",
"o3": "92",
"o3_desc": "",
"no2": "4",
"no2_desc": "",
"so2": "4",
"so2_desc": "",
"co": "0.4",
"co_desc": "",
"kouzhao": "不用佩戴口罩",
"yundong": "适宜运动",
"waichu": "适宜外出",
"kaichuang": "适宜开窗",
"jinghuaqi": "不需要打开"
}
},
"map": {}
}