浏览代码

添加登录接口
企业注册添加域名

wangmh 8 年之前
父节点
当前提交
753638b99c
共有 25 个文件被更改,包括 1127 次插入29 次删除
  1. 8 0
      pom.xml
  2. 17 6
      sso-common/pom.xml
  3. 245 0
      sso-common/src/main/java/com/uas/sso/entity/UserAccount.java
  4. 5 0
      sso-server/pom.xml
  5. 20 0
      sso-server/src/main/java/com/uas/sso/controller/AppManageController.java
  6. 250 0
      sso-server/src/main/java/com/uas/sso/controller/LoginController.java
  7. 12 0
      sso-server/src/main/java/com/uas/sso/core/Const.java
  8. 15 0
      sso-server/src/main/java/com/uas/sso/dao/AppDao.java
  9. 73 0
      sso-server/src/main/java/com/uas/sso/dao/UserAccountDao.java
  10. 9 0
      sso-server/src/main/java/com/uas/sso/dao/UserDao.java
  11. 8 0
      sso-server/src/main/java/com/uas/sso/dao/UserspaceDao.java
  12. 17 17
      sso-server/src/main/java/com/uas/sso/entity/App.java
  13. 1 1
      sso-server/src/main/java/com/uas/sso/entity/RegisterLog.java
  14. 1 1
      sso-server/src/main/java/com/uas/sso/entity/UserLog.java
  15. 15 1
      sso-server/src/main/java/com/uas/sso/entity/Userspace.java
  16. 36 0
      sso-server/src/main/java/com/uas/sso/service/AppService.java
  17. 21 0
      sso-server/src/main/java/com/uas/sso/service/UserService.java
  18. 9 0
      sso-server/src/main/java/com/uas/sso/service/UserspaceService.java
  19. 37 0
      sso-server/src/main/java/com/uas/sso/service/impl/AppServiceImpl.java
  20. 71 0
      sso-server/src/main/java/com/uas/sso/service/impl/UserAccountService.java
  21. 51 0
      sso-server/src/main/java/com/uas/sso/service/impl/UserAccountServiceImpl.java
  22. 43 3
      sso-server/src/main/java/com/uas/sso/service/impl/UserServiceImpl.java
  23. 60 0
      sso-server/src/main/java/com/uas/sso/service/impl/UserspaceServiceImpl.java
  24. 34 0
      sso-server/src/main/java/com/uas/sso/util/AccountTypeUtils.java
  25. 69 0
      sso-server/src/main/java/com/uas/sso/util/ChineseUtils.java

+ 8 - 0
pom.xml

@@ -30,6 +30,8 @@
         <zookeeper.version>3.4.6</zookeeper.version>
         <zkclient.version>0.1</zkclient.version>
         <dfs.version>0.0.2</dfs.version>
+
+        <pinyin.version>2.5.1</pinyin.version>
     </properties>
 
     <dependencyManagement>
@@ -90,6 +92,12 @@
                 <artifactId>dfs-api</artifactId>
                 <version>${dfs.version}</version>
             </dependency>
+
+            <dependency>
+                <groupId>com.belerweb</groupId>
+                <artifactId>pinyin4j</artifactId>
+                <version>${pinyin.version}</version>
+            </dependency>
         </dependencies>
     </dependencyManagement>
 

+ 17 - 6
sso-common/pom.xml

@@ -22,18 +22,29 @@
             <artifactId>sso-core</artifactId>
             <version>0.0.1-SNAPSHOT</version>
         </dependency>
+
+        <!-- spring boot -->
         <dependency>
-            <groupId>org.springframework</groupId>
-            <artifactId>spring-beans</artifactId>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-actuator</artifactId>
         </dependency>
         <dependency>
-            <groupId>org.springframework</groupId>
-            <artifactId>spring-context</artifactId>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-data-jpa</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-web</artifactId>
         </dependency>
         <dependency>
-            <groupId>org.apache.tomcat.embed</groupId>
-            <artifactId>tomcat-embed-core</artifactId>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-security</artifactId>
         </dependency>
+        <dependency>
+            <groupId>org.springframework</groupId>
+            <artifactId>spring-tx</artifactId>
+        </dependency>
+
         <dependency>
             <groupId>net.sf.flexjson</groupId>
             <artifactId>flexjson</artifactId>

+ 245 - 0
sso-common/src/main/java/com/uas/sso/entity/UserAccount.java

@@ -0,0 +1,245 @@
+package com.uas.sso.entity;
+
+import javax.persistence.*;
+import java.io.Serializable;
+
+/**
+ * 用户账号,包括个人账号
+ *
+ * @author wangmh
+ * @date 2018/1/6
+ */
+@Entity
+@Table(name = "v$user$account")
+public class UserAccount implements Serializable {
+
+    /**
+     *
+     */
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * uu号
+     */
+    @Id
+    @Column(name = "useruu")
+    private Long userUU;
+
+    /**
+     * 会员名
+     */
+    @Column(name = "vip_name", nullable = false)
+    private String vipName;
+
+    /**
+     * 手机号
+     */
+    @Column(name = "mobile", unique = true, nullable = false)
+    private String mobile;
+
+    /**
+     * 手机号所属区域(continent or Hongkong)
+     */
+    @Column(name = "mobile_area")
+    private String mobileArea;
+
+    /**
+     * 手机号认证状态
+     */
+    @Column(name = "mobile_is_valid")
+    private Short mobileIsValid;
+
+    /**
+     * 用户密码
+     */
+    @Column(name = "_password", nullable = false)
+    private String password;
+
+    /**
+     * 用户erp密码
+     */
+    @Column(name = "erp_password")
+    private String erpPassword;
+
+    /**
+     * 盐值
+     */
+    @Column(name = "salt")
+    private String salt;
+
+    /**
+     * 用户邮箱
+     */
+    @Column(name = "user_email")
+    private String email;
+
+    /**
+     * 用户邮箱认证状态
+     */
+    @Column(name = "email_is_valid")
+    private Short emailIsValid;
+
+    /**
+     * 账户是否冻结(1、冻结)
+     */
+    @Column(name = "_lock")
+    private Integer lock;
+
+    /**
+     * 企业uu号
+     */
+    @Column(name = "spaceuu")
+    private Long spaceUU;
+
+    /**
+     * 企业名称
+     */
+    @Column(name = "space_name", unique = true)
+    private String spaceName;
+
+    /**
+     * 营业执照号
+     */
+    @Column(name = "business_code")
+    private String businessCode;
+
+    /**
+     * 企业域名
+     */
+    @Column(name = "domain")
+    private String spaceDomain;
+
+    /**
+     * 应用唯一标志
+     */
+    @Column(name = "app_uid")
+    private String appId;
+
+    public Long getUserUU() {
+        return userUU;
+    }
+
+    public void setUserUU(Long userUU) {
+        this.userUU = userUU;
+    }
+
+    public String getVipName() {
+        return vipName;
+    }
+
+    public void setVipName(String vipName) {
+        this.vipName = vipName;
+    }
+
+    public String getMobile() {
+        return mobile;
+    }
+
+    public void setMobile(String mobile) {
+        this.mobile = mobile;
+    }
+
+    public String getMobileArea() {
+        return mobileArea;
+    }
+
+    public void setMobileArea(String mobileArea) {
+        this.mobileArea = mobileArea;
+    }
+
+    public Short getMobileIsValid() {
+        return mobileIsValid;
+    }
+
+    public void setMobileIsValid(Short mobileIsValid) {
+        this.mobileIsValid = mobileIsValid;
+    }
+
+    public String getPassword() {
+        return password;
+    }
+
+    public void setPassword(String password) {
+        this.password = password;
+    }
+
+    public String getErpPassword() {
+        return erpPassword;
+    }
+
+    public void setErpPassword(String erpPassword) {
+        this.erpPassword = erpPassword;
+    }
+
+    public String getSalt() {
+        return salt;
+    }
+
+    public void setSalt(String salt) {
+        this.salt = salt;
+    }
+
+    public String getEmail() {
+        return email;
+    }
+
+    public void setEmail(String email) {
+        this.email = email;
+    }
+
+    public Short getEmailIsValid() {
+        return emailIsValid;
+    }
+
+    public void setEmailIsValid(Short emailIsValid) {
+        this.emailIsValid = emailIsValid;
+    }
+
+    public Integer getLock() {
+        return lock;
+    }
+
+    public void setLock(Integer lock) {
+        this.lock = lock;
+    }
+
+    public Long getSpaceUU() {
+        return spaceUU;
+    }
+
+    public void setSpaceUU(Long spaceUU) {
+        this.spaceUU = spaceUU;
+    }
+
+    public String getSpaceName() {
+        return spaceName;
+    }
+
+    public void setSpaceName(String spaceName) {
+        this.spaceName = spaceName;
+    }
+
+    public String getBusinessCode() {
+        return businessCode;
+    }
+
+    public void setBusinessCode(String businessCode) {
+        this.businessCode = businessCode;
+    }
+
+    public String getSpaceDomain() {
+        return spaceDomain;
+    }
+
+    public void setSpaceDomain(String spaceDomain) {
+        this.spaceDomain = spaceDomain;
+    }
+
+    public String getAppId() {
+        return appId;
+    }
+
+    public void setAppId(String appId) {
+        this.appId = appId;
+    }
+}

+ 5 - 0
sso-server/pom.xml

@@ -108,6 +108,11 @@
 			<groupId>com.uas.dfs</groupId>
 			<artifactId>dfs-api</artifactId>
 		</dependency>
+
+		<dependency>
+			<groupId>com.belerweb</groupId>
+			<artifactId>pinyin4j</artifactId>
+		</dependency>
 	</dependencies>
 
 	<build>

+ 20 - 0
sso-server/src/main/java/com/uas/sso/controller/AppManageController.java

@@ -0,0 +1,20 @@
+package com.uas.sso.controller;
+
+import com.uas.sso.entity.App;
+import org.springframework.stereotype.Controller;
+
+/**
+ * Created by uas on 2018/1/5.
+ */
+@Controller
+public class AppManageController extends BaseController {
+
+    /**
+     * 保存应用信息
+     *
+     * @param app
+     */
+    public void save(App app) {
+
+    }
+}

+ 250 - 0
sso-server/src/main/java/com/uas/sso/controller/LoginController.java

@@ -0,0 +1,250 @@
+package com.uas.sso.controller;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONObject;
+import com.uas.sso.SSOConfig;
+import com.uas.sso.SSOHelper;
+import com.uas.sso.SSOToken;
+import com.uas.sso.common.util.HttpUtil;
+import com.uas.sso.core.Const;
+import com.uas.sso.entity.App;
+import com.uas.sso.entity.UserAccount;
+import com.uas.sso.service.AppService;
+import com.uas.sso.service.UserService;
+import com.uas.sso.service.impl.UserAccountService;
+import com.uas.sso.util.AccountTypeUtils;
+import com.uas.sso.web.waf.request.WafRequestWrapper;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.ui.ModelMap;
+import org.springframework.util.CollectionUtils;
+import org.springframework.util.StringUtils;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.ResponseBody;
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.*;
+
+/**
+ * 登录controller
+ *
+ * @author wangmh
+ * @date 2018/1/5
+ */
+@RequestMapping("/sso/login")
+@RestController
+public class LoginController extends BaseController {
+
+    @Autowired
+    private AppService appService;
+
+    @Autowired
+    private UserService userService;
+
+    @Autowired
+    private UserAccountService userAccountService;
+
+    @RequestMapping(method = RequestMethod.POST)
+    @ResponseBody
+    public ModelMap login() {
+        // 获取登录信息
+        WafRequestWrapper wr = new WafRequestWrapper(request);
+        String appId = wr.getParameter("appId");
+        String spaceUU = wr.getParameter("spaceUU");
+        String username = StringUtils.trimAllWhitespace(wr.getParameter("username"));
+        String password = wr.getParameter("password");
+        String returnUrl = wr.getParameter("returnUrl");
+        String baseUrl = wr.getParameter("baseUrl");
+
+        // 校验空参数
+        if (StringUtils.isEmpty(username)) {
+            return error("用户名不能为空");
+        }
+        if (StringUtils.isEmpty(password)) {
+            return error("密码不能为空");
+        }
+
+        // 设置baseUrl
+        if (!StringUtils.isEmpty(baseUrl)) {
+            request.getSession().setAttribute("baseUrl", baseUrl);
+        }
+
+        // 校验appId,appId为空的话默认为sso
+        appId = StringUtils.isEmpty(appId) ? "sso" : appId;
+        App app = appService.findOne(appId);
+        if (app == null) {
+            return error("应用id不存在");
+        }
+
+        // 登录
+        App controlApp = StringUtils.isEmpty(app.getUserControl()) ? app : appService.findOne(app.getUserControl());
+        boolean personalEnable = Const.YES == controlApp.getPersonalEnable();
+
+        if (StringUtils.isEmpty(spaceUU)) {
+            /*企业uu号为空,让用户选择企业*/
+            // 找到用户账号信息
+            List<UserAccount> userAccounts = getUserAccountByUserName(controlApp.getUid(), username);
+
+            // 应用不允许个人账号,并且账号未绑定企业
+            if (!personalEnable && CollectionUtils.isEmpty(userAccounts)) {
+                return error("用户名或密码错误");
+            }
+
+            // 应用允许个人账号,并且账号未绑定企业,或者只绑定了一个企业,直接登录
+            if (userAccounts.size() == 1) {
+                return loginByUser(userAccounts.get(0), password, returnUrl);
+            }
+
+            // 由于老账户存在多个账号绑定一个邮箱的情况,把密码不符合的企业去除
+            Iterator<UserAccount> iterator = userAccounts.iterator();
+            while (iterator.hasNext()) {
+                UserAccount userAccount = iterator.next();
+                String encryPwd = userService.getEncryPassword(Const.ENCRY_FORMAT, password, userAccount.getSalt());
+                if (!encryPwd.equals(userAccount.getPassword())) {
+                    iterator.remove();
+                }
+            }
+
+            // 返回企业id和名称
+            return success(getSpaceSelect(userAccounts, personalEnable));
+        } else if (spaceUU.equals(Const.SPACEUU_PERSONAL)) {
+            // 使用个人账号登录
+            UserAccount userAccount = getUserAccountByUserName(controlApp.getUid(), username, null);
+            return loginByUser(userAccount, password, returnUrl);
+        } else {
+            // 带企业登录
+            UserAccount userAccount = getUserAccountByUserName(controlApp.getUid(), username, spaceUU);
+            return loginByUser(userAccount, password, returnUrl);
+        }
+    }
+
+    private List<UserAccount> getUserAccountByUserName(String appId, String username) {
+        String type = AccountTypeUtils.getAccountType(username);
+        if (AccountTypeUtils.MOBILE.equals(type)) {
+            // 手机号登录
+            return userAccountService.findByMobile(appId, username);
+        }
+        if (AccountTypeUtils.EMAIL.equals(type)) {
+            // 邮箱登录
+            return userAccountService.findByEmail(appId, username);
+        }
+        if (AccountTypeUtils.UU_NUMBER.equals(type)) {
+            // uu号登录
+            return userAccountService.findOneByUserUU(appId, Long.valueOf(username));
+        }
+
+        // 其余情况
+        return null;
+    }
+
+    private UserAccount getUserAccountByUserName(String appId, String username, String spaceUU) {
+        String type = AccountTypeUtils.getAccountType(username);
+        if (AccountTypeUtils.MOBILE.equals(type)) {
+            // 手机号登录
+            return userAccountService.findOneByMobile(appId, username, spaceUU);
+        }
+        if (AccountTypeUtils.EMAIL.equals(type)) {
+            // 邮箱登录
+            return userAccountService.findOneByEmail(appId, username, spaceUU);
+        }
+        if (AccountTypeUtils.UU_NUMBER.equals(type)) {
+            // uu号登录
+            return userAccountService.findOneByUserUU(appId, Long.valueOf(username), spaceUU);
+        }
+
+        // 其余情况
+        return null;
+    }
+
+    private ModelMap loginByUser(UserAccount userAccount, String password, String returnUrl) {
+        if (StringUtils.isEmpty((userAccount.getPassword()))) {
+            // 使用错误码100来判断
+            return error("100", "未设置密码");
+        } else {
+            // 校验密码
+            String encryPwd = userService.getEncryPassword(Const.ENCRY_FORMAT, password, userAccount.getSalt());
+            if (!encryPwd.equals(userAccount.getPassword())) {
+                return error("您输入的账号或密码有误");
+            }
+
+            // 登录
+            /*
+             * 设置登录 Cookie 最后一个参数 true 时添加 cookie 同时销毁当前 JSESSIONID
+             * 创建信任的 JSESSIONID
+             */
+            SSOToken st = new SSOToken(request, userAccount.getMobile());
+            st.setData(JSON.toJSONString(userAccount));
+            SSOHelper.setSSOCookie(request, response, st, true);
+
+            // 通知各个应用用户已经登录
+            ModelMap data = new ModelMap();
+            data = addOtherAppRequestData(userAccount, data, request.getSession().getAttribute("baseUrl"), true);
+            data.put("returnUrl", HttpUtil.decodeURL(returnUrl));
+            return success(data);
+        }
+    }
+
+    private ModelMap addOtherAppRequestData(UserAccount userAccount, ModelMap data, Object loginUrl,
+                                            boolean isLoginAll) {
+        // 需要通知的应用数量
+        int count = 0;
+        List<App> apps = appService.findAll();
+        List<String> loginUrls = new ArrayList<>();
+        boolean hasLoginUrl = false;
+        if (isLoginAll) {
+            for (App app : apps) {
+                if (StringUtils.isEmpty(app.getLoginUrl())) {
+                    continue;
+                }
+                if (app.getLoginUrl().equals(loginUrl)) {
+                    hasLoginUrl = true;
+                }
+                loginUrls.add(app.getLoginUrl());
+                count++;
+            }
+        }
+
+        // 添加baseUrl
+        if (!hasLoginUrl && !StringUtils.isEmpty(loginUrl)) {
+            loginUrls.add(loginUrl.toString());
+            count++;
+        }
+
+        data.put("count", count);
+        data.put("loginUrls", loginUrls);
+
+        // 添加传递数据
+        JSONObject jsonObject = JSON.parseObject(JSON.toJSONString(userAccount));
+        Integer maxage = (Integer) request.getAttribute(SSOConfig.SSO_COOKIE_MAXAGE);
+        jsonObject.put("maxage", maxage);
+        data.put("data", jsonObject);
+        return data;
+    }
+
+    /**
+     * 获取选择企业信息(id:企业uu号,name:名称)
+     *
+     * @param userAccounts 用户账户信息
+     * @param personalEnable 该应用是否允许个人账户
+     * @return
+     */
+    private ModelMap getSpaceSelect(List<UserAccount> userAccounts, boolean personalEnable) {
+        List<Map<String, Object>> spaces = new ArrayList<Map<String, Object>>();
+        Map<String, Object> space = null;
+        // 设置带企业账号
+        for (UserAccount userAccount : userAccounts) {
+            space = new HashMap<String, Object>(2);
+            space.put("id", userAccount.getSpaceUU());
+            space.put("name", userAccount.getSpaceName());
+        }
+
+        // 设置个人账号
+        if (personalEnable) {
+            space = new HashMap<String, Object>(2);
+            space.put("id", Const.SPACEUU_PERSONAL);
+            space.put("name", String.format("%s(个人)", userAccounts.get(0).getVipName()));
+        }
+        return new ModelMap("spaces", spaces);
+    }
+
+}

+ 12 - 0
sso-server/src/main/java/com/uas/sso/core/Const.java

@@ -8,6 +8,11 @@ package com.uas.sso.core;
  */
 public class Const {
 
+    /**
+     * 邮箱正则
+     */
+    public static final String REGEXP_EMAIL = "^[a-z0-9]+([._\\\\-]*[a-z0-9])*@([a-z0-9]+[-a-z0-9]*[a-z0-9]+.){1,63}[a-z0-9]+$";
+
     /**
      * 中国大陆手机号正则
      */
@@ -18,6 +23,11 @@ public class Const {
      */
     public static final String REGEXP_MOBILE_HONGKONG = "[0-9]{8}";
 
+    /**
+     * 用户uu号正则
+     */
+    public static String REGEXP_USERUU_NUMBER = "^[0-9]{10}$";
+
     /**
      * 中国大陆
      */
@@ -50,4 +60,6 @@ public class Const {
     public static final String SUCCESS = "success";
 
     public static final String ERROR = "error";
+
+    public static Long SPACEUU_PERSONAL = 1L;
 }

+ 15 - 0
sso-server/src/main/java/com/uas/sso/dao/AppDao.java

@@ -0,0 +1,15 @@
+package com.uas.sso.dao;
+
+import com.uas.sso.entity.App;
+import org.springframework.data.jpa.repository.JpaRepository;
+import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
+
+/**
+ * 应用dao, 应用主键为uid
+ *
+ * @author wangmh
+ * @date 2018/1/5
+ */
+public interface AppDao extends JpaRepository<App, String>, JpaSpecificationExecutor<App> {
+
+}

+ 73 - 0
sso-server/src/main/java/com/uas/sso/dao/UserAccountDao.java

@@ -0,0 +1,73 @@
+package com.uas.sso.dao;
+
+import com.uas.sso.entity.UserAccount;
+import org.springframework.data.jpa.repository.JpaRepository;
+import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
+
+import java.util.List;
+
+/**
+ * 用户账号dao
+ *
+ * @author wangmh
+ * @date 2018/1/8
+ */
+public interface UserAccountDao extends JpaRepository<UserAccount, Long>, JpaSpecificationExecutor<UserAccount> {
+
+    /**
+     * 根据手机号和企业uu号查找用户账号
+     *
+     * @param appId 登录的应用
+     * @param mobile 手机号
+     * @param spaceUU 企业uu号
+     * @return 用户账户信息
+     */
+    UserAccount findByAppIdAndMobileAndSpaceUU(String appId, String mobile, String spaceUU);
+
+    /**
+     * 根据邮箱和企业uu号查找用户账号
+     *
+     * @param appId 登录的应用
+     * @param email 邮箱
+     * @param spaceUU 企业uu号
+     * @return 用户账户信息
+     */
+    UserAccount findByAppIdAndEmailAndSpaceUU(String appId, String email, String spaceUU);
+
+    /**
+     * 根据用户uu号和企业uu号查找用户账号
+     *
+     * @param appId 登录的应用
+     * @param userUU 用户uu号
+     * @param spaceUU 企业uu号
+     * @return 用户账户信息
+     */
+    UserAccount findByAppIdAndUserUUAndSpaceUU(String appId, Long userUU, String spaceUU);
+
+    /**
+     * 根据手机号和查找用户账号(包括个人账号)
+     *
+     * @param appId 登录应用
+     * @param mobile 手机号
+     * @return 用户账户信息
+     */
+    List<UserAccount> findByAppIdAndMobile(String appId, String mobile);
+
+    /**
+     * 根据邮箱查找用户账号(包括个人账号)
+     *
+     * @param appId 登录应用
+     * @param email 邮箱
+     * @return 用户账户信息
+     */
+    List<UserAccount> findByAppIdAndEmail(String appId, String email);
+
+    /**
+     * 根据用户uu号查找用户账号(包括个人账号)
+     *
+     * @param appId 登录应用
+     * @param userUU 用户uu号
+     * @return 用户账户信息
+     */
+    List<UserAccount> findByAppIdAndUserUU(String appId, Long userUU);
+}

+ 9 - 0
sso-server/src/main/java/com/uas/sso/dao/UserDao.java

@@ -54,4 +54,13 @@ public interface UserDao extends JpaRepository<User, Long>, JpaSpecificationExec
      */
     @Query("select max(u.userUU) from User u")
     Long findMaxUU();
+
+    /**
+     * 根据邮箱查找用户信息
+     *
+     * @param email 邮箱
+     * @param emailIsValid 邮箱认证状态
+     * @return
+     */
+    List<User> findByEmailAndEmailIsValid(String email, Short emailIsValid);
 }

+ 8 - 0
sso-server/src/main/java/com/uas/sso/dao/UserspaceDao.java

@@ -35,4 +35,12 @@ public interface UserspaceDao extends JpaRepository<Userspace, Long>, JpaSpecifi
      */
     @Query("select max(us.spaceUU) from Userspace us")
     Long findMaxUU();
+
+    /**
+     * 根据域名查找企业
+     *
+     * @param domain 域名
+     * @return
+     */
+    Userspace findByDomain(String domain);
 }

+ 17 - 17
sso-server/src/main/java/com/uas/sso/entity/App.java

@@ -22,87 +22,87 @@ public class App implements Serializable {
      * 应用唯一标志
      */
     @Id
-    @Column(name = "_uid")
+    @Column(name = "uid_")
     @GeneratedValue
     private String uid;
 
     /**
      * 应用描述(名称)
      */
-    @Column(name = "description")
+    @Column(name = "description", nullable = false)
     private String description;
 
     /**
      * 级联应用,为空时为独立应用
      */
-    @Column(name = "userControl")
+    @Column(name = "user_control")
     private String userControl;
 
     /**
      * 应用首页Url
      */
-    @Column(name = "homePage")
+    @Column(name = "home_page")
     private String homePage;
 
     /**
      * 企业信息回调接口(用于应用同步)
      */
-    @Column(name = "backSpaceUrl")
+    @Column(name = "back_space_url")
     private String backSpaceUrl;
 
     /**
      * 用户信息回调接口(用于应用同步)
      */
-    @Column(name = "backUserUrl")
+    @Column(name = "back_user_url")
     private String backUserUrl;
 
     /**
      * 合作伙伴回调接口(用于应用同步)
      */
-    @Column(name = "backPartnerUrl")
+    @Column(name = "back_partner_url")
     private String backPartnerUrl;
 
     /**
      * 更换企业管理员回调接口(用于同步)
      */
-    @Column(name = "backChangeAdminUrl")
+    @Column(name = "back_change_admin_url")
     private String backChangeAdminUrl;
 
     /**
      * 登录通知接口
      */
-    @Column(name = "loginUrl")
+    @Column(name = "login_url")
     private String loginUrl;
 
     /**
      * 登出通知接口
      */
-    @Column(name = "logoutUrl")
+    @Column(name = "logout_url")
     private String logoutUrl;
 
     /**
      * 公钥,用于跨域认证
      */
-    @Column(name = "publicKey")
+    @Column(name = "public_key")
     private String publicKey;
 
     /**
      * 绑定企业数
      */
-    @Column(name = "usCount")
+    @Column(name = "us_count")
     private String usCount;
 
     /**
      * 是否默认开通
      */
-    @Column(name = "defaultUse")
+    @Column(name = "default_use")
     private String defaultUse;
 
     /**
      * 是否支持个人账号
      */
-    @Column(name = "personalEnable")
-    private String personalEnable;
+    @Column(name = "personal_enable", nullable = false)
+    private int personalEnable;
 
     public String getUid() {
         return uid;
@@ -208,11 +208,11 @@ public class App implements Serializable {
         this.defaultUse = defaultUse;
     }
 
-    public String getPersonalEnable() {
+    public int getPersonalEnable() {
         return personalEnable;
     }
 
-    public void setPersonalEnable(String personalEnable) {
+    public void setPersonalEnable(int personalEnable) {
         this.personalEnable = personalEnable;
     }
 }

+ 1 - 1
sso-server/src/main/java/com/uas/sso/entity/RegisterLog.java

@@ -12,7 +12,7 @@ import com.alibaba.fastjson.JSON;
 import javax.persistence.*;
 
 @Entity
-@Table(name = "sso$register$log")
+@Table(name = "sso$log$register")
 public class RegisterLog extends BaseLog {
 
     /**

+ 1 - 1
sso-server/src/main/java/com/uas/sso/entity/UserLog.java

@@ -13,7 +13,7 @@ import java.sql.Timestamp;
  * @date 2018/1/2
  */
 @Entity
-@Table(name = "sso$user$log")
+@Table(name = "sso$log$user")
 public class UserLog extends BaseLog implements Serializable {
 
     /**

+ 15 - 1
sso-server/src/main/java/com/uas/sso/entity/Userspace.java

@@ -29,7 +29,7 @@ public class Userspace implements Serializable {
     /**
      * 企业名称
      */
-    @Column(name = "space_name", unique = true)
+    @Column(name = "space_name", unique = true, nullable = false)
     private String spaceName;
 
     /**
@@ -147,6 +147,12 @@ public class Userspace implements Serializable {
     @Column(name = "bank")
     private String bank;
 
+    /**
+     * 企业域名
+     */
+    @Column(name = "domain")
+    private String domain;
+
     public Userspace() {
     }
 
@@ -317,4 +323,12 @@ public class Userspace implements Serializable {
     public void setBank(String bank) {
         this.bank = bank;
     }
+
+    public String getDomain() {
+        return domain;
+    }
+
+    public void setDomain(String domain) {
+        this.domain = domain;
+    }
 }

+ 36 - 0
sso-server/src/main/java/com/uas/sso/service/AppService.java

@@ -0,0 +1,36 @@
+package com.uas.sso.service;
+
+import com.uas.sso.entity.App;
+
+import java.util.List;
+
+/**
+ * app service
+ *
+ * @author wangmh
+ * @date 2018/1/5
+ */
+public interface AppService {
+
+    /**
+     * 保存 APP信息
+     *
+     * @param app 应用
+     * @return 保存后的app
+     */
+    App save(App app);
+
+    /**
+     * 根据主键查找应用
+     *
+     * @param uid 应用唯一标志
+     * @return 应用信息
+     */
+    App findOne(String uid);
+
+    /**
+     * 查询所有应用
+     * @return
+     */
+    List<App> findAll();
+}

+ 21 - 0
sso-server/src/main/java/com/uas/sso/service/UserService.java

@@ -1,6 +1,9 @@
 package com.uas.sso.service;
 
 import com.uas.sso.entity.User;
+import com.uas.sso.entity.UserAccount;
+
+import java.util.List;
 
 /**
  * 用户信息service
@@ -71,4 +74,22 @@ public interface UserService {
      * @param isEncry 密码是否加密
      */
     void checkPassword(Long userUU, String password, boolean isEncry);
+
+    /**
+     * 根据手机号校验优软云密码,不能校验erp的密码
+     *
+     * @param mobile 登录的手机号
+     * @param password 密码
+     * @param isEncry 密码是否加密
+     */
+    void checkPasswordByMobile(String mobile, String password, boolean isEncry);
+
+    /**
+     * 根据邮箱校验优软云密码,不能校验erp的密码
+     *
+     * @param email 登录邮箱
+     * @param password 密码
+     * @param isEncry 密码是否加密
+     */
+    void checkPasswordByEmail(String email, String password, boolean isEncry);
 }

+ 9 - 0
sso-server/src/main/java/com/uas/sso/service/UserspaceService.java

@@ -27,4 +27,13 @@ public interface UserspaceService {
      * @param businessCode 企业营业执照号
      */
     void checkBusinessCode(String businessCode);
+
+    /**
+     * 查找企业详细信息
+     *
+     * @param domain
+     *            域名
+     * @return
+     */
+    Userspace findByDomain(String domain);
 }

+ 37 - 0
sso-server/src/main/java/com/uas/sso/service/impl/AppServiceImpl.java

@@ -0,0 +1,37 @@
+package com.uas.sso.service.impl;
+
+import com.uas.sso.dao.AppDao;
+import com.uas.sso.entity.App;
+import com.uas.sso.service.AppService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+/**
+ * app service实现
+ *
+ * @author wangmh
+ * @date 2018/1/5
+ */
+@Service
+public class AppServiceImpl implements AppService {
+
+    @Autowired
+    private AppDao appDao;
+
+    @Override
+    public App save(App app) {
+        return appDao.save(app);
+    }
+
+    @Override
+    public App findOne(String uid) {
+        return appDao.findOne(uid);
+    }
+
+    @Override
+    public List<App> findAll() {
+        return appDao.findAll();
+    }
+}

+ 71 - 0
sso-server/src/main/java/com/uas/sso/service/impl/UserAccountService.java

@@ -0,0 +1,71 @@
+package com.uas.sso.service.impl;
+
+import com.uas.sso.entity.UserAccount;
+
+import java.util.List;
+
+/**
+ * 用户账号service
+ *
+ * @author wangmh
+ * @date 2018/1/8
+ */
+public interface UserAccountService {
+
+    /**
+     * 根据手机号查找用户账号
+     *
+     * @param appId 应用id
+     * @param mobile 手机号
+     * @param spaceUU 企业uu号
+     * @return
+     */
+    UserAccount findOneByMobile(String appId, String mobile, String spaceUU);
+
+    /**
+     * 根据邮箱查找用户账号
+     *
+     * @param appId 应用id
+     * @param email 邮箱
+     * @param spaceUU 企业uu号
+     * @return
+     */
+    UserAccount findOneByEmail(String appId, String email, String spaceUU);
+
+    /**
+     * 根据uu号查找用户账号
+     *
+     * @param appId
+     * @param userUU
+     * @param spaceUU
+     * @return
+     */
+    UserAccount findOneByUserUU(String appId, Long userUU, String spaceUU);
+
+    /**
+     * 根据手机号和应用找到用户账号信息
+     *
+     * @param appId 应用id
+     * @param mobile 手机号
+     * @return
+     */
+    List<UserAccount> findByMobile(String appId, String mobile);
+
+    /**
+     * 根据邮箱和应用找到用户账号信息
+     *
+     * @param appId 应用id
+     * @param email 邮箱
+     * @return
+     */
+    List<UserAccount> findByEmail(String appId, String email);
+
+    /**
+     * 根据用户uu号和应用找到用户账号信息
+     *
+     * @param appId 应用id
+     * @param userUU 用户uu号
+     * @return
+     */
+    List<UserAccount> findOneByUserUU(String appId, Long userUU);
+}

+ 51 - 0
sso-server/src/main/java/com/uas/sso/service/impl/UserAccountServiceImpl.java

@@ -0,0 +1,51 @@
+package com.uas.sso.service.impl;
+
+import com.uas.sso.dao.UserAccountDao;
+import com.uas.sso.entity.UserAccount;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+/**
+ * 用户账户service实现类
+ *
+ * @author wangmh
+ * @date 2018/1/8
+ */
+@Service
+public class UserAccountServiceImpl implements UserAccountService {
+
+    @Autowired
+    private UserAccountDao userAccountDao;
+
+    @Override
+    public UserAccount findOneByMobile(String appId, String mobile, String spaceUU) {
+        return userAccountDao.findByAppIdAndMobileAndSpaceUU(appId, mobile, spaceUU);
+    }
+
+    @Override
+    public UserAccount findOneByEmail(String appId, String email, String spaceUU) {
+        return userAccountDao.findByAppIdAndEmailAndSpaceUU(appId, email, spaceUU);
+    }
+
+    @Override
+    public UserAccount findOneByUserUU(String appId, Long userUU, String spaceUU) {
+        return userAccountDao.findByAppIdAndUserUUAndSpaceUU(appId, userUU, spaceUU);
+    }
+
+    @Override
+    public List<UserAccount> findByMobile(String appId, String mobile) {
+        return userAccountDao.findByAppIdAndMobile(appId, mobile);
+    }
+
+    @Override
+    public List<UserAccount> findByEmail(String appId, String email) {
+        return userAccountDao.findByAppIdAndEmail(appId, email);
+    }
+
+    @Override
+    public List<UserAccount> findOneByUserUU(String appId, Long userUU) {
+        return userAccountDao.findByAppIdAndUserUU(appId, userUU);
+    }
+}

+ 43 - 3
sso-server/src/main/java/com/uas/sso/service/impl/UserServiceImpl.java

@@ -12,11 +12,13 @@ import com.uas.sso.logging.UserBufferedLogger;
 import com.uas.sso.service.UserService;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
+import org.springframework.util.CollectionUtils;
 import org.springframework.util.StringUtils;
 
 import com.uas.sso.exception.AccountException;
 
 import java.sql.Timestamp;
+import java.util.List;
 
 /**
  * 用户service实现类
@@ -105,9 +107,48 @@ public class UserServiceImpl implements UserService {
         // 根据用户uu号找到旧数据
         User oldUser = userDao.findByUserUU(userUU);
         if (oldUser == null) {
-            throw new VisibleError("该用户不存在");
+            throw new VisibleError("用户名或密码错误");
         }
 
+        // 校验密码
+        checkPassword(oldUser, password, isEncry);
+
+    }
+
+    @Override
+    public void checkPasswordByMobile(String mobile, String password, boolean isEncry) {
+        // 找到用户
+        User oldUser = userDao.findByMobile(mobile);
+        if (oldUser == null) {
+            throw new VisibleError("用户名或密码错误");
+        }
+
+        // 校验密码
+        checkPassword(oldUser, password, isEncry);
+    }
+
+    @Override
+    public void checkPasswordByEmail(String email, String password, boolean isEncry) {
+        // 找到用户
+        List<User> oldUsers = userDao.findByEmailAndEmailIsValid(email, (short) Status.AUTHENTICATED.getCode());
+        if (CollectionUtils.isEmpty(oldUsers)) {
+            throw new VisibleError("该邮箱未认证,请使用手机号登录");
+        }
+
+        // 校验密码
+        for (User oldUser : oldUsers) {
+            checkPassword(oldUser, password, isEncry);
+        }
+    }
+
+    /**
+     * 校验用户密码
+     *
+     * @param oldUser 用户信息
+     * @param password 需要校验的密码
+     * @param isEncry 需校验的密码是否被加密
+     */
+    private void checkPassword(User oldUser, String password, boolean isEncry) {
         // 密码未加密,转换成加密后的密码
         String encryPassword = password;
         if (!isEncry) {
@@ -115,9 +156,8 @@ public class UserServiceImpl implements UserService {
         }
 
         // 校验密码
-        if (!encryPassword.equals(password)) {
+        if (!encryPassword.equals(oldUser.getPassword())) {
             throw new VisibleError("密码不一致");
         }
-
     }
 }

+ 60 - 0
sso-server/src/main/java/com/uas/sso/service/impl/UserspaceServiceImpl.java

@@ -4,8 +4,11 @@ import com.uas.sso.dao.UserspaceDao;
 import com.uas.sso.entity.Userspace;
 import com.uas.sso.exception.VisibleError;
 import com.uas.sso.service.UserspaceService;
+import com.uas.sso.util.ChineseUtils;
+import com.uas.sso.util.StringUtil;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
+import org.springframework.util.StringUtils;
 
 /**
  * 企业信息service层
@@ -19,6 +22,11 @@ public class UserspaceServiceImpl implements UserspaceService {
     @Autowired
     private UserspaceDao userspaceDao;
 
+    /**
+     * 企业初始uu号
+     */
+    public static final Long SPACE_INIT_UU = 10000000L;
+
     @Override
     public void register(Userspace userspace) {
         // 校验企业名是否重复
@@ -27,10 +35,57 @@ public class UserspaceServiceImpl implements UserspaceService {
         // 校验营业执照号是否重复
         checkBusinessCode(userspace.getBusinessCode());
 
+        // 设置域名
+       if (StringUtils.isEmpty(userspace.getDomain())) {
+           generateDefaultDomain(userspace);
+       }
+
+        // 设置uu号
+        Long maxUU = userspaceDao.findMaxUU();
+        userspace.setSpaceUU(StringUtils.isEmpty(maxUU) ? SPACE_INIT_UU : (maxUU + 1));
+
         // 注册企业
         userspaceDao.save(userspace);
     }
 
+    /**
+     * 生成默认域名
+     *
+     * @return
+     */
+    private String generateDefaultDomain(Userspace userspace) {
+        String domain = null;
+        Userspace oldOne = null;
+        /// 代码复制,以后可能用到这个
+//        if (!StringUtils.isEmpty(userspace.getUrl())) {
+//            Pattern p = Pattern.compile("http(s)*://(.+\\.)*(.+)\\..+", Pattern.CASE_INSENSITIVE);
+//            Matcher m = p.matcher(userspace.getUrl());
+//            if (m.find()) {
+//                domain = m.group(3);
+//                if ("1688".equals(domain) || "taobao".equals(domain) || "qq".equals(domain) || "baidu".equals(domain)) {
+//                    domain = m.group(2);
+//                }
+//            }
+//        }
+        if (domain == null) {
+            domain = StringUtil.substr(ChineseUtils.converterToFirstSpell(StringUtils.trimAllWhitespace(userspace.getSpaceName())), 0, 16);
+        } else {
+            oldOne = findByDomain(domain);
+            if (oldOne != null) {
+                domain = StringUtil.substr(ChineseUtils.converterToFirstSpell(StringUtils.trimAllWhitespace(userspace.getSpaceName())), 0, 16);
+            }
+        }
+        oldOne = findByDomain(domain);
+        if (oldOne != null) {
+            domain = StringUtil.substr(ChineseUtils.converterToSpell(StringUtils.trimAllWhitespace(userspace.getSpaceName())), 0, 16);
+            oldOne = findByDomain(domain);
+            if (oldOne != null) {
+                domain = null;
+            }
+        }
+        return domain;
+    }
+
     @Override
     public void checkSpaceName(String spaceName) {
         Userspace userspace = userspaceDao.findBySpaceName(spaceName);
@@ -46,4 +101,9 @@ public class UserspaceServiceImpl implements UserspaceService {
             throw new VisibleError("该企业营业执照已被注册,请确认");
         }
     }
+
+    @Override
+    public Userspace findByDomain(String domain) {
+        return userspaceDao.findByDomain(domain);
+    }
 }

+ 34 - 0
sso-server/src/main/java/com/uas/sso/util/AccountTypeUtils.java

@@ -0,0 +1,34 @@
+package com.uas.sso.util;
+
+import com.uas.sso.core.Const;
+
+/**
+ * 账户类型工具类
+ *
+ * @author wangmh
+ * @date 2018/1/8
+ */
+public class AccountTypeUtils {
+
+    public final static String MOBILE = "mobile";
+
+    public final static String EMAIL = "email";
+
+    public final static String UU_NUMBER = "uuNumber";
+
+    public static String getAccountType(String username) {
+        if (username.matches(Const.REGEXP_MOBILE_CONTINENT) || username.matches(Const.REGEXP_MOBILE_HONGKONG)) {
+            // 使用的是手机号
+            return MOBILE;
+        }
+        if (username.matches(Const.REGEXP_EMAIL)){
+            // 使用的是邮箱
+            return EMAIL;
+        }
+        if (username.matches(Const.REGEXP_USERUU_NUMBER)) {
+            return UU_NUMBER;
+        }
+        // 其余情况
+        return null;
+    }
+}

+ 69 - 0
sso-server/src/main/java/com/uas/sso/util/ChineseUtils.java

@@ -0,0 +1,69 @@
+package com.uas.sso.util;
+
+import net.sourceforge.pinyin4j.PinyinHelper;
+import net.sourceforge.pinyin4j.format.HanyuPinyinCaseType;
+import net.sourceforge.pinyin4j.format.HanyuPinyinOutputFormat;
+import net.sourceforge.pinyin4j.format.HanyuPinyinToneType;
+import net.sourceforge.pinyin4j.format.exception.BadHanyuPinyinOutputFormatCombination;
+
+public class ChineseUtils {
+
+	/**
+	 * 汉字转换位汉语拼音首字母,英文字符不变
+	 * 
+	 * @param chinese
+	 *            汉字
+	 * @return 拼音
+	 */
+	public static String converterToFirstSpell(String chinese) {
+		String pinyinName = "";
+		char[] nameChar = chinese.toCharArray();
+		HanyuPinyinOutputFormat defaultFormat = new HanyuPinyinOutputFormat();
+		defaultFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);
+		defaultFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);
+		for (int i = 0; i < nameChar.length; i++) {
+			if (nameChar[i] > 128) {
+				try {
+					pinyinName += PinyinHelper.toHanyuPinyinStringArray(nameChar[i], defaultFormat)[0].charAt(0);
+				} catch (BadHanyuPinyinOutputFormatCombination e) {
+					e.printStackTrace();
+				} catch (ArrayIndexOutOfBoundsException e) {
+					// 特殊符号
+				}
+			} else {
+				pinyinName += nameChar[i];
+			}
+		}
+		return pinyinName;
+	}
+
+	/**
+	 * 汉字转换位汉语拼音,英文字符不变
+	 * 
+	 * @param chinese
+	 *            汉字
+	 * @return 拼音
+	 */
+	public static String converterToSpell(String chinese) {
+		String pinyinName = "";
+		char[] nameChar = chinese.toCharArray();
+		HanyuPinyinOutputFormat defaultFormat = new HanyuPinyinOutputFormat();
+		defaultFormat.setCaseType(HanyuPinyinCaseType.LOWERCASE);
+		defaultFormat.setToneType(HanyuPinyinToneType.WITHOUT_TONE);
+		for (int i = 0; i < nameChar.length; i++) {
+			if (nameChar[i] > 128) {
+				try {
+					pinyinName += PinyinHelper.toHanyuPinyinStringArray(nameChar[i], defaultFormat)[0];
+				} catch (BadHanyuPinyinOutputFormatCombination e) {
+					e.printStackTrace();
+				} catch (ArrayIndexOutOfBoundsException e) {
+					// 特殊符号
+				}
+			} else {
+				pinyinName += nameChar[i];
+			}
+		}
+		return pinyinName;
+	}
+
+}