查询天气预报系统之---如何将传统服务拆分成微服务(六)

我们做的这一系列的工作,其实目的就是为了将我们的服务进行拆分成微服务,我们可以简单看一下这个系统,它集成了数据采集,数据缓存,提供查询天气等功能,但是唯一的不足之处,耦合性太高,缺少业务上的隔离,一旦第三方采集的接口协议变化或者缓存服务down掉;都会影响到整个应用,所以,我们开始拆分服务,采用微服务的方式。

针对这个天气预报系统我们可以拆分成四个微服务:分别为:

天气数据采集微服务(springBoot-collection)

天气数据API微服务(springBoot-data)

城市数据API微服务(springBoot-city)

天气预报微服务(springBoot-report)

天气数据采集微服务(springBoot-collection)

项目:

CityClient这个接口现在不需要放在这里,后面才会用到。

 

pom文件:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>com.csq.study</groupId>
  <artifactId>springBoot-collection</artifactId>
  <version>0.0.1-SNAPSHOT</version>
<parent>
		<groupId>org.springframework.boot</groupId>
		<artifactId>spring-boot-starter-parent</artifactId>
		 <version>1.5.2.RELEASE</version>
	</parent>
	
	<dependencies>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-web</artifactId>
		</dependency>

		<!-- https://mvnrepository.com/artifact/org.apache.httpcomponents/httpclient -->
		<dependency>
			<groupId>org.apache.httpcomponents</groupId>
			<artifactId>httpclient</artifactId>
		</dependency>
		<!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-test -->
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-test</artifactId>
			<scope>test</scope>
		</dependency>
		<!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-data-redis -->
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-data-redis</artifactId>
		</dependency>
		<!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-quartz -->
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-quartz</artifactId>
			  <version>2.1.5.RELEASE</version>
			</dependency>
		</dependencies>
		<build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>
</project>

配置类 config

package com.yian.springboot.config;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.web.client.RestTemplateBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;
/**
 * 配置类
 * @Description: TODO 
 * @ClassName: RestConfiguration
 * @author csq 2019年2月28日 上午10:25:38
 * @see TODO
 */
@Configuration
public class RestConfiguration {

	@Autowired
	private RestTemplateBuilder builder;
	@Bean
	public RestTemplate restTemplate(){
		return builder.build();
	}
}

job类


package com.yian.springboot.job;

import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

import com.yian.springboot.service.WeatherDataCollectionService;
import com.yian.springboot.vo.City;

@Component
public class ScheduledTasks {

	  private static final Logger logger = LoggerFactory.getLogger(ScheduledTasks.class);
	  private static final SimpleDateFormat formate = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
	 
	  
	  @Autowired
	  private WeatherDataCollectionService weatherDataCollectionService;
	    @Scheduled(fixedRate = 30000)
	    public void scheduledDemo(){
	        logger.info("天气数据同步任务 开始  every 5 seconds:{}", formate.format(new Date()) );
	        
	        List<City> cityList=null;
	   
	        try {
          //此处因为还需要另外一个微服务提供,所以为了演示本微服务 我们暂且写死,后面会进行修改
				cityList = new ArrayList<City>();
	        	City city=new City();
	        	city.setCityId("101010100");
	        	cityList.add(city);
			} catch (Exception e) {
				logger.info("获取异常",e);
			}
	        
	       for (City city : cityList) {
	    	   String cityId = city.getCityId();
	    	   logger.info("天气任务同步中,cityId:"+cityId);
	    	   //根据城市id获取天气
	    	   weatherDataCollectionService.syncDataByCityId(cityId);
		}
	       logger.info("天气任务同步End");
	    }
}

 

service接口和实现类

package com.yian.springboot.service;

public interface WeatherDataCollectionService {
     /**
      * 根据城市Id同步天气数据
      * @Title: syncDataByCityId 
      * @Description: TODO 
      * @param cityId
      * @author csq 2019年6月4日 下午2:35:52
      */
	void syncDataByCityId(String cityId);
}
实现类:
package com.yian.springboot.service;

import java.util.concurrent.TimeUnit;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;
/**
 * 
 * @Description: 天气数据采集服务
 * @ClassName: WeatherDataCollectionServiceImpl
 * @author csq  2019年6月4日 下午2:37:25
 * @see TODO
 */
@Service
public class WeatherDataCollectionServiceImpl implements WeatherDataCollectionService {
	
	
	private final static Logger logger=LoggerFactory.getLogger(WeatherDataCollectionServiceImpl.class);
	
	@Autowired
	private RestTemplate restTemplate;
	@Autowired
	private StringRedisTemplate stringRedisTemplate;
	
	private final String WEATHER_API="http://wthrcdn.etouch.cn/weather_mini";
	 //设置超时时间
	private final Long TIME_OUT=1800L;

	@Override
	public void syncDataByCityId(String cityId) {
		logger.info("Start 同步天气 .cityId"+cityId);
		String uri = WEATHER_API + "?citykey=" + cityId;
        this.saveWeatherData(uri);
        
        logger.info("End 同步天气");
	}
	private void saveWeatherData(String uri) {
		String key=uri;
        String strBody = null;
        ValueOperations<String, String> ops = stringRedisTemplate.opsForValue();
        //调用服务接口来获取
        ResponseEntity<String> respString = restTemplate.getForEntity(uri,String.class);

        //将接口返回的Json字符串转换成对象
        if (respString.getStatusCodeValue() == 200) {
            strBody = respString.getBody();
        }

        //数据写入缓存
        ops.set(key,strBody,TIME_OUT, TimeUnit.SECONDS);
    }
}

vo类

package com.yian.springboot.vo;
public class City{	 
	    private String cityId;	  
	    private String cityName;  
	    private String cityCode;	  
	    private String province;

		public String getCityId() {
			return cityId;
		}
		public void setCityId(String cityId) {
			this.cityId = cityId;
		}
		public String getCityName() {
			return cityName;
		}
		public void setCityName(String cityName) {
			this.cityName = cityName;
		}
		public String getCityCode() {
			return cityCode;
		}
		public void setCityCode(String cityCode) {
			this.cityCode = cityCode;
		}
		public String getProvince() {
			return province;
		}
		public void setProvince(String province) {
			this.province = province;
		}
        	@Override
		public String toString() {
			return "City [cityId=" + cityId + ", cityName=" + cityName + ", cityCode=" + cityCode + ", province="
					+ province + "]";
		}		    
}

配置文件 

启动类:

package com.yian.springboot;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.scheduling.annotation.EnableScheduling;
@SpringBootApplication
@EnableScheduling
public class Aplication {
	public static void main(String[] args) {
		SpringApplication.run(Aplication.class, args);
	}

}

在启动程序之前别忘记启动你的redis哦。

启动程序:看到如下截图就成功了。

猜你喜欢

转载自blog.csdn.net/FindHuni/article/details/91415612