本文單純從簡單的技術實現來說,不涉及開放平臺的多維度的運營理念。前端
經過開放本身平臺產品服務的各類API接口,讓其餘第三方開發者在開發應用時根據需求直接調用,例如微信登陸、QQ登陸、微信支付、微博登陸、熱門等。
讓第三方應用經過開發平臺,使得自身海量數據資源獲得沉澱(變現)
目前國內主流的網站的的開放平臺,都是基於oauth2.0 協議進行作的開放平臺git
受權碼模式(authorization code)是功能最完整、流程最嚴密的受權模式。 它的特色就是經過客戶端的後臺服務器,與"服務提供商"的認證服務器進行互動,可以知足絕大多數開放平臺認證受權的需求。spring
<dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-oauth2</artifactId> </dependency> <dependency> <groupId>org.springframework.cloud</groupId> <artifactId>spring-cloud-starter-security</artifactId> </dependency>
經過內存模式,初始化一個支持受權碼模式的客戶端數據庫
@Configuration @AllArgsConstructor @EnableAuthorizationServer public class AuthorizationServerConfig extends AuthorizationServerConfigurerAdapter { @Override @SneakyThrows public void configure(ClientDetailsServiceConfigurer clients) { clients.inMemory() .withClient("pigx") // client_id .secret("pigx") // client_secret .authorizedGrantTypes("authorization_code") // 該client容許的受權類型 .scopes("app"); // 容許的受權範圍 } }
注意這裏是 /oauth/authorize 不是 /oauth/token 接口,只須要帶 client_id 便可。安全
localhost:9999/oauth/authorize?client_id=pigx&response_type=code&redirect_uri=https://pig4cloud.com
簡單的幾步就完成上圖微信或者其餘網站的受權流程,不過目前爲止 略顯簡陋服務器
@Primary @Order(90) @Configuration public class WebSecurityConfigurer extends WebSecurityConfigurerAdapter { @Override @SneakyThrows protected void configure(HttpSecurity http) { http .formLogin() .loginPage("/token/login") .loginProcessingUrl("/token/form") .and() .authorizeRequests() .anyRequest().authenticated(); } }
@Override public void configure(AuthorizationServerEndpointsConfigurer endpoints) { endpoints.userDetailsService(pigxUserDetailsService) } // 經過這步去加載數據的用戶名密碼 public interface UserDetailsService { UserDetails loadUserByUsername(String var1) throws UsernameNotFoundException; }
默認邏輯/oauth/confirm_access,讓他重定向到咱們本身的路徑,而後進行個性哈微信
@Override public void configure(AuthorizationServerEndpointsConfigurer endpoints) { endpoints .userDetailsService(pigxUserDetailsService) .pathMapping("/oauth/confirm_access", "/token/confirm_access") }
獲取上下文中的受權信息,傳給前端session
/** * 確認受權頁面 * * @param request * @param session * @param modelAndView * @return */ @GetMapping("/confirm_access") public ModelAndView confirm(HttpServletRequest request, HttpSession session, ModelAndView modelAndView) { Map<String, Object> scopeList = (Map<String, Object>) request.getAttribute("scopes"); modelAndView.addObject("scopeList", scopeList.keySet()); Object auth = session.getAttribute("authorizationRequest"); if (auth != null) { AuthorizationRequest authorizationRequest = (AuthorizationRequest) auth; ClientDetails clientDetails = clientDetailsService.loadClientByClientId(authorizationRequest.getClientId()); modelAndView.addObject("app", clientDetails.getAdditionalInformation()); modelAndView.addObject("user", SecurityUtils.getUser()); } modelAndView.setViewName("ftl/confirm"); return modelAndView; }