Browse Source

代码提交

chenweida 7 years ago
parent
commit
cce43e1c92

+ 2 - 0
common-security-starter/src/main/java/com.yihu.base.security/SercurityConfig.java

@ -8,6 +8,7 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.security.access.PermissionEvaluator;
@ -24,6 +25,7 @@ import java.util.List;
 * Created by chenweida on 2017/12/4.
 */
@Configuration
@ComponentScan("com.yihu.base.security")
public class SercurityConfig {
    private Logger logger = LoggerFactory.getLogger(SercurityConfig.class);

+ 3 - 2
common-security-starter/src/main/java/com.yihu.base.security/config/ResourceServerConfig.java

@ -10,7 +10,6 @@ import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableResourceServer;
import org.springframework.security.oauth2.config.annotation.web.configuration.ResourceServerConfigurerAdapter;
import org.springframework.security.oauth2.config.annotation.web.configurers.ResourceServerSecurityConfigurer;
@ -49,9 +48,11 @@ public class ResourceServerConfig extends ResourceServerConfigurerAdapter {
    public void configure(HttpSecurity http) throws Exception {
        http
                    .csrf().disable()
                .formLogin()//设置验证码 账号密码登陆
                .formLogin()//设置 账号密码登陆
                    .loginPage(SecurityProperties.formLoginPage)
                    .loginProcessingUrl(SecurityProperties.formLogin)
                    .usernameParameter("username")
                    .passwordParameter("password")
                    .successHandler(authenticationSuccessHandler)
                    .failureHandler(authenticationFailureHandler)
                .and()

+ 1 - 1
common-security-starter/src/main/java/com.yihu.base.security/hander/BaseAuthenticationSuccessHandler.java

@ -85,7 +85,7 @@ public class BaseAuthenticationSuccessHandler extends SavedRequestAwareAuthentic
        if (clientDetails == null) {
            throw new UnapprovedClientAuthenticationException("clientId不存在 client:" + clientId);
        } else if (!passwordEncoder.matches(clientSecurity,clientDetails.getClientSecret())) {
        } else if (!StringUtils.equals(clientSecurity,clientDetails.getClientSecret())) {
            throw new UnapprovedClientAuthenticationException("clientSecurity 不匹配 client:" + clientId);
        }

+ 9 - 0
common-security-starter/src/main/java/com.yihu.base.security/rbas/UserServiceProvider.java

@ -0,0 +1,9 @@
package com.yihu.base.security.rbas;
import org.springframework.security.core.userdetails.UserDetailsService;
/**
 * Created by Administrator on 2018/4/3 0003.
 */
public interface UserServiceProvider extends UserDetailsService {
}

+ 2 - 0
common-security-starter/src/main/resources/META-INF/spring.factories

@ -0,0 +1,2 @@
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
  com.yihu.base.security.SercurityConfig

+ 10 - 5
demo/pom.xml

@ -12,6 +12,16 @@
    <artifactId>demo</artifactId>
    <dependencies>
        <dependency>
            <groupId>com.yihu</groupId>
            <artifactId>common-security-starter</artifactId>
            <version>1.0.0</version>
        </dependency>
        <dependency>
            <groupId>com.yihu</groupId>
            <artifactId>common-swagger-starter</artifactId>
            <version>1.0.0</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
@ -21,11 +31,6 @@
            <artifactId>spring-beans</artifactId>
            <version>4.3.10.RELEASE</version>
        </dependency>
        <dependency>
            <groupId>com.yihu</groupId>
            <artifactId>common-logback-starter</artifactId>
            <version>1.0.2</version>
        </dependency>
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-tx</artifactId>

+ 88 - 0
demo/src/main/java/com/demo/config/SwaggerConfig.java

@ -0,0 +1,88 @@
package com.demo.config;
import io.github.swagger2markup.GroupBy;
import io.github.swagger2markup.Language;
import io.github.swagger2markup.Swagger2MarkupConfig;
import io.github.swagger2markup.Swagger2MarkupConverter;
import io.github.swagger2markup.builder.Swagger2MarkupConfigBuilder;
import io.github.swagger2markup.markup.builder.MarkupLanguage;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2;
import java.net.URL;
import java.nio.file.Path;
import java.nio.file.Paths;
import static com.google.common.base.Predicates.or;
import static springfox.documentation.builders.PathSelectors.regex;
@Configuration
@EnableSwagger2
public class SwaggerConfig {
    public static final String system_API = "system"; //系统相关
    @Bean
    public Docket systemAPI() {
        return new Docket(DocumentationType.SWAGGER_2)
                .groupName(system_API)
                .pathMapping("/")
                .select()
                .apis(RequestHandlerSelectors.any()) // 对所有api进行监控
                .paths(or(
                        regex("/system/.*"),
                        regex("/security/.*")
                ))
                .build()
                .apiInfo(systemApiInfo());
    }
    private ApiInfo systemApiInfo() {
        ApiInfo iotInfo = new ApiInfo("基卫2.0API",
                "EHR API,提供开放平台相关服务。",
                "1.0",
                "No terms of service",
                "wenfujian@jkzl.com",
                "The Apache License, Version 2.0",
                "http://www.apache.org/licenses/LICENSE-2.0.html"
        );
        return iotInfo;
    }
    /**
     * 生成html文章专用
     *
     * @param args
     * @throws Exception
     */
    public static void main(String[] args) throws Exception {
        String groupName="openAPI";
       // String groupName="iot";
        URL remoteSwaggerFile = new URL("http://127.0.0.1:8080//v2/api-docs?group="+groupName);
        Path outputFile = Paths.get("open-api/build/"+groupName);
        Swagger2MarkupConfig config = new Swagger2MarkupConfigBuilder()
                .withMarkupLanguage(MarkupLanguage.ASCIIDOC)
                .withOutputLanguage(Language.ZH)
                .withPathsGroupedBy(GroupBy.TAGS)
                .withGeneratedExamples()
                .withoutInlineSchema()
                .withBasePathPrefix()
                .build();
        Swagger2MarkupConverter converter = Swagger2MarkupConverter.from(remoteSwaggerFile)
                .withConfig(config)
                .build();
        converter.toFile(outputFile);
    }
}

+ 130 - 0
demo/src/main/java/com/demo/controller/SecurityController.java

@ -0,0 +1,130 @@
package com.demo.controller;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import net.sf.json.JSONObject;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Random;
import java.util.UUID;
/**
 * Created by Administrator on 2018/4/3 0003.
 */
@RestController
@RequestMapping("/security")
@Api(tags = "登陆相关", description = "登陆相关demo")
public class SecurityController {
    private RestTemplate restTemplate = new RestTemplate();
    /**
     * @return
     */
    @RequestMapping(value = "/login_usernamePassword", method = RequestMethod.POST)
    @ApiOperation("自定义账号密码模式demo")
    public String loginfo() {
        String result = "";
        try {
            //设置header
            HttpHeaders headers = new HttpHeaders();
            headers.add("Accept", "*/*");
            headers.add("Cache-Control", "no-cache");
            //client_id:client_securt
            headers.add("Authorization","Basic Y2xpZW50X2lkOmNsaWVudF9zZWNyZXQ==");
            //传参数JSON格式
            //  封装参数,千万不要替换为Map与HashMap,否则参数无法传递
            MultiValueMap<String, String> params= new LinkedMultiValueMap<String, String>();
            //  也支持中文
            params.add("username", "admin");
            params.add("password", "123456");
            //设置http请求实体
            HttpEntity<MultiValueMap<String, String>> requestEntity = new HttpEntity<MultiValueMap<String, String>>(params, headers);
            result = restTemplate.postForObject("http://localhost:8080/authentication/form", requestEntity, String.class);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "登陆成功:" + result;
    }
    @RequestMapping(value = "/login_sendSms", method = RequestMethod.POST)
    @ApiOperation("发送验证码")
    public String login_sendSms(
            @RequestParam(value = "mobile", required = false)String mobile
    ) {
        String result = "";
        try {
            //设置header
            HttpHeaders headers = new HttpHeaders();
            headers.add("Accept", "*/*");
            headers.add("Cache-Control", "no-cache");
            //client_id:client_securt
            headers.add("Authorization","Basic Y2xpZW50X2lkOmNsaWVudF9zZWNyZXQ==");
            //传参数JSON格式
            //  封装参数,千万不要替换为Map与HashMap,否则参数无法传递
            MultiValueMap<String, String> params= new LinkedMultiValueMap<String, String>();
            //  也支持中文
            params.add("mobile", "admin");
            //设置http请求实体
            HttpEntity<MultiValueMap<String, String>> requestEntity = new HttpEntity<MultiValueMap<String, String>>(params, headers);
            result = restTemplate.postForObject("http://localhost:8080/authentication/form", requestEntity, String.class);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "登陆成功:" + result;
    }
    /**
     * @return
     */
    @RequestMapping(value = "/login_mobileCms", method = RequestMethod.POST)
    @ApiOperation("自定义手机号验证码模式")
    public String login_mobileCms() {
        String result = "";
        try {
            //设置header
            HttpHeaders headers = new HttpHeaders();
            headers.add("Accept", "*/*");
            headers.add("Cache-Control", "no-cache");
            //client_id:client_securt
            headers.add("Authorization","Basic Y2xpZW50X2lkOmNsaWVudF9zZWNyZXQ==");
            //传参数JSON格式
            //  封装参数,千万不要替换为Map与HashMap,否则参数无法传递
            MultiValueMap<String, String> params= new LinkedMultiValueMap<String, String>();
            //  也支持中文
            params.add("mobile", "admin");
            params.add("password", "123456");
            //设置http请求实体
            HttpEntity<MultiValueMap<String, String>> requestEntity = new HttpEntity<MultiValueMap<String, String>>(params, headers);
            result = restTemplate.postForObject("http://localhost:8080/authentication/form", requestEntity, String.class);
        } catch (Exception e) {
            e.printStackTrace();
        }
        return "登陆成功:" + result;
    }
}

+ 18 - 0
demo/src/main/java/com/demo/service/RBASService.java

@ -0,0 +1,18 @@
package com.demo.service;
import com.yihu.base.security.rbas.RbasServiceProvider;
import org.springframework.security.core.Authentication;
import org.springframework.stereotype.Component;
import javax.servlet.http.HttpServletRequest;
/**
 * Created by Administrator on 2018/4/3 0003.
 */
@Component("rbasServiceProvider")
public class RBASService implements RbasServiceProvider {
    @Override
    public Boolean hasPerssion(HttpServletRequest request, Authentication authentication) {
        return true;
    }
}

+ 44 - 0
demo/src/main/java/com/demo/service/UserService.java

@ -0,0 +1,44 @@
package com.demo.service;
import com.yihu.base.security.rbas.ClientServiceProvider;
import com.yihu.base.security.rbas.UserServiceProvider;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.authority.AuthorityUtils;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.oauth2.provider.ClientDetails;
import org.springframework.security.oauth2.provider.ClientRegistrationException;
import org.springframework.security.oauth2.provider.client.BaseClientDetails;
import org.springframework.stereotype.Component;
import java.util.ArrayList;
/**
 * Created by Administrator on 2018/4/3 0003.
 */
@Component
public class UserService implements ClientServiceProvider, UserServiceProvider {
    @Autowired
    private PasswordEncoder passwordEncoder;
    @Override
    public ClientDetails loadClientByClientId(String clientId) throws ClientRegistrationException {
        BaseClientDetails baseClientDetails = new BaseClientDetails();
        baseClientDetails.setClientId("client_id");
        baseClientDetails.setClientSecret("client_secret");
        return baseClientDetails;
    }
    @Override
    public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
        return new User("admin",
                    passwordEncoder.encode("123456"),
                    true,
                    true,
                    true,
                    true
                    , AuthorityUtils.commaSeparatedStringToAuthorityList("admin,ROLE_USER")); //权限
    }
}

+ 43 - 0
demo/src/main/resources/application.yml

@ -1,2 +1,45 @@
server:
  port: 8080
spring:
  datasource:
    driver-class-name: com.mysql.jdbc.Driver
    max-active: 50
    max-idle: 50 #最大空闲连接
    min-idle: 10 #最小空闲连接
    validation-query-timeout: 20
    log-validation-errors: true
    validation-interval: 60000 #避免过度验证,保证验证不超过这个频率——以毫秒为单位。如果一个连接应该被验证,但上次验证未达到指定间隔,将不再次验证。
    validation-query: SELECT 1 #SQL 查询, 用来验证从连接池取出的连接, 在将连接返回给调用者之前。 如果指定, 则查询必须是一个SQL SELECT 并且必须返回至少一行记录
    test-on-borrow: true #指明是否在从池中取出连接前进行检验, 如果检验失败, 则从池中去除连接并尝试取出另一个。注意: 设置为true 后如果要生效,validationQuery 参数必须设置为非空字符串
    test-on-return: true #指明是否在归还到池中前进行检验 注意: 设置为true 后如果要生效validationQuery 参数必须设置为非空字符串
    idle-timeout: 30000
    connection-test-query: SELECT 1
    num-tests-per-eviction-run: 50 #在每次空闲连接回收器线程(如果有)运行时检查的连接数量,最好和maxActive
    test-while-idle: true #指明连接是否被空闲连接回收器(如果有)进行检验,如果检测失败,则连接将被从池中去除
    min-evictable-idle-time-millis: 3600000 #连接池中连接,在时间段内一直空闲,被逐出连接池的时间(1000*60*60),以毫秒为单位
    time-between-eviction-runs-millis: 300000 #在空闲连接回收器线程运行期间休眠的时间值,以毫秒为单位,一般比minEvictableIdleTimeMillis小
    url: jdbc:mysql://127.0.0.1/oauth?useUnicode=true&amp;characterEncoding=utf-8&amp;autoReconnect=true
    username: root
    password: 123456
  redis:
    host: 172.19.103.88 # Redis server host.
    port: 6379 # Redis server port.
    database: 0
  aop:
    proxy-target-class: true
security:
  oauth2:
    token:
      accessTokenValidityHours: 2 # 2小时
      refreshTokenValidityHours: 2 # 2小时
      tokenType: accessToken
    sms:
      expireIn: 1 ##1分钟过期
      length: 6 #验证码长度

+ 0 - 23
demo/src/main/resources/logback.xml

@ -8,29 +8,6 @@
    <logger name="io.searchbox" level="WARN"/>
    <appender name="hbase_appender" class="com.yihu.base.hbase.HbaseAppender">
        <tableName>flumeLog</tableName><!--表明-->
        <familyName>flumeLogFamily</familyName> <!--列族-->
        <zkHosts>master,slave1,slave2</zkHosts>  <!--zk 路径-->
        <hdfsUserName>hadoop</hdfsUserName> <!--hdfs的用户名-->
        <zkZnodeParent>/hbase</zkZnodeParent>
        <rowkey>UUID</rowkey> <!--rowKey规则  目前只支持UUID 默认UUID -->
    </appender>
    <appender name="console" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>%d{yyyy/MM/dd-HH:mm:ss} %level [%thread] %caller{1} - %msg%n</pattern>
            <charset class="java.nio.charset.Charset">UTF-8</charset>
        </encoder>
    </appender>
    <logger name="hbase_logger" level="INFO" additivity="false">
        <appender-ref ref="hbase_appender"/>
    </logger>
    <!--提高整个日志的错误级别-->
    <root level="INFO">
    </root>