237 lines
		
	
	
		
			5.4 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
			
		
		
	
	
			237 lines
		
	
	
		
			5.4 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
| package role
 | |
| 
 | |
| import (
 | |
| 	"bytes"
 | |
| 	"context"
 | |
| 	"fmt"
 | |
| 	"time"
 | |
| 
 | |
| 	"management/internal/erpserver/model/dto"
 | |
| 	"management/internal/erpserver/model/system"
 | |
| 	"management/internal/erpserver/repository"
 | |
| 	"management/internal/pkg/sqldb"
 | |
| 
 | |
| 	"github.com/drhin/logger"
 | |
| )
 | |
| 
 | |
| type store struct {
 | |
| 	db  *repository.Store
 | |
| 	log *logger.Logger
 | |
| }
 | |
| 
 | |
| func NewStore(db *repository.Store, log *logger.Logger) system.RoleRepository {
 | |
| 	return &store{
 | |
| 		db:  db,
 | |
| 		log: log,
 | |
| 	}
 | |
| }
 | |
| 
 | |
| func (s *store) Initialize(ctx context.Context) (*system.Role, error) {
 | |
| 	count, err := s.Count(ctx, dto.SearchDto{})
 | |
| 	if err != nil {
 | |
| 		return nil, err
 | |
| 	}
 | |
| 	if count == 0 {
 | |
| 		obj := system.Role{
 | |
| 			Name:        "Company",
 | |
| 			DisplayName: "公司",
 | |
| 			Vip:         false,
 | |
| 			ParentID:    0,
 | |
| 			ParentPath:  ",0,",
 | |
| 			Status:      0,
 | |
| 			CreatedAt:   time.Now(),
 | |
| 			UpdatedAt:   time.Now(),
 | |
| 		}
 | |
| 		if err := s.Create(ctx, &obj); err != nil {
 | |
| 			return nil, err
 | |
| 		}
 | |
| 
 | |
| 		obj1 := system.Role{
 | |
| 			Name:        "SuperAdmin",
 | |
| 			DisplayName: "超级管理员",
 | |
| 			Vip:         true,
 | |
| 			ParentID:    obj.ID,
 | |
| 			ParentPath:  fmt.Sprintf(",0,%d,", obj.ID),
 | |
| 			Status:      0,
 | |
| 			CreatedAt:   time.Now(),
 | |
| 			UpdatedAt:   time.Now(),
 | |
| 		}
 | |
| 		if err := s.Create(ctx, &obj1); err != nil {
 | |
| 			return nil, err
 | |
| 		}
 | |
| 		return &obj1, nil
 | |
| 	}
 | |
| 
 | |
| 	return s.GetByVip(ctx, true)
 | |
| 
 | |
| }
 | |
| 
 | |
| func (s *store) Create(ctx context.Context, obj *system.Role) error {
 | |
| 	//goland:noinspection ALL
 | |
| 	const q = `
 | |
| 	INSERT INTO sys_role (
 | |
| 		name, display_name, parent_id, parent_path, vip, status, sort
 | |
| 	) VALUES (
 | |
| 		:name, :display_name, :parent_id, :parent_path, :vip, :status, :sort
 | |
| 	)`
 | |
| 
 | |
| 	return sqldb.NamedExecContext(ctx, s.log, s.db.DB(ctx), q, obj)
 | |
| }
 | |
| 
 | |
| func (s *store) Update(ctx context.Context, obj *system.Role) error {
 | |
| 	const q = `
 | |
| 	UPDATE sys_role
 | |
| 	SET name = :name,
 | |
| 		display_name = :display_name,
 | |
| 		parent_id = :parent_id,
 | |
| 		parent_path = :parent_path,
 | |
| 		status = :status,
 | |
| 		sort = :sort,
 | |
| 		updated_at = :updated_at
 | |
| 	WHERE id = :id;`
 | |
| 
 | |
| 	return sqldb.NamedExecContext(ctx, s.log, s.db.DB(ctx), q, obj)
 | |
| }
 | |
| 
 | |
| func (s *store) GetByVip(ctx context.Context, vip bool) (*system.Role, error) {
 | |
| 	//goland:noinspection ALL
 | |
| 	const q = `
 | |
| 	SELECT
 | |
| 		id, name, display_name, parent_id, parent_path, vip, status, sort, created_at, updated_at
 | |
| 	FROM 
 | |
| 		sys_role
 | |
| 	WHERE 
 | |
| 		vip = :vip;`
 | |
| 
 | |
| 	data := map[string]any{
 | |
| 		"vip": vip,
 | |
| 	}
 | |
| 
 | |
| 	var role system.Role
 | |
| 	if err := sqldb.NamedQueryStruct(ctx, s.log, s.db.DB(ctx), q, data, &role); err != nil {
 | |
| 		return nil, fmt.Errorf("select vip role: %w", err)
 | |
| 	}
 | |
| 
 | |
| 	return &role, nil
 | |
| }
 | |
| 
 | |
| func (s *store) Get(ctx context.Context, id int32) (*system.Role, error) {
 | |
| 	//goland:noinspection ALL
 | |
| 	const q = `
 | |
| 	SELECT
 | |
| 		id, name, display_name, parent_id, parent_path, vip, status, sort, created_at, updated_at
 | |
| 	FROM 
 | |
| 		sys_role
 | |
| 	WHERE 
 | |
| 		id = :id;`
 | |
| 
 | |
| 	data := map[string]any{
 | |
| 		"id": id,
 | |
| 	}
 | |
| 
 | |
| 	var role system.Role
 | |
| 	err := sqldb.NamedQueryStruct(ctx, s.log, s.db.DB(ctx), q, data, &role)
 | |
| 	if err != nil {
 | |
| 		return nil, fmt.Errorf("select id role: %w", err)
 | |
| 	}
 | |
| 
 | |
| 	return &role, nil
 | |
| }
 | |
| 
 | |
| func (s *store) All(ctx context.Context) ([]*system.Role, error) {
 | |
| 	//goland:noinspection ALL
 | |
| 	const q = `
 | |
| 	SELECT
 | |
| 		id, name, display_name, parent_id, parent_path, vip, status, sort, created_at, updated_at
 | |
| 	FROM 
 | |
| 		sys_role;`
 | |
| 
 | |
| 	data := map[string]any{}
 | |
| 
 | |
| 	var roles []system.Role
 | |
| 	err := sqldb.NamedQuerySlice(ctx, s.log, s.db.DB(ctx), q, data, &roles)
 | |
| 	if err != nil {
 | |
| 		return nil, fmt.Errorf("select all role: %w", err)
 | |
| 	}
 | |
| 
 | |
| 	return toPointer(roles), nil
 | |
| }
 | |
| 
 | |
| func (s *store) Count(ctx context.Context, filter dto.SearchDto) (int64, error) {
 | |
| 	//goland:noinspection ALL
 | |
| 	const q = `
 | |
| 	SELECT 
 | |
| 		COUNT(1)
 | |
| 	FROM 
 | |
| 		sys_role`
 | |
| 
 | |
| 	data := map[string]any{}
 | |
| 
 | |
| 	buf := bytes.NewBufferString(q)
 | |
| 	applyFilter(filter, data, buf)
 | |
| 
 | |
| 	var count struct {
 | |
| 		Count int64 `db:"count"`
 | |
| 	}
 | |
| 
 | |
| 	err := sqldb.NamedQueryStruct(ctx, s.log, s.db.DB(ctx), buf.String(), data, &count)
 | |
| 	if err != nil {
 | |
| 		return 0, fmt.Errorf("select count role: %w", err)
 | |
| 	}
 | |
| 
 | |
| 	return count.Count, nil
 | |
| }
 | |
| 
 | |
| func (s *store) List(ctx context.Context, filter dto.SearchDto) ([]*system.Role, error) {
 | |
| 	//goland:noinspection ALL
 | |
| 	const q = `
 | |
| 	SELECT
 | |
| 		id, name, display_name, parent_id, parent_path, vip, status, sort, created_at, updated_at
 | |
| 	FROM 
 | |
| 		sys_role`
 | |
| 
 | |
| 	data := map[string]any{
 | |
| 		"offset":        (filter.Page - 1) * filter.Rows,
 | |
| 		"rows_per_page": filter.Rows,
 | |
| 	}
 | |
| 
 | |
| 	buf := bytes.NewBufferString(q)
 | |
| 	applyFilter(filter, data, buf)
 | |
| 
 | |
| 	buf.WriteString(" ORDER BY id DESC")
 | |
| 	buf.WriteString(" LIMIT :rows_per_page OFFSET :offset")
 | |
| 
 | |
| 	var roles []system.Role
 | |
| 	err := sqldb.NamedQuerySlice(ctx, s.log, s.db.DB(ctx), buf.String(), data, &roles)
 | |
| 	if err != nil {
 | |
| 		return nil, err
 | |
| 	}
 | |
| 	return toPointer(roles), nil
 | |
| }
 | |
| 
 | |
| func (s *store) RebuildParentPath(ctx context.Context) error {
 | |
| 	query := `UPDATE sys_role AS tm
 | |
| 	SET parent_path = (SELECT ',' || string_agg(cast(t.parent_id AS VARCHAR), ',') || ','
 | |
| 					   FROM (WITH RECURSIVE temp (id, parent_id) AS (SELECT id, tm.parent_id
 | |
| 																	 FROM sys_role
 | |
| 																	 WHERE id = tm.id
 | |
| 																	 UNION ALL
 | |
| 																	 SELECT sys_role.id, sys_role.parent_id
 | |
| 																	 FROM sys_role,
 | |
| 																		  temp
 | |
| 																	 WHERE sys_role.id = temp.parent_id)
 | |
| 							 SELECT id, parent_id
 | |
| 							 FROM temp
 | |
| 							 ORDER BY id) AS t)
 | |
| 	WHERE tm.status = 0;`
 | |
| 	return sqldb.NamedExecContext(ctx, s.log, s.db.DB(ctx), query, nil)
 | |
| }
 | |
| 
 | |
| func toPointer(data []system.Role) []*system.Role {
 | |
| 	var res []*system.Role
 | |
| 	for _, v := range data {
 | |
| 		res = append(res, &v)
 | |
| 	}
 | |
| 	return res
 | |
| }
 |