• Daily Archives: 2020年8月18日

SpringBoot2.1.1微服务架构引入SpringCloudSecurity安全认证

1、在eureka服务器的pom.xml中引入依赖:

	<!-- Spring Cloud Security 依赖 -->
	<dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-security</artifactId>
        </dependency>

2、创建密码安全认证密码匹配规则类MyPasswordEncoder.java:

package com.zero4j.config;

import org.springframework.security.crypto.password.PasswordEncoder;

public class MyPasswordEncoder implements PasswordEncoder {

	@Override
    public String encode(CharSequence charSequence) {
        return charSequence.toString();
    }

    @Override
    public boolean matches(CharSequence charSequence, String s) {
        return s.equals(charSequence.toString());
    }
    
}

3、在eureka服务器中创建配置类SecurityConfig.java:

package com.zero4j.config;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.factory.PasswordEncoderFactories;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;

@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter {
    
	@Bean
    public PasswordEncoder passwordEncoder() {
        return PasswordEncoderFactories.createDelegatingPasswordEncoder();
    }
    
    //@Autowired
    //BCryptPasswordEncoder passwordEncoder;

    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
    	
    	//以前可以不指定PasswordEncoder,但是新的SpringBoot依赖的SpringCloudScurity需要了
    	//auth.inMemoryAuthentication().withUser("admin").password("123456").roles("ADMIN");
    	//这样,密码以明文的方式进行匹配
    	auth.inMemoryAuthentication().passwordEncoder(new MyPasswordEncoder()).withUser("admin").password("123456").roles("ADMIN");
    	//auth.inMemoryAuthentication().withUser("admin").password(passwordEncoder.encode("123456")).roles("ADMIN");
    }

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.csrf().ignoringAntMatchers("/eureka/**");
        super.configure(http);
    }
}

4、启动服务,访问eureka服务中心,使用admin:123456进行登录,成功进入eureka控制台

5、对微服务提供者的application.propertites说引用的eureka服务中心地址的前面加入“admin:123456@”,如:http\://admin:123456@localhost\:8761/eureka/ ,然后启动即可~

SpringBoot2.1.1使用SpringCloud的Feign调用Eureka微服务并开启Hystrix熔断机制

1、先在pom.xml中引入如下依赖:

	<!--Netflix Eureka依赖-->
	<dependency>
		<groupId>org.springframework.cloud</groupId>
		<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
	</dependency>
	<dependency>
		<groupId>org.springframework.cloud</groupId>
		<artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
	</dependency>
	<!--springcloud整合的openFeign-->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>
        </dependency>

2、在pom.xml中的<project></project>之间增加以下关于springcloud的版本管理:

	<dependencyManagement>
		<dependencies>
			<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-dependencies</artifactId>
			<version>${spring-cloud.version}</version>
			<type>pom</type>
			<scope>import</scope>
			</dependency>
		</dependencies>
	</dependencyManagement>

3、在application.propertites中增加如下配置:

#feign的配置,连接超时及读取超时配置
feign.client.config.default.connectTimeout=5000
feign.client.config.default.readTimeout=5000
feign.client.config.default.loggerLevel=basic
#开启熔断功能
feign.hystrix.enabled=true

4、在application启动入口增加@EnableFeignClients注解:

@EnableFeignClients
@ImportResource("classpath:hibernate.xml")
@SpringBootApplication
public class Zero4jApplication extends SpringBootServletInitializer{
	
	@Override
	protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) {
		return builder.sources(Zero4jApplication.class);
	}

	public static void main(String[] args) {
		SpringApplication.run(Zero4jApplication.class, args);
	}

}

5、创建FeignClient客户端:

package com.zero4j.controller.api.v1;

import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PatchMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestParam;

@FeignClient(value="zero4j-provider-area", fallback=AreasApiHystrixV1.class)
public interface AreasApiFeignClientV1 {

	@PatchMapping(value="api/v1/areas/{id}")
	String update(
			@PathVariable(value="id") String id,
			@RequestParam(value="token",required=false) String token,
			@RequestParam(value="name",required=false) String name,
			@RequestParam(value="parentId",required=false) String parentId,
			@RequestParam(value="hasChildren",required=false) Boolean hasChildren
		);

}

6、编写调用微服务的Controller:

package com.zero4j.controller.api.v1;

import java.util.HashMap;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import net.sf.json.JSONObject;

import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpMethod;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PatchMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;

import com.zero4j.model.area.service.AreaService;


@RestController
@RequestMapping("/api/v1/areas")
public class AreasApiControllerV1 {

	@Autowired
	private AreaService areaService;
	
	@Autowired
	private SessionFactory sessionFactory;
	
	@Autowired
	private RestTemplate restTemplate;
	
	@PatchMapping(value="/{id}")
	public ResponseEntity update(HttpServletRequest request,HttpServletResponse response,
			@PathVariable(value="id") String id,
			@RequestParam(required=false) String token,
			@RequestParam(required=false) String name,
			@RequestParam(required=false) String parentId,
			@RequestParam(required=false) Boolean hasChildren
		){
		
		return ResponseEntity.ok((String)areaApiFeignClient.update(id,token,name,parentId,hasChildren));
	}
	

}

7、编写熔断处理方法:

package com.zero4j.controller.api.v1;

import net.sf.json.JSONObject;

import org.springframework.stereotype.Component;

@Component
public class AreasApiHystrixV1 implements AreasApiFeignClientV1 {

	@Override
	public String update(String id, String token, String name, String parentId, Boolean hasChildren) {
		JSONObject out = new JSONObject();
		out.put("status", 400);
		out.put("message", "update服务异常");
		out.put("debug", "update服务异常");
		return out.toString();
	}

}

8、启动服务,访问对应的api,分别在微服务开启、关闭的时候调用API,查看结果即可。

close