mirror of
				https://github.com/TeaOSLab/EdgeAdmin.git
				synced 2025-11-04 05:00:25 +08:00 
			
		
		
		
	增加企业版认证相关API
This commit is contained in:
		
							
								
								
									
										6
									
								
								internal/const/plus.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										6
									
								
								internal/const/plus.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,6 @@
 | 
			
		||||
// Copyright 2021 Liuxiangchao iwind.liu@gmail.com. All rights reserved.
 | 
			
		||||
 | 
			
		||||
package teaconst
 | 
			
		||||
 | 
			
		||||
// IsPlus 是否为企业版
 | 
			
		||||
var IsPlus = false
 | 
			
		||||
@@ -87,7 +87,7 @@ func (this *AdminNode) Run() {
 | 
			
		||||
		Start()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// 实现守护进程
 | 
			
		||||
// Daemon 实现守护进程
 | 
			
		||||
func (this *AdminNode) Daemon() {
 | 
			
		||||
	path := os.TempDir() + "/edge-admin.sock"
 | 
			
		||||
	isDebug := lists.ContainsString(os.Args, "debug")
 | 
			
		||||
@@ -132,7 +132,7 @@ func (this *AdminNode) Daemon() {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// 安装系统服务
 | 
			
		||||
// InstallSystemService 安装系统服务
 | 
			
		||||
func (this *AdminNode) InstallSystemService() error {
 | 
			
		||||
	shortName := teaconst.SystemdServiceName
 | 
			
		||||
 | 
			
		||||
@@ -149,7 +149,7 @@ func (this *AdminNode) InstallSystemService() error {
 | 
			
		||||
	return nil
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// 添加子PID
 | 
			
		||||
// AddSubPID 添加子PID
 | 
			
		||||
func (this *AdminNode) AddSubPID(pid int) {
 | 
			
		||||
	this.subPIDs = append(this.subPIDs, pid)
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -207,7 +207,7 @@ func (this *RPCClient) HTTPRewriteRuleRPC() pb.HTTPRewriteRuleServiceClient {
 | 
			
		||||
	return pb.NewHTTPRewriteRuleServiceClient(this.pickConn())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// 访问日志
 | 
			
		||||
// HTTPAccessLogRPC 访问日志
 | 
			
		||||
func (this *RPCClient) HTTPAccessLogRPC() pb.HTTPAccessLogServiceClient {
 | 
			
		||||
	return pb.NewHTTPAccessLogServiceClient(this.pickConn())
 | 
			
		||||
}
 | 
			
		||||
@@ -328,7 +328,11 @@ func (this *RPCClient) NodeTaskRPC() pb.NodeTaskServiceClient {
 | 
			
		||||
	return pb.NewNodeTaskServiceClient(this.pickConn())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// 构造Admin上下文
 | 
			
		||||
func (this *RPCClient) AuthorityKeyRPC() pb.AuthorityKeyServiceClient {
 | 
			
		||||
	return pb.NewAuthorityKeyServiceClient(this.pickConn())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Context 构造Admin上下文
 | 
			
		||||
func (this *RPCClient) Context(adminId int64) context.Context {
 | 
			
		||||
	ctx := context.Background()
 | 
			
		||||
	m := maps.Map{
 | 
			
		||||
@@ -351,7 +355,7 @@ func (this *RPCClient) Context(adminId int64) context.Context {
 | 
			
		||||
	return ctx
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// 构造API上下文
 | 
			
		||||
// APIContext 构造API上下文
 | 
			
		||||
func (this *RPCClient) APIContext(apiNodeId int64) context.Context {
 | 
			
		||||
	ctx := context.Background()
 | 
			
		||||
	m := maps.Map{
 | 
			
		||||
@@ -374,7 +378,7 @@ func (this *RPCClient) APIContext(apiNodeId int64) context.Context {
 | 
			
		||||
	return ctx
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// 修改配置
 | 
			
		||||
// UpdateConfig 修改配置
 | 
			
		||||
func (this *RPCClient) UpdateConfig(config *configs.APIConfig) error {
 | 
			
		||||
	this.apiConfig = config
 | 
			
		||||
	return this.init()
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										68
									
								
								internal/tasks/task_authority.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										68
									
								
								internal/tasks/task_authority.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,68 @@
 | 
			
		||||
// Copyright 2021 Liuxiangchao iwind.liu@gmail.com. All rights reserved.
 | 
			
		||||
 | 
			
		||||
package tasks
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	teaconst "github.com/TeaOSLab/EdgeAdmin/internal/const"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/events"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/rpc"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeCommon/pkg/rpc/pb"
 | 
			
		||||
	"github.com/iwind/TeaGo/Tea"
 | 
			
		||||
	"github.com/iwind/TeaGo/logs"
 | 
			
		||||
	"time"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
func init() {
 | 
			
		||||
	events.On(events.EventStart, func() {
 | 
			
		||||
		task := NewAuthorityTask()
 | 
			
		||||
		go task.Start()
 | 
			
		||||
	})
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
type AuthorityTask struct {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func NewAuthorityTask() *AuthorityTask {
 | 
			
		||||
	return &AuthorityTask{}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func (this *AuthorityTask) Start() {
 | 
			
		||||
	ticker := time.NewTicker(10 * time.Minute)
 | 
			
		||||
	if Tea.IsTesting() {
 | 
			
		||||
		// 快速测试
 | 
			
		||||
		ticker = time.NewTicker(1 * time.Minute)
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// 初始化的时候先获取一次
 | 
			
		||||
	timeout := time.NewTimer(5 * time.Second)
 | 
			
		||||
	<-timeout.C
 | 
			
		||||
	err := this.Loop()
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		logs.Println("[TASK][AuthorityTask]" + err.Error())
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// 定时获取
 | 
			
		||||
	for range ticker.C {
 | 
			
		||||
		err := this.Loop()
 | 
			
		||||
		if err != nil {
 | 
			
		||||
			logs.Println("[TASK][AuthorityTask]" + err.Error())
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func (this *AuthorityTask) Loop() error {
 | 
			
		||||
	rpcClient, err := rpc.SharedRPC()
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		return err
 | 
			
		||||
	}
 | 
			
		||||
	resp, err := rpcClient.AuthorityKeyRPC().ReadAuthorityKey(rpcClient.Context(0), &pb.ReadAuthorityKeyRequest{})
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		return err
 | 
			
		||||
	}
 | 
			
		||||
	if resp.AuthorityKey != nil {
 | 
			
		||||
		teaconst.IsPlus = true
 | 
			
		||||
	} else {
 | 
			
		||||
		teaconst.IsPlus = false
 | 
			
		||||
	}
 | 
			
		||||
	return nil
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										51
									
								
								internal/web/actions/default/settings/authority/index.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										51
									
								
								internal/web/actions/default/settings/authority/index.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,51 @@
 | 
			
		||||
// Copyright 2021 Liuxiangchao iwind.liu@gmail.com. All rights reserved.
 | 
			
		||||
 | 
			
		||||
package server
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	teaconst "github.com/TeaOSLab/EdgeAdmin/internal/const"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/web/actions/actionutils"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeCommon/pkg/rpc/pb"
 | 
			
		||||
	"github.com/iwind/TeaGo/maps"
 | 
			
		||||
	timeutil "github.com/iwind/TeaGo/utils/time"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
type IndexAction struct {
 | 
			
		||||
	actionutils.ParentAction
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func (this *IndexAction) Init() {
 | 
			
		||||
	this.Nav("", "", "")
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func (this *IndexAction) RunGet(params struct{}) {
 | 
			
		||||
	keyResp, err := this.RPC().AuthorityKeyRPC().ReadAuthorityKey(this.AdminContext(), &pb.ReadAuthorityKeyRequest{})
 | 
			
		||||
	if err != nil {
 | 
			
		||||
		this.ErrorPage(err)
 | 
			
		||||
		return
 | 
			
		||||
	}
 | 
			
		||||
	var keyMap maps.Map = nil
 | 
			
		||||
	teaconst.IsPlus = false
 | 
			
		||||
	if keyResp.AuthorityKey != nil {
 | 
			
		||||
		if len(keyResp.AuthorityKey.MacAddresses) == 0 {
 | 
			
		||||
			keyResp.AuthorityKey.MacAddresses = []string{}
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		isActive := len(keyResp.AuthorityKey.DayTo) > 0 && keyResp.AuthorityKey.DayTo >= timeutil.Format("Y-m-d")
 | 
			
		||||
		if isActive {
 | 
			
		||||
			teaconst.IsPlus = true
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		keyMap = maps.Map{
 | 
			
		||||
			"dayFrom":      keyResp.AuthorityKey.DayFrom,
 | 
			
		||||
			"dayTo":        keyResp.AuthorityKey.DayTo,
 | 
			
		||||
			"macAddresses": keyResp.AuthorityKey.MacAddresses,
 | 
			
		||||
			"hostname":     keyResp.AuthorityKey.Hostname,
 | 
			
		||||
			"isExpired":    !isActive,
 | 
			
		||||
			"updatedTime":  timeutil.FormatTime("Y-m-d H:i:s", keyResp.AuthorityKey.UpdatedAt),
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
	this.Data["key"] = keyMap
 | 
			
		||||
 | 
			
		||||
	this.Show()
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										19
									
								
								internal/web/actions/default/settings/authority/init.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										19
									
								
								internal/web/actions/default/settings/authority/init.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,19 @@
 | 
			
		||||
package server
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/configloaders"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/settings/settingutils"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/web/helpers"
 | 
			
		||||
	"github.com/iwind/TeaGo"
 | 
			
		||||
)
 | 
			
		||||
 | 
			
		||||
func init() {
 | 
			
		||||
	TeaGo.BeforeStart(func(server *TeaGo.Server) {
 | 
			
		||||
		server.
 | 
			
		||||
			Helper(helpers.NewUserMustAuth(configloaders.AdminModuleCodeSetting)).
 | 
			
		||||
			Helper(settingutils.NewAdvancedHelper("authority")).
 | 
			
		||||
			Prefix("/settings/authority").
 | 
			
		||||
			Get("", new(IndexAction)).
 | 
			
		||||
			EndAll()
 | 
			
		||||
	})
 | 
			
		||||
}
 | 
			
		||||
@@ -2,6 +2,7 @@ package settingutils
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/configloaders"
 | 
			
		||||
	teaconst "github.com/TeaOSLab/EdgeAdmin/internal/const"
 | 
			
		||||
	"github.com/TeaOSLab/EdgeAdmin/internal/web/actions/actionutils"
 | 
			
		||||
	"github.com/iwind/TeaGo/actions"
 | 
			
		||||
)
 | 
			
		||||
@@ -34,7 +35,10 @@ func (this *AdvancedHelper) BeforeAction(actionPtr actions.ActionWrapper) (goNex
 | 
			
		||||
		tabbar.Add("API节点", "", "/api", "", this.tab == "apiNodes")
 | 
			
		||||
		tabbar.Add("用户节点", "", "/settings/userNodes", "", this.tab == "userNodes")
 | 
			
		||||
		tabbar.Add("日志数据库", "", "/db", "", this.tab == "dbNodes")
 | 
			
		||||
		tabbar.Add("监控节点", "", "/settings/monitorNodes", "", this.tab == "monitorNodes")
 | 
			
		||||
		if teaconst.IsPlus {
 | 
			
		||||
			tabbar.Add("监控节点", "", "/settings/monitorNodes", "", this.tab == "monitorNodes")
 | 
			
		||||
		}
 | 
			
		||||
		tabbar.Add("企业版认证", "", "/settings/authority", "", this.tab == "authority")
 | 
			
		||||
 | 
			
		||||
		//tabbar.Add("备份", "", "/settings/backup", "", this.tab == "backup")
 | 
			
		||||
	}
 | 
			
		||||
 
 | 
			
		||||
@@ -234,6 +234,7 @@ func (this *userMustAuth) modules(adminId int64) []maps.Map {
 | 
			
		||||
					"name": "通知媒介",
 | 
			
		||||
					"url":  "/admins/recipients",
 | 
			
		||||
					"code": "recipients",
 | 
			
		||||
					"isOn": teaconst.IsPlus,
 | 
			
		||||
				},
 | 
			
		||||
			},
 | 
			
		||||
		},
 | 
			
		||||
 
 | 
			
		||||
@@ -84,6 +84,7 @@ import (
 | 
			
		||||
	_ "github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/servers/server/settings/websocket"
 | 
			
		||||
	_ "github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/servers/server/stat"
 | 
			
		||||
	_ "github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/settings"
 | 
			
		||||
	_ "github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/settings/authority"
 | 
			
		||||
	_ "github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/settings/backup"
 | 
			
		||||
	_ "github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/settings/database"
 | 
			
		||||
	_ "github.com/TeaOSLab/EdgeAdmin/internal/web/actions/default/settings/ip-library"
 | 
			
		||||
 
 | 
			
		||||
@@ -85,7 +85,7 @@
 | 
			
		||||
                    <div class="subtitle" v-if="module.subtitle != null && module.subtitle.length > 0">{{module.subtitle}}</div>
 | 
			
		||||
				</a>
 | 
			
		||||
				<div v-if="teaMenu == module.code" class="sub-items">
 | 
			
		||||
					<a class="item" v-for="subItem in module.subItems" :href="subItem.url" :class="{active:subItem.code == teaSubMenu}">{{subItem.name}}</a>
 | 
			
		||||
					<a class="item" v-for="subItem in module.subItems" v-if="subItem.isOn !== false" :href="subItem.url" :class="{active:subItem.code == teaSubMenu}">{{subItem.name}}</a>
 | 
			
		||||
				</div>
 | 
			
		||||
			</div>
 | 
			
		||||
        </div>
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										41
									
								
								web/views/@default/settings/authority/index.html
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										41
									
								
								web/views/@default/settings/authority/index.html
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,41 @@
 | 
			
		||||
{$layout}
 | 
			
		||||
 | 
			
		||||
<div class="ui message warning" v-if="key == null">认证之后,可以使用企业版功能,当前你还没有认证,<a href="http://edge.teaos.cn/docs/Plus/Authority/Index.md" target="_blank">[在这里看认证方法]</a>。</div>
 | 
			
		||||
 | 
			
		||||
<div v-if="key != null">
 | 
			
		||||
    <div class="margin"></div>
 | 
			
		||||
    <table class="ui table definition selectable">
 | 
			
		||||
        <tr>
 | 
			
		||||
            <td>状态</td>
 | 
			
		||||
            <td>
 | 
			
		||||
                <span class="green">已认证</span>
 | 
			
		||||
            </td>
 | 
			
		||||
        </tr>
 | 
			
		||||
        <tr>
 | 
			
		||||
            <td class="title">开始日期</td>
 | 
			
		||||
            <td>{{key.dayFrom}}</td>
 | 
			
		||||
        </tr>
 | 
			
		||||
        <tr>
 | 
			
		||||
            <td class="title">结束日期</td>
 | 
			
		||||
            <td>{{key.dayTo}}
 | 
			
		||||
                <div v-if="key.isExpired" style="margin-top: 0.5em">
 | 
			
		||||
                    <span class="red">已过期,请尽快更新认证信息。</span>
 | 
			
		||||
                </div>
 | 
			
		||||
            </td>
 | 
			
		||||
        </tr>
 | 
			
		||||
        <tr>
 | 
			
		||||
            <td>主机名</td>
 | 
			
		||||
            <td>{{key.hostname}}
 | 
			
		||||
                <p class="comment">认证服务所在服务器主机名。</p>
 | 
			
		||||
            </td>
 | 
			
		||||
        </tr>
 | 
			
		||||
        <tr>
 | 
			
		||||
            <td>主机MAC地址</td>
 | 
			
		||||
            <td>
 | 
			
		||||
                <span v-for="address in key.macAddresses" class="ui label basic small">{{address}}</span>
 | 
			
		||||
                <p class="comment">认证服务所在服务器的MAC地址。</p>
 | 
			
		||||
            </td>
 | 
			
		||||
        </tr>
 | 
			
		||||
    </table>
 | 
			
		||||
    <p class="comment">数据更新于{{key.updatedTime}}。</p>
 | 
			
		||||
</div>
 | 
			
		||||
		Reference in New Issue
	
	Block a user