custom

package
v0.0.0-...-6ac6f58 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Apr 11, 2024 License: Apache-2.0, BSD-3-Clause, MIT Imports: 8 Imported by: 0

README

自定义handler接入

[TOC]

1. 快速入门

img

如上图所示,是一个任务的流程图,其中:

  1. 黄色部分是一个任务本身的基本过程
    • "work":任务主体,如make build、bazel build等。
    • "sub-work":子任务,是分布式加速的直接对象。work通过并发执行多个sub-work来提升处理效率,如make下的gcc、clang等编译命令。
  2. 绿色部分是tbs提供的功能
    • "start with bk-booster":提供程序入口,用户可以直接下载工具作为入口执行。
    • "hook library":提供preload的hook动态库,可以劫持想要的sub-work。
    • "remote-execute":提供远程分布式资源调配、执行命令、返回结果。
    • "local-execute":提供错误本地重试、本机资源保护。
  3. 蓝色部分是用户接入handler需要实现的部分,均为函数级别的实现
    • "pre-work":定义在work主体执行前要做的事
    • "post-work":定义在work主体结束后要收尾的事
    • "pre-load hook config":定义hook的配置,告诉tbs你要劫持的命令,如gcc、clang
    • "pre-execute":定义单个sub-work被远程执行前的工作,并给出远程执行需要的信息(依赖文件、命令参数、需要的结果等)
    • "post-execute":定义单个sub-work远程执行后的工作,并根据remote返回的信息来确定命令的结果
    • "final-execute":定义单个sub-work最后的收尾工作

用户根据实际要扩展的场景,选取下文的接入方式之一,完成蓝色部分的函数实现,即可实现一个自定义handler接入。

2. 接入方式介绍

非侵入性,独立的handler插件。

2.1 Golang Plugins

golang提供了以plugin的形式导出函数与类型,当扩展方式是plugin时,tbs将主动获取plugin,并用其提供的接口作为handler操作。

接入时,只需独立编写、构建出plugin,然后与官网下载的对应版本的tbs套件结合使用即可。

3. 接入样例

tbs将从环境变量BK_DIST_CUSTOM_SETTINGS中获取自定义handler的信息。

其内容应为json格式

{
    "type": 1,
    "path": "/etc/bk_dist/custom.so"
}

其中type是接入的类型

type 类型
1 plugin
2 shared library
3 script
4 API
3.1 Golang Plugins

plugin/example包中给出了一个完整的plugin handler接入样例。

样例实现的是一个将本地命令原封不动放到远程执行的handler。

3.1.1 自定义实现
3.1.1.1 pre-work

pre-work接收完整的booster启动指令参数集,在这个场景里我们没有需要实现的。

func (c *Example) PreWork(dcType.BoosterConfig) error {
	return nil
}
3.1.1.2 post-work

post-work同上,在这个场景里没有需要实现的。

func (c *Example) PostWork(dcType.BoosterConfig) error {
	return nil
}
3.1.1.3 pre-load hook config

pre-load hook config负责从默认配置文件bk_custom_example_rules.json中读取hook信息,并返回hook配置。

const (
	hookConfigPath = "bk_custom_example_rules.json"
)

func (c *Example) GetPreloadConfig(dcType.BoosterConfig) (*dcSDK.PreloadConfig, error) {
	return getPreloadConfig(dcConfig.GetFile(hookConfigPath))
}

func getPreloadConfig(configPath string) (*dcSDK.PreloadConfig, error) {
	f, err := os.Open(configPath)
	if err != nil {
		return nil, err
	}
	defer func() {
		_ = f.Close()
	}()

	var pConfig dcSDK.PreloadConfig
	if err = codec.DecJSONReader(f, &pConfig); err != nil {
		return nil, err
	}

	return &pConfig, nil
}

3.1.1.4 pre-execute

pre-execute获得sub-work的命令行参数,并决定如何在远程执行

func (c *Example) PreExecute(command []string) (*dcSDK.BKDistCommand, error) {
	if len(command) < 1 {
		return nil, fmt.Errorf("invalid command and pararms")
	}

	return &dcSDK.BKDistCommand{
		Commands: []dcSDK.BKCommand{{
			ExeName: command[0],
			Params:  command[1:],
		}},
	}, nil
}

在这个场景里,我们原封不动地将命令组装起来即可,不需要额外发送、接收文件,远程的标准输出/标准错误会直接返回到本地。

3.1.1.5 post-execute

post-execute获得sub-work在远程执行的结果,并决定最终的结果。在这个场景中,只要远程的执行返回码为0,我们就认为成功了。

func (c *Example) PostExecute(result *dcSDK.BKDistResult) error {
	if result != nil && len(result.Results) > 0 && result.Results[0].RetCode == 0 {
		return nil
	}

	return fmt.Errorf("remote execute error")
}
3.1.1.6 final-execute

final-execute在这个场景中无需做什么。

func (c *Example) FinalExecute([]string) {
}
3.1.2 使用

可以采用以下命令编译

CGO_ENABLED=1 go build -buildmode=plugin -o custom-plugin.so ./example/example.go

并获取plugin handler:custom-plugin.so

使用时,将custom-plugin.so放在/etc/bk_dist/custom.so

指定custom信息

export BK_DIST_CUSTOM_SETTINGS="{\"type\": 1, \"path\":\"/etc/bk_dist/custom-plugin.so\"}"

同时写入hook配置/etc/bk_dist/bk_custom_example_rules.json

{
    "hooks":[
        {"src_command":"cat","target_command":"/usr/local/bin/bk-dist-executor $SRC_CMD"}
    ]
}

这样就能够hook住脚本中的cat命令,然后下载对应版本的tbs工具套件,执行bk-booster,指定-bt(booster type)为custom

bk-booster -bt custom -p TMPcustomtest -a "cat /etc/resolv.conf" -t --hook

即可实现一个cat远程机器文件的自定义任务。

image

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func NewCustom

func NewCustom() (handler.Handler, error)

NewCustom get a new custom handler

Types

type Custom

type Custom struct {
	// contains filtered or unexported fields
}

Custom 定义一个总的custom handler, 转发actions到具体的实现上

func (*Custom) FinalExecute

func (c *Custom) FinalExecute(command []string)

FinalExecute 收尾工作, 无论如何都会执行的步骤, 例如清理临时文件

func (*Custom) GetFilterRules

func (c *Custom) GetFilterRules() ([]dcSDK.FilterRuleItem, error)

GetFilterRules 获取filter rules配置, 用来决定文件分发的策略

func (*Custom) GetPreloadConfig

func (c *Custom) GetPreloadConfig(config dcType.BoosterConfig) (*dcSDK.PreloadConfig, error)

GetPreloadConfig 获取preload配置, 用来决定hook的对象和处理方法

func (*Custom) InitExtra

func (c *Custom) InitExtra(extra []byte)

InitExtra 用来解析从project拿到的extra信息, 详情参见: disttask.CustomData

func (*Custom) InitSandbox

func (c *Custom) InitSandbox(sandbox *dcSyscall.Sandbox)

InitSandbox 在执行每个具体任务之前, 都会传入一个当前的执行环境sandbox

func (*Custom) LocalExecute

func (c *Custom) LocalExecute(command []string) (int, error)

LocalExecute 自定义本地执行

func (*Custom) LocalExecuteNeed

func (c *Custom) LocalExecuteNeed(command []string) bool

LocalExecuteNeed 决定是否要自定义本地执行的内容

func (*Custom) LocalLockWeight

func (c *Custom) LocalLockWeight(command []string) int32

LocalLockWeight decide local-execute lock weight, default 1

func (*Custom) NeedRemoteResource

func (c *Custom) NeedRemoteResource(command []string) bool

NeedRemoteResource check whether this command need remote resource

func (*Custom) OnRemoteFail

func (c *Custom) OnRemoteFail(command []string) (*dcSDK.BKDistCommand, error)

OnRemoteFail give chance to try other way if failed to remote execute

func (*Custom) PostExecute

func (c *Custom) PostExecute(result *dcSDK.BKDistResult) error

PostExecute 单个任务的后置处理, 需要处理远程任务执行的结果

func (*Custom) PostExecuteNeedLock

func (c *Custom) PostExecuteNeedLock(result *dcSDK.BKDistResult) bool

PostExecuteNeedLock 决定是否需要在执行PostExecute之前获取一个post-lock

func (*Custom) PostLockWeight

func (c *Custom) PostLockWeight(result *dcSDK.BKDistResult) int32

PostLockWeight decide post-execute lock weight, default 1

func (*Custom) PostWork

func (c *Custom) PostWork(config *dcType.BoosterConfig) error

PostWork 处理整个任务的后置工作, 如缓存命中率统计

func (*Custom) PreExecute

func (c *Custom) PreExecute(command []string) (*dcSDK.BKDistCommand, error)

PreExecute 单个任务的预处理, 如c/c++编译的pre-process, 决定了分发到远程处理的任务信息

func (*Custom) PreExecuteNeedLock

func (c *Custom) PreExecuteNeedLock(command []string) bool

PreExecuteNeedLock 决定是否需要在执行PreExecute之前获取一个pre-lock

func (*Custom) PreLockWeight

func (c *Custom) PreLockWeight(command []string) int32

PreLockWeight decide pre-execute lock weight, default 1

func (*Custom) PreWork

func (c *Custom) PreWork(config *dcType.BoosterConfig) error

PreWork 处理整个任务的前置工作, 如工作空间初始化

func (*Custom) RemoteRetryTimes

func (c *Custom) RemoteRetryTimes() int

RemoteRetryTimes will return the remote retry times

func (*Custom) RenderArgs

func (c *Custom) RenderArgs(config dcType.BoosterConfig, originArgs string) string

RenderArgs 在执行整个任务的指令之前, 会传入原始任务, 允许handler修改

func (*Custom) ResultExtra

func (c *Custom) ResultExtra() []byte

ResultExtra 用来生成在结束后需要上传的extra信息

type Settings

type Settings struct {
	T    Type   `json:"type"`
	Path string `json:"path"`
}

Settings 定义了custom配置, 决定使用哪种加载方式, 以及目标库的位置

type Type

type Type int
const (
	TypeUnknown Type = iota
	TypePlugin
	TypeSharedLibrary
	TypeScript
	TypeAPI
)

func (Type) String

func (t Type) String() string

String return string of Custom Type

Directories

Path Synopsis

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL