Commit b4c0d038 authored by qiwanqing's avatar qiwanqing Committed by qiwanqing

自定义登录、授权页面

parent 8390fc6f
......@@ -29,12 +29,25 @@
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<!-- oauth -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-configuration-processor</artifactId>
<optional>true</optional>
</dependency>
<!--&lt;!&ndash; oauth &ndash;&gt;
<dependency>
<groupId>org.springframework.security.oauth</groupId>
<artifactId>spring-security-oauth2</artifactId>
<version>2.2.1.RELEASE</version>
<version>2.3.3.RELEASE</version>
</dependency>-->
<dependency>
<groupId>org.springframework.security.oauth.boot</groupId>
<artifactId>spring-security-oauth2-autoconfigure</artifactId>
<version>2.1.3.RELEASE</version>
</dependency>
<!-- security -->
<dependency>
<groupId>org.springframework.cloud</groupId>
......@@ -54,7 +67,34 @@
<scope>runtime</scope>
<version>5.1.47</version>
</dependency>
<!--redis-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
<!--swagger start-->
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger2</artifactId>
<version>2.9.2</version>
</dependency>
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-swagger-ui</artifactId>
<version>2.9.2</version>
</dependency>
<!--swagger end-->
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
</dependency>
</dependencies>
<build>
......
package com.yingxin.server.client;
import com.yingxin.server.client.Service.ClientService;
import com.yingxin.server.client.Service.Impl.ClientServiceImpl;
import com.yingxin.server.client.entities.Client;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableAuthorizationServer;
import org.springframework.security.oauth2.provider.ClientDetailsService;
import org.springframework.security.oauth2.provider.ClientRegistrationException;
import org.springframework.security.oauth2.provider.OAuth2Authentication;
import org.springframework.security.oauth2.provider.client.BaseClientDetails;
import org.springframework.security.oauth2.provider.code.AuthorizationCodeServices;
import org.springframework.security.oauth2.provider.code.RandomValueAuthorizationCodeServices;
import java.util.Arrays;
import java.util.HashSet;
import java.util.List;
import java.util.concurrent.TimeUnit;
@EnableAuthorizationServer
@SpringBootApplication
public class ClientApplication {
@Bean
public ClientService clientService(){
return new ClientServiceImpl();
}
@Bean
public BCryptPasswordEncoder bCryptPasswordEncoder(){
return new BCryptPasswordEncoder();
}
@Autowired
BCryptPasswordEncoder bCryptPasswordEncoder;
@Bean
public ClientDetailsService myClientDetailsService(ClientService clientService) {
return clientId -> {
List<Client> clients1 = clientService.findClientByCLientId(clientId);
if (clients1 == null || clients1.size() == 0) {
throw new ClientRegistrationException("clientId无效");
}
Client client = clients1.get(0);
String clientSecretAfterEncoder = bCryptPasswordEncoder.encode(client.getClientSecret());
BaseClientDetails clientDetails = new BaseClientDetails();
clientDetails.setClientId(client.getClientId());
clientDetails.setClientSecret(clientSecretAfterEncoder);
clientDetails.setRegisteredRedirectUri(new HashSet(Arrays.asList(client.getWebServerRedirectUri())));
clientDetails.setAuthorizedGrantTypes(Arrays.asList(client.getAuthorizedGrantTypes().split(",")));
clientDetails.setScope(Arrays.asList(client.getScope().split(",")));
return clientDetails;
};
}
public static void main(String[] args) {
SpringApplication.run(ClientApplication.class, args);
}
......
package com.yingxin.server.client.Service;
import com.yingxin.server.client.entities.Client;
import java.util.List;
public interface ClientService {
List<Client> findClientByCLientId(String clientId);
}
package com.yingxin.server.client.Service.Impl;
import com.yingxin.server.client.Service.ClientService;
import com.yingxin.server.client.dao.ClientDao;
import com.yingxin.server.client.entities.Client;
import org.springframework.beans.factory.annotation.Autowired;
import java.util.List;
public class ClientServiceImpl implements ClientService{
@Autowired
ClientDao clientDao;
@Override
public List<Client> findClientByCLientId(String clientId) {
return clientDao.findClientByCLientId(clientId);
}
}
package com.yingxin.server.client.Service.Impl;
import com.yingxin.server.client.Service.UserService;
import com.yingxin.server.client.dao.UserDao;
import com.yingxin.server.client.entities.Role;
import com.yingxin.server.client.entities.User;
import org.springframework.beans.factory.annotation.Autowired;
import java.util.List;
public class UserServiceImpl implements UserService {
@Autowired
private UserDao userDao;
@Override
public User findByUsername(String username) {
return userDao.findByUsername(username);
}
@Override
public List<Role> findRoleByUsername(String username) {
return userDao.findRoleByUsername(username);
}
}
package com.yingxin.server.client.Service;
import com.yingxin.server.client.entities.Role;
import com.yingxin.server.client.entities.User;
import java.util.List;
public interface UserService {
User findByUsername(String username);
List<Role> findRoleByUsername(String username);
}
......@@ -3,15 +3,21 @@ package com.yingxin.server.client.config;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.redis.connection.RedisConnectionFactory;
import org.springframework.http.HttpMethod;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.factory.PasswordEncoderFactories;
import org.springframework.security.oauth2.config.annotation.configurers.ClientDetailsServiceConfigurer;
import org.springframework.security.oauth2.config.annotation.web.configuration.AuthorizationServerConfigurerAdapter;
import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerEndpointsConfigurer;
import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerSecurityConfigurer;
import org.springframework.security.oauth2.provider.ClientDetailsService;
import org.springframework.security.oauth2.provider.code.AuthorizationCodeServices;
import org.springframework.security.oauth2.provider.token.TokenStore;
import org.springframework.security.oauth2.provider.token.store.InMemoryTokenStore;
import org.springframework.security.oauth2.provider.token.store.redis.RedisTokenStore;
import javax.annotation.Resource;
import javax.sql.DataSource;
/**
* description//TODO
......@@ -22,18 +28,22 @@ import org.springframework.security.oauth2.provider.token.store.InMemoryTokenSto
*/
@Configuration
public class AuthorizationServerConfiguration extends AuthorizationServerConfigurerAdapter {
@Autowired
private AuthenticationManager authenticationManager;
@Autowired
private RedisConnectionFactory connectionFactory;
@Autowired
UserDetailsService myUserDetailsService;
// 使用最基本的InMemoryTokenStore生成token
@Autowired
ClientDetailsService myClientDetailsService;
@Bean
public TokenStore memoryTokenStore() {
return new InMemoryTokenStore();
public RedisTokenStore redisTokenStore(){
return new RedisTokenStore(connectionFactory);
}
/**
......@@ -44,12 +54,7 @@ public class AuthorizationServerConfiguration extends AuthorizationServerConfig
*/
@Override
public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
clients.inMemory()
.withClient("client1")//用于标识用户ID
.authorizedGrantTypes("authorization_code","client_credentials","password","refresh_token")//授权方式
.scopes("test")//授权范围
.secret(PasswordEncoderFactories.createDelegatingPasswordEncoder().encode("123456"));//客户端安全码,secret密码配置从 Spring Security 5.0开始必须以 {bcrypt}+加密后的密码 这种格式填写;
// .secret(PasswordEncoderFactories.createDelegatingPasswordEncoder().encode("123456"));passwordEncoder.encode("123456")
clients.withClientDetails(myClientDetailsService);
}
/**
......@@ -60,7 +65,6 @@ public class AuthorizationServerConfiguration extends AuthorizationServerConfig
@Override
public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
/* 配置token获取合验证时的策略 */
// security.tokenKeyAccess("permitAll()").checkTokenAccess("isAuthenticated()");
security.tokenKeyAccess("permitAll()").checkTokenAccess("isAuthenticated()").allowFormAuthenticationForClients();
}
......@@ -72,9 +76,9 @@ public class AuthorizationServerConfiguration extends AuthorizationServerConfig
*/
@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
// 配置tokenStore,需要配置userDetailsService,否则refresh_token会报错
endpoints.authenticationManager(authenticationManager).tokenStore(memoryTokenStore()).userDetailsService(myUserDetailsService);
endpoints.authenticationManager(authenticationManager)
.tokenStore(new RedisTokenStore(connectionFactory))
.userDetailsService(myUserDetailsService)
.allowedTokenEndpointRequestMethods(HttpMethod.GET,HttpMethod.POST);
}
}
package com.yingxin.server.client.config;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Configuration;
@Configuration
@EnableConfigurationProperties
public class MySecurityProperties {
private String loginProcessUrl="/auth/authorize";
private String loginPage="/auth/login";
public String getLoginProcessUrl() {
return loginProcessUrl;
}
public void setLoginProcessUrl(String loginProcessUrl) {
this.loginProcessUrl = loginProcessUrl;
}
public String getLoginPage() {
return loginPage;
}
public void setLoginPage(String loginPage) {
this.loginPage = loginPage;
}
}
/*
package com.yingxin.server.client.config;
import org.springframework.security.core.Authentication;
import org.springframework.security.oauth2.provider.token.DefaultUserAuthenticationConverter;
import java.util.LinkedHashMap;
import java.util.Map;
public class MyUserAuthenticationConverter extends DefaultUserAuthenticationConverter {
@Override
public Map<String, ?> convertUserAuthentication(Authentication authentication) {
Map<String, Object> response = new LinkedHashMap();
response.put("user_name", authentication);
return response;
}
}
*/
package com.yingxin.server.client.config;
import com.yingxin.server.client.dao.UserDao;
import com.yingxin.server.client.Service.Impl.UserServiceImpl;
import com.yingxin.server.client.Service.UserService;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
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.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.factory.PasswordEncoderFactories;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Component;
/**
* description//TODO
* 自定义登陆
......@@ -28,15 +28,22 @@ public class MyUserDetailsService implements UserDetailsService {
private org.slf4j.Logger logger = LoggerFactory.getLogger(getClass());
@Bean
public UserService userService(){
return new UserServiceImpl();
}
@Autowired
private UserDao userDao;
private UserService userService;
@Autowired
BCryptPasswordEncoder bCryptPasswordEncoder;
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
logger.info("登陆用户名:",username);
// return
return new User(username, PasswordEncoderFactories.createDelegatingPasswordEncoder().encode((userDao.findByUsername(username)).getPassword()), AuthorityUtils.commaSeparatedStringToAuthorityList("admin"));
logger.info("登陆用户名:");
logger.info(username);
return new User(username, bCryptPasswordEncoder.encode((userService.findByUsername(username).getPassword())), AuthorityUtils.commaSeparatedStringToAuthorityList("myClient"));
}
}
package com.yingxin.server.client.config;
import com.yingxin.server.client.dao.UserDao;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.security.authentication.AuthenticationManager;
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.builders.WebSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.factory.PasswordEncoderFactories;
import org.springframework.security.provisioning.InMemoryUserDetailsManager;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
/**
......@@ -26,6 +28,9 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Autowired
private UserDetailsService myUserDetailsService;
@Autowired
private MySecurityProperties properties;
/**
* 配置这个bean会在做AuthorizationServerConfigurer配置的时候使用
* @return
......@@ -37,11 +42,44 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter {
return super.authenticationManagerBean();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(myUserDetailsService).passwordEncoder(new BCryptPasswordEncoder());
}
@Override
public void configure(WebSecurity web) throws Exception {
web.ignoring().antMatchers
("/swagger-ui.html/**", "/webjars/**",
"/swagger-resources/**", "/v2/api-docs/**",
"/swagger-resources/configuration/ui/**", "/swagger-resources/configuration/security/**",
"/images/**");
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(myUserDetailsService);
protected void configure(HttpSecurity http) throws Exception {
http
// 必须配置,不然OAuth2的http配置不生效
.requestMatchers()
.antMatchers( "/oauth/**",properties.getLoginProcessUrl(),properties.getLoginPage())
.and()
.authorizeRequests()
// 自定义页面或处理url时,如果不配置全局允许,浏览器会提示服务器将页面转发多次
.antMatchers("/auth/login",properties.getLoginProcessUrl())
.permitAll()
.anyRequest()
.authenticated();
// 表单登录
http.formLogin()
// 登录页面
.loginPage(properties.getLoginPage())
.loginProcessingUrl(properties.getLoginProcessUrl());
http.httpBasic().disable();
}
}
package com.yingxin.server.client.controller;
import com.yingxin.server.client.Service.ClientService;
import com.yingxin.server.client.Service.UserService;
import com.yingxin.server.client.entities.Client;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.web.client.RestTemplateBuilder;
import org.springframework.context.annotation.Bean;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.http.client.ClientHttpResponse;
import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
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.DefaultResponseErrorHandler;
import org.springframework.web.client.RestTemplate;
import java.io.IOException;
import java.security.Principal;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@RestController
public class CallbackController {
@Bean
public RestTemplate restTemplate(RestTemplateBuilder builder) {
return builder.build();
}
@Autowired
private RestTemplate restTemplate;
@Autowired
ClientService clientService;
@Autowired
UserService userService;
private org.slf4j.Logger logger = LoggerFactory.getLogger(getClass());
@RequestMapping("/oauth/callback")
public Map getToken(@RequestParam(value = "code") String code, Principal principal){
//String role=userService.findRoleByUsername(principal.getName()).iterator().next().getRole_name();
//System.out.println(role);
String clientId="client1";
logger.info("receive code {}",code);
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_FORM_URLENCODED);
MultiValueMap<String,String> params= new LinkedMultiValueMap<>();
List<Client> clients=clientService.findClientByCLientId(clientId);
params.add("grant_type","authorization_code");
params.add("code",code);
params.add("client_id",clientId);
params.add("client_secret",clients.get(0).getClientSecret());
params.add("redirect_uri",clients.get(0).getWebServerRedirectUri());
HttpEntity<MultiValueMap<String,String>> requestEntity = new HttpEntity<>(params, headers);
//System.out.println(requestEntity.toString());
ResponseEntity<Map> response = restTemplate.postForEntity("http://localhost:8080/oauth/token",requestEntity,Map.class);
Map token = response.getBody();
logger.info("token => {}",token);
Map map=new HashMap();
map.put("access_token",token.get("access_token").toString());
logger.info("access_token => {}",token.get("access_token").toString());
restTemplate.setErrorHandler(new DefaultResponseErrorHandler() {
@Override
public void handleError(ClientHttpResponse response) throws IOException {
if (response.getRawStatusCode() != 401) {
super.handleError(response);
}
}
});
ResponseEntity<Map> responseEntity=restTemplate.getForEntity("http://localhost:8088/user?access_token={access_token}",Map.class,map);
return responseEntity.getBody();
}
}
package com.yingxin.server.client.controller;
import org.springframework.security.oauth2.provider.AuthorizationRequest;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.SessionAttributes;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import java.util.Map;
@Controller
@SessionAttributes("authorizationRequest")
public class GrantController {
@RequestMapping(value = "/oauth/confirm_access")
public ModelAndView getAccessConfirmation(Map<String, Object> model,HttpServletRequest request) throws Exception {
AuthorizationRequest authorizationRequest = (AuthorizationRequest) model.get("authorizationRequest");
String clientId=authorizationRequest.getClientId();
ModelAndView view = new ModelAndView();
view.setViewName("grant");
view.addObject("clientId",clientId );
view.addObject("scopes",authorizationRequest.getScope());
System.out.println(authorizationRequest.toString());
return view;
}
}
package com.yingxin.server.client.controller;
import com.yingxin.server.client.config.MySecurityProperties;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
@Controller
public class LoginController {
@Autowired
private MySecurityProperties properties;
@RequestMapping("/auth/login")
public String login(Model model) {
//System.out.println(properties.getLoginProcessUrl());
model.addAttribute("loginProcessUrl",properties.getLoginProcessUrl());
return "login";
}
}
package com.yingxin.server.client.dao;
import com.yingxin.server.client.entities.Client;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
import java.util.List;
@Mapper
public interface ClientDao {
@Select("select * from oauth_client_details where clientId = #{clientId}")
List<Client> findClientByCLientId(@Param("clientId") String clientId);
}
package com.yingxin.server.client.dao;
import com.yingxin.server.client.entities.Role;
import com.yingxin.server.client.entities.User;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.annotations.*;
import java.util.List;
/**
* description//TODO
......@@ -17,4 +17,7 @@ public interface UserDao {
@Select("select * from user where username = #{username}")
User findByUsername(@Param("username") String username);
@Select("select role_name,role.id from user,role where user.role_id=role.id and username= #{username}")
List<Role> findRoleByUsername(@Param("username") String username);
}
package com.yingxin.server.client.entities;
public class Client {
private String clientId;
private String clientSecret;
private String scope;
private String authorizedGrantTypes;
private String webServerRedirectUri;
public String getClientId() {
return clientId;
}
public void setClientId(String clientId) {
this.clientId = clientId;
}
public String getClientSecret() {
return clientSecret;
}
public void setClientSecret(String clientSecret) {
this.clientSecret = clientSecret;
}
public String getScope() {
return scope;
}
public void setScope(String scope) {
this.scope = scope;
}
public String getAuthorizedGrantTypes() {
return authorizedGrantTypes;
}
public void setAuthorizedGrantTypes(String authorizedGrantTypes) {
this.authorizedGrantTypes = authorizedGrantTypes;
}
public String getWebServerRedirectUri() {
return webServerRedirectUri;
}
public void setWebServerRedirectUri(String webServerRedirectUri) {
this.webServerRedirectUri = webServerRedirectUri;
}
@Override
public String toString() {
return "Client{" +
"clientId='" + clientId + '\'' +
", clientSecret='" + clientSecret + '\'' +
", scope='" + scope + '\'' +
", authorizedGrantTypes='" + authorizedGrantTypes + '\'' +
", webServerRedirectUri='" + webServerRedirectUri + '\'' +
'}';
}
}
package com.yingxin.server.client.entities;
public class Role {
private Integer id;
private String role_name;
@Override
public String toString() {
return "Role{" +
"id=" + id +
", role_name='" + role_name + '\'' +
'}';
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getRole_name() {
return role_name;
}
public void setRole_name(String role_name) {
this.role_name = role_name;
}
}
......@@ -8,18 +8,18 @@ package com.yingxin.server.client.entities;
* @date 2019/8/22
*/
public class User {
private Integer uid;
private Integer id;
private String username;
private String password;
public Integer getUid() {
return uid;
public Integer getId() {
return id;
}
public void setUid(Integer uid) {
this.uid = uid;
public void setId(Integer id) {
this.id = id;
}
public String getUsername() {
......@@ -40,6 +40,10 @@ public class User {
@Override
public String toString() {
return "User{" + "uid=" + uid + ", username='" + username + '\'' + ", password='" + password + '\'' + '}';
return "User{" +
"id=" + id +
", username='" + username + '\'' +
", password='" + password + '\'' +
'}';
}
}
server:
port: 8080
spring:
datasource:
# 数据源基本配置
......@@ -22,8 +21,11 @@ spring:
poolPreparedStatements: true
# 配置监控统计拦截的filters ,去掉后监控界面sql无法统计,'wall'用于防火墙
filters: stat,wall,log4j
redis:
url: redis://localhost:6379
thymeleaf:
prefix: classpath:/views/
suffix: .html
cache: false
mybatis:
type-aliases-package: com.mybatis.demo.entities
\ No newline at end of file
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>授权</title>
</head>
<style>
html{
padding: 0px;
margin: 0px;
}
.title {
background-color: #E9686B;
height: 50px;
padding-left: 20%;
padding-right: 20%;
color: white;
line-height: 50px;
font-size: 18px;
}
.title-left{
float: right;
}
.title-right{
float: left;
}
.title-left a{
color: white;
}
.container{
clear: both;
text-align: center;
}
.btn {
width: 350px;
height: 35px;
line-height: 35px;
cursor: pointer;
margin-top: 20px;
border-radius: 3px;
background-color: #E9686B;
color: white;
border: none;
font-size: 15px;
}
</style>
<body style="margin: 0px">
<div class="title">
<div class="title-right">OAUTH 授权</div>
<div class="title-left">
<a href="#help">帮助</a>
</div>
</div>
<div class="container">
<h3 th:text="${clientId}+' 请求授权,该应用将获取你的用户名'"></h3>
授权后表明你已同意 <a href="#boot" style="color: #E9686B">OAUTH 服务协议</a>
<form method="post" action="/oauth/authorize">
<input type="hidden" name="user_oauth_approval" value="true">
<input type="hidden" name="_csrf" th:value="${_csrf.getToken()}"/>
<div th:each="item:${scopes}" >
<input type="checkbox" th:name="'scope.'+${item}" value="true" checked />
<span th:id="${item}" name="span"></span>
</div>
<button class="btn" type="submit"> 同意/授权</button>
</form>
</div>
<script th:inline="javascript">
window.onload=function(){
document.getElementsByName("span")[0].innerText=document.getElementsByName("span")[0].id;
}
</script>
</body>
</html>
\ No newline at end of file
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>登录</title>
</head>
<style>
.login-container {
margin: 50px;
width: 100%;
}
.form-container {
margin: 0px auto;
width: 50%;
text-align: center;
box-shadow: 1px 1px 10px #888888;
height: 300px;
padding: 5px;
}
input {
margin-top: 10px;
width: 350px;
height: 30px;
border-radius: 3px;
border: 1px #E9686B solid;
padding-left: 2px;
}
.btn {
width: 350px;
height: 35px;
line-height: 35px;
cursor: pointer;
margin-top: 20px;
border-radius: 3px;
background-color: #E9686B;
color: white;
border: none;
font-size: 15px;
}
.title{
margin-top: 5px;
font-size: 18px;
color: #E9686B;
}
</style>
<body>
<div class="login-container">
<div class="form-container">
<p class="title">用户登录</p>
<form name="loginForm" method="post" th:action="${loginProcessUrl}">
<input type="hidden" name="_csrf" th:value="${_csrf.getToken()}"/>
<input type="text" name="username" placeholder="用户名"/>
<br>
<input type="password" name="password" placeholder="密码"/>
<br>
<button type="submit" class="btn">&nbsp;&nbsp;</button>
</form>
<p style="color: red" th:if="${param.error}">用户名或密码错误</p>
</div>
</div>
</body>
</html>
......@@ -41,6 +41,16 @@
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-oauth2</artifactId>
</dependency>
<!--redis-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-thymeleaf</artifactId>
</dependency>
</dependencies>
<dependencyManagement>
......
......@@ -6,10 +6,11 @@ server:
security:
oauth2:
client:
access-token-uri: ${auth-server-url}/oauth/token
user-authorization-uri: ${auth-server-url}/oauth/authorize
client-id: client1
client-secret: 123456
scope: test
access-token-uri: ${auth-server-url}/oauth/token
user-authorization-uri: ${auth-server-url}/oauth/authorize
resource:
token-info-uri: ${auth-server-url}/oauth/check_token #检查令牌
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment