initial crm server

This commit is contained in:
zchengo
2022-11-28 16:38:30 +08:00
parent 61122aef6a
commit af7cd0c44c
36 changed files with 2615 additions and 0 deletions
+33
View File
@@ -0,0 +1,33 @@
package service
import (
"context"
"crm/global"
"crm/models"
)
const (
// 数据库表名
USER = "user"
CUSTOMER = "customer"
CONTRACT = "contract"
PRODUCT = "product"
)
var ctx = context.Background()
// RestPage 分页查询
// page 设置起始页、每页条数,
// name 查询目标表的名称
// query 查询条件,
// dest 查询结果绑定的结构体,
// bind 绑定表结构对应的结构体
func restPage(page models.Page, name string, query interface{}, dest interface{}, bind interface{}) (int64, error) {
if page.PageNum > 0 && page.PageSize > 0 {
offset := (page.PageNum - 1) * page.PageSize
global.Db.Offset(offset).Limit(page.PageSize).Table(name).Where(query).Find(dest)
}
res := global.Db.Table(name).Where(query).Find(bind)
return res.RowsAffected, res.Error
}
+106
View File
@@ -0,0 +1,106 @@
package service
import (
"crm/global"
"crm/models"
"crm/response"
"time"
)
type ContractService struct {
}
// 创建合同
func (c *ContractService) Create(param *models.ContractCreateParam) int {
contract := models.Contract{
Name: param.Name,
Amount: param.Amount,
BeginTime: param.BeginTime,
OverTime: param.OverTime,
Remarks: param.Remarks,
Cid: param.Cid,
Productlist: param.Productlist,
Status: param.Status,
Creator: param.Creator,
Created: time.Now().Unix(),
}
if err := global.Db.Create(&contract).Error; err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 更新合同
func (c *ContractService) Update(param *models.ContractUpdateParam) int {
contract := models.Contract{
Id: param.Id,
Name: param.Name,
Amount: param.Amount,
BeginTime: param.BeginTime,
OverTime: param.OverTime,
Remarks: param.Remarks,
Cid: param.Cid,
Productlist: param.Productlist,
Status: param.Status,
Updated: time.Now().Unix(),
}
err := global.Db.Model(&contract).Updates(&contract).Error
if err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 删除合同
func (c *ContractService) Delete(param *models.ContractDeleteParam) int {
if err := global.Db.Delete(&models.Contract{}, param.Ids).Error; err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 查询合同列表
func (c *ContractService) QueryList(param *models.ContractQueryParam) ([]*models.ContractList, int64, int) {
contractList := make([]*models.ContractList, 0)
s := "contract.id, contract.name, contract.amount, contract.begin_time, contract.over_time, customer.name as cname, contract.remarks, contract.status, contract.created, contract.updated"
j := "inner join customer on contract.cid = customer.id and contract.creator = ?"
// 分页查询
offset := (param.Page.PageNum - 1) * param.Page.PageSize
mdb := global.Db.Offset(offset).Limit(param.Page.PageSize).Table(CONTRACT).Select(s)
var err error
if param.Id != 0 {
err = mdb.Joins(j+" and contract.id = ?", param.Creator, param.Id).Scan(&contractList).Error
} else {
err = mdb.Joins(j, param.Creator).Scan(&contractList).Error
}
if err != nil {
return nil, 0, response.ErrCodeFailed
}
var rows int64
global.Db.Raw("select count(*) from contract where creator = ?", param.Creator).Scan(&rows)
return contractList, rows, response.ErrCodeSuccess
}
// 查询合同信息
func (c *ContractService) QueryInfo(param *models.ContractQueryParam) (*models.ContractInfo, int) {
contract := models.Contract{
Id: param.Id,
}
contractInfo := models.ContractInfo{}
err := global.Db.Table(CONTRACT).Where(&contract).First(&contractInfo).Error
if err != nil {
return nil, response.ErrCodeFailed
}
return &contractInfo, response.ErrCodeSuccess
}
// 在编辑合同中,添加产品后,增加已添加的产品列表
func (p *ContractService) QueryPlist(param *models.ProductQueryParam) ([]*models.Products, int) {
products := make([]*models.Products, 0)
err := global.Db.Table(PRODUCT).Find(&products, param.Ids).Error
if err != nil {
return nil, response.ErrCodeFailed
}
return products, response.ErrCodeSuccess
}
+103
View File
@@ -0,0 +1,103 @@
package service
import (
"crm/global"
"crm/models"
"crm/response"
"time"
)
type CustomerService struct {
}
// 创建客户
func (c *CustomerService) Create(param *models.CustomerCreateParam) int {
customer := models.Customer{
Name: param.Name,
Source: param.Source,
Phone: param.Phone,
Email: param.Email,
Industry: param.Industry,
Level: param.Level,
Remarks: param.Remarks,
Region: param.Region,
Address: param.Address,
Status: 1,
Creator: param.Creator,
Created: time.Now().Unix(),
}
if err := global.Db.Create(&customer).Error; err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 更新客户
func (c *CustomerService) Update(param *models.CustomerUpdateParam) int {
customer := models.Customer{
Name: param.Name,
Source: param.Source,
Phone: param.Phone,
Email: param.Email,
Industry: param.Industry,
Level: param.Level,
Remarks: param.Remarks,
Region: param.Region,
Address: param.Address,
Status: param.Status,
Updated: time.Now().Unix(),
}
err := global.Db.Model(&models.Customer{}).Where("id = ?", param.Id).Updates(&customer).Error
if err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 删除客户
func (c *CustomerService) Delete(param *models.CustomerDeleteParam) int {
if err := global.Db.Delete(&models.Customer{}, param.Ids).Error; err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 查询客户列表
func (c *CustomerService) QueryList(param *models.CustomerQueryParam) ([]*models.CustomerList, int64, int) {
customer := models.Customer{
Name: param.Name,
Creator: param.Creator,
}
customerList := make([]*models.CustomerList, 0)
rows, err := restPage(param.Page, CUSTOMER, customer, &customerList, &[]*models.CustomerList{})
if err != nil {
return nil, 0, response.ErrCodeFailed
}
return customerList, rows, response.ErrCodeSuccess
}
// 查询客户信息
func (c *CustomerService) QueryInfo(param *models.CustomerQueryParam) (*models.CustomerInfo, int) {
customer := models.Customer{
Id: param.Id,
}
customerInfo := models.CustomerInfo{}
err := global.Db.Table(CUSTOMER).Where(&customer).First(&customerInfo).Error
if err != nil {
return nil, response.ErrCodeFailed
}
return &customerInfo, response.ErrCodeSuccess
}
// 查询客户选项
func (c *CustomerService) QueryOption(uid int64) ([]*models.CustomerOption, int) {
customer := models.Customer{
Creator: uid,
}
option := make([]*models.CustomerOption, 0)
err := global.Db.Table(CUSTOMER).Where(&customer).Find(&option).Error
if err != nil {
return nil, response.ErrCodeFailed
}
return option, response.ErrCodeSuccess
}
+40
View File
@@ -0,0 +1,40 @@
package service
import (
"crm/global"
"crm/models"
"fmt"
"time"
)
type DashboardService struct {
}
// 数据汇总
func (d *DashboardService) Summary(uid int64) models.DashboardSum {
var ds models.DashboardSum
global.Db.Raw("select count(*) from customer where creator = ?", uid).Scan(&ds.Customers)
global.Db.Raw("select count(*) from contract where creator = ?", uid).Scan(&ds.Contracts)
global.Db.Raw("select sum(amount) from contract where creator = ?", uid).Scan(&ds.ContractAmount)
global.Db.Raw("select count(*) from product where creator = ?", uid).Scan(&ds.Products)
now := time.Now().Unix()
con := "created > ? and created < ? and status = 1 and creator = ?"
for i, d := 0, 7; i < 7; i++ {
day := now - (int64(d) * 24 * 60 * 60)
start, end := dayRange(day)
fmt.Println(start, end)
global.Db.Table(CONTRACT).Where(con, start, end, uid).Pluck("amount", &ds.Amount[i])
ds.Date[i] = time.Unix(day, 0).Format("01-02")
d--
}
return ds
}
// 获取某一天的时间范围
func dayRange(day int64) (int64, int64) {
t := time.Unix(day, 0)
start := time.Date(t.Year(), t.Month(), t.Day(), 0, 0, 0, 0, t.Location())
end := start.AddDate(0, 0, 1)
return start.Unix(), end.Unix()
}
+87
View File
@@ -0,0 +1,87 @@
package service
import (
"crm/global"
"crm/models"
"crm/response"
"time"
)
type ProductService struct {
}
// 创建产品
func (p *ProductService) Create(param *models.ProductCreateParam) int {
product := models.Product{
Name: param.Name,
Type: param.Type,
Unit: param.Unit,
Code: param.Code,
Price: param.Price,
Description: param.Description,
Status: param.Status,
Creator: param.Creator,
Created: time.Now().Unix(),
}
if err := global.Db.Create(&product).Error; err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 更新产品
func (p *ProductService) Update(param *models.ProductUpdateParam) int {
product := models.Product{
Id: param.Id,
Name: param.Name,
Type: param.Type,
Unit: param.Unit,
Code: param.Code,
Price: param.Price,
Description: param.Description,
Status: param.Status,
Updated: time.Now().Unix(),
}
err := global.Db.Model(&product).Updates(&product).Error
if err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 删除产品
func (p *ProductService) Delete(param *models.ProductDeleteParam) int {
err := global.Db.Delete(&models.Product{}, param.Ids).Error
if err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 查询产品列表
func (p *ProductService) QueryList(param *models.ProductQueryParam) ([]*models.ProductList, int64, int) {
product := models.Product{
Name: param.Name,
Status: param.Status,
Creator: param.Creator,
}
productList := make([]*models.ProductList, 0)
rows, err := restPage(param.Page, PRODUCT, product, &productList, &[]*models.ProductList{})
if err != nil {
return nil, 0, response.ErrCodeFailed
}
return productList, rows, response.ErrCodeSuccess
}
// 查询产品信息
func (p *ProductService) QueryInfo(param *models.ProductQueryParam) (*models.ProductInfo, int) {
product := models.Product{
Id: param.Id,
}
productInfo := models.ProductInfo{}
err := global.Db.Table(PRODUCT).Where(&product).First(&productInfo).Error
if err != nil {
return nil, response.ErrCodeFailed
}
return &productInfo, response.ErrCodeSuccess
}
+233
View File
@@ -0,0 +1,233 @@
package service
import (
"crm/common"
"crm/global"
"crm/models"
"crm/response"
"fmt"
"log"
"strconv"
"time"
"golang.org/x/crypto/bcrypt"
)
const (
TOKEN_MAX_EXPIRE_TIME = 7 * 24 // Token最长有效期
)
type UserService struct {
}
// 用户注册
func (u *UserService) Register(param *models.UserCreateParam) int {
// 判断用户是否存在
var user = models.User{}
err := global.Db.Where("email = ?", param.Email).First(&user).Error
if err == nil && user.Id > 0 {
return response.ErrCodeUserHasExist
}
// 校验验证码是否正确
key := fmt.Sprintf("user:%s:code", param.Email)
code := global.Rdb.Get(ctx, key).Val()
if code != param.Code {
return response.ErrCodeVerityCodeInvalid
}
// 对密码进行加密
password, err := bcrypt.GenerateFromPassword([]byte(param.Password), bcrypt.DefaultCost)
if err != nil {
return response.ErrCodeFailed
}
// 创建用户
newUser := models.User{
Email: param.Email,
Password: string(password),
Version: 1,
Status: 1,
Created: time.Now().Unix(),
}
if err := global.Db.Create(&newUser).Error; err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 用户登录
func (u *UserService) Login(param *models.UserLoginParam) (*models.UserInfo, int) {
// 判断用户是否存在
var user = models.User{}
err := global.Db.Where("email = ?", param.Email).First(&user).Error
if err != nil {
return nil, response.ErrCodeUserNotExist
}
// 校验账号密码
err = bcrypt.CompareHashAndPassword([]byte(user.Password), []byte(param.Password))
if err != nil {
return nil, response.ErrCOdeUserEmailOrPass
}
// 生成并保存Token
token, err := common.GenToken(user.Id, TOKEN_MAX_EXPIRE_TIME)
if err != nil {
log.Printf("[error]Login:GenerateToken:%s", err)
return nil, response.ErrCodeFailed
}
expiration := time.Duration(TOKEN_MAX_EXPIRE_TIME) * time.Hour
if err := global.Rdb.SetEx(ctx, token, "", expiration).Err(); err != nil {
log.Printf("[error]Login:SaveToken:%s", err)
return nil, response.ErrCodeFailed
}
userInfo := models.UserInfo{
Uid: user.Id,
Token: token,
}
return &userInfo, response.ErrCodeSuccess
}
// 获取验证码
func (u *UserService) GetVerifyCode(email string) int {
// 生成6位随机数
code := common.RandInt(100000, 999998)
// 保存验证码
key := fmt.Sprintf("user:%s:code", email)
if err := global.Rdb.SetEx(ctx, key, strconv.Itoa(code), 10*time.Minute).Err(); err != nil {
return response.ErrCodeFailed
}
// 发送验证码
content := fmt.Sprintf("验证码%v,您正在找回密码,切勿向他人泄露。", code)
err := common.SendMail(email, content)
if err != nil {
return response.ErrCodeVerityCodeSendFailed
}
return response.ErrCodeSuccess
}
// 忘记密码
func (u *UserService) ForgotPass(param *models.UserPassParam) int {
// 判断用户是否存在
var user = models.User{}
if err := global.Db.Where("email = ?", param.Email).First(&user).Error; err != nil {
return response.ErrCodeUserNotExist
}
// 校验验证码是否正确
key := fmt.Sprintf("user:%s:code", param.Email)
code := global.Rdb.Get(ctx, key).Val()
if code != param.Code {
return response.ErrCodeVerityCodeInvalid
}
// 对密码进行加密,更新密码
password, err := bcrypt.GenerateFromPassword([]byte(param.Password), bcrypt.DefaultCost)
if err != nil {
return response.ErrCodeFailed
}
upass := models.User{
Password: string(password),
Updated: time.Now().Unix(),
}
err = global.Db.Model(&models.User{}).Where("email = ?", param.Email).Updates(&upass).Error
if err != nil {
return response.ErrCodeUserPassResetFailed
}
return response.ErrCodeSuccess
}
// 修改邮箱
func (u *UserService) UpdateMail(param *models.UserMailParam) int {
// 校验验证码是否正确
key := fmt.Sprintf("user:%s:code", param.Email)
code := global.Rdb.Get(ctx, key).Val()
if code != param.Code {
return response.ErrCodeVerityCodeInvalid
}
user := models.User{
Email: param.NewEmail,
Updated: time.Now().Unix(),
}
err := global.Db.Table(USER).Where("email = ?", param.Email).Updates(&user).Error
if err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 退出登录
func (u *UserService) Logout(token string) int {
err := global.Rdb.Del(ctx, token).Err()
if err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 注销账号
func (u *UserService) Delete(param models.UserDeleteParam) int {
// 校验验证码是否正确
key := fmt.Sprintf("user:%s:code", param.Email)
code := global.Rdb.Get(ctx, key).Val()
if code != param.Code {
return response.ErrCodeVerityCodeInvalid
}
err := global.Db.Delete(&models.User{}, param.Id).Error
if err != nil {
return response.ErrCodeFailed
}
return response.ErrCodeSuccess
}
// 获取用户信息
func (u *UserService) GetInfo(uid int64) (*models.UserPersonInfo, int) {
var user models.UserPersonInfo
err := global.Db.Table(USER).Where("id = ?", uid).First(&user).Error
if err != nil {
return nil, response.ErrCodeFailed
}
// 判断用户订阅是否过期
if user.Version == 2 && time.Now().Unix() > int64(user.Expired) {
err := global.Db.Model(&models.User{}).Where("id = ?", uid).Update("version", 1).Error
if err != nil {
return nil, response.ErrCodeFailed
}
return &user, response.ErrCodeSuccess
}
return &user, response.ErrCodeSuccess
}
// 订阅个人版
func (u *UserService) Buy(uid int64) (*models.UserVerisonInfo, int) {
// 订阅一个月按30天计算
month := time.Now().Unix() + int64(2592000)
user := models.User{
Version: 2,
Expired: month,
Updated: time.Now().Unix(),
}
err := global.Db.Model(&models.User{}).Where("id = ?", uid).Updates(&user).Error
if err != nil {
return nil, response.ErrCodeFailed
}
// 查询版本信息
var version models.UserVerisonInfo
if err := global.Db.Table(USER).Where("id = ?", uid).First(&version).Error; err != nil {
return nil, response.ErrCodeFailed
}
return &version, response.ErrCodeSuccess
}
// 校验用户Token
func (u *UserService) VerifyToken(token string) error {
return global.Rdb.Exists(ctx, token).Err()
}