go: Deadline Pattern

项目结构:

Go 复制代码
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:41
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : logger.go
*/
package common
 
import (
    "fmt"
    "log"
    "os"
    "time"
)
 
// 自定义Logger结构体,配套Info/Error方法
type Logger struct {
    name   string
    logger *log.Logger
}
 
// 格式化时间:2006-01-02 15:04:05,000
func formatNow() string {
    return time.Now().Format("2006-01-02 15:04:05,000")
}
 
// GetLogger 获取模块日志实例
func GetLogger(name string) *Logger {
    return &Logger{
        name:   name,
        logger: log.New(os.Stdout, "", 0),
    }
}
 
func (l *Logger) Info(msg string) {
    t := formatNow()
    line := fmt.Sprintf("%s | INFO | %s | %s", t, l.name, msg)
    l.logger.Println(line)
}
 
func (l *Logger) Error(msg string) {
    t := formatNow()
    line := fmt.Sprintf("%s | ERROR | %s | %s", t, l.name, msg)
    l.logger.Println(line)
}
 
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:41
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : exception.go
*/
package common
 
import "errors"
 
var ServiceTimeoutErr = errors.New("任务超时,已终止等待")
var ServiceInvokeErr = errors.New("服务调用异常")
 
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:55
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : deadlinebll.go
*/
package bll
 
import (
    "fmt"
    "godesginpattern/deadline/common"
    "godesginpattern/deadline/config"
    "godesginpattern/deadline/core"
    "godesginpattern/deadline/domain"
    "math/rand"
    "time"
)
 
func DeadlineMain() {
    rand.Seed(time.Now().UnixNano())
    fmt.Println("===== 展示【Deadline Pattern(截止期限模式)】示例 =====")
 
    logger := common.GetLogger("DeadlineBll")
    logger.Info("=== 珠宝定制系统启动 ===")
 
    orderID := fmt.Sprintf("%s_%d", config.OrderIDPrefix, rand.Intn(9000)+1000)
    order := &domain.JewelryOrder{OrderID: orderID}
    logger.Info(fmt.Sprintf("订单创建:%+v", order))
 
    manager := core.NewJewelryWorkflowManager()
    final := manager.Run(order)
 
    logger.Info("============================================================")
    logger.Info(fmt.Sprintf("最终订单状态:%+v", final))
    logger.Info("=== 系统运行完成 ===")
}
 
 
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:42
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : deadline.go
*/
package common
 
import (
    "time"
)
 
type DeadlineExecutor[T any] struct {
    Timeout time.Duration
}
 
func NewDeadlineExecutor[T any](timeoutSec int) *DeadlineExecutor[T] {
    return &DeadlineExecutor[T]{Timeout: time.Duration(timeoutSec) * time.Second}
}
 
func (d *DeadlineExecutor[T]) Execute(fn func() T) (T, error) {
    ch := make(chan T, 1)
    go func() {
        ch <- fn()
    }()
 
    select {
    case res := <-ch:
        return res, nil
    case <-time.After(d.Timeout):
        var zero T
        return zero, ServiceTimeoutErr
    }
}
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:42
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : config.go
*/
package config
 
const (
    GemIdentifyTimeoutSeconds = 3
    OrderIDPrefix             = "JEWELRY_ORDER"
)
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:42
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : models.go
*/
package domain
 
type GemIdentifyResult struct {
    GemType    string
    Carat      float64
    Color      string
    Clarity    string
    IdentifyNo string
}
 
type JewelryOrder struct {
    OrderID          string
    IdentifyResult   *GemIdentifyResult
    MaterialApproved bool
    ProduceFinished  bool
    QualityPassed    bool
    Delivered        bool
}
Go 复制代码
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:43
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : gem_identify.go
*/
package external
 
import (
    "fmt"
    "godesginpattern/deadline/common"
    "godesginpattern/deadline/domain"
    "math/rand"
    "time"
)
 
type GemIdentifyService struct{}
 
func NewGemIdentifyService() *GemIdentifyService {
    return &GemIdentifyService{}
}
 
func (g *GemIdentifyService) Identify() *domain.GemIdentifyResult {
    log := common.GetLogger("GemIdentifyService")
    log.Info("开始调用第三方宝石鉴定服务...")
 
    // 50%快速 1s,50%阻塞10s触发超时
    delay := 1
    if rand.Float64() < 0.5 {
        delay = 10
    }
    time.Sleep(time.Duration(delay) * time.Second)
 
    identifyNo := "GEM_" + randStr(6)
    res := &domain.GemIdentifyResult{
        GemType:    "钻石",
        Carat:      1.0,
        Color:      "D",
        Clarity:    "VVS1",
        IdentifyNo: identifyNo,
    }
    log.Info(fmt.Sprintf("鉴定完成:%+v", res))
    return res
}
 
func randStr(n int) string {
    letters := []rune("0123456789")
    b := make([]rune, n)
    for i := range b {
        b[i] = letters[rand.Intn(len(letters))]
    }
    return string(b)
}
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:43
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : material.go
*/
package internal
 
type MaterialService struct{}
 
func NewMaterialService() *MaterialService {
    return &MaterialService{}
}
 
func (m *MaterialService) Approve() bool {
    return true
}
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:45
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : produce.go
*/
package internal
 
type ProduceService struct{}
 
func NewProduceService() *ProduceService { return &ProduceService{} }
func (p *ProduceService) Produce() bool  { return true }
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:45
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : quality.go
*/
package internal
 
type QualityService struct{}
 
func NewQualityService() *QualityService { return &QualityService{} }
func (q *QualityService) Check() bool    { return true }
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:46
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : deliver.go
*/
package internal
 
type DeliverService struct{}
 
func NewDeliverService() *DeliverService { return &DeliverService{} }
func (d *DeliverService) Deliver() bool  { return true }
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 22:08
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : facade.go
*/
package service
 
import (
    "godesginpattern/deadline/service/internal"
)
 
// 对外导出服务实例,core只能导入service,不能碰internal   门面层(统一暴露内部服务)
type ServiceFacade struct {
    Material *internal.MaterialService
    Produce  *internal.ProduceService
    Quality  *internal.QualityService
    Deliver  *internal.DeliverService
}
 
func NewServiceFacade() *ServiceFacade {
    return &ServiceFacade{
        Material: internal.NewMaterialService(),
        Produce:  internal.NewProduceService(),
        Quality:  internal.NewQualityService(),
        Deliver:  internal.NewDeliverService(),
    }
}
 
 
 
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:46
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : workflow_manager.go
*/
package core
 
import (
    "godesginpattern/deadline/common"
    "godesginpattern/deadline/config"
    "godesginpattern/deadline/domain"
    "godesginpattern/deadline/service"
    "godesginpattern/deadline/service/external"
)
 
type JewelryWorkflowManager struct {
    identify *external.GemIdentifyService
    facade   *service.ServiceFacade // 使用门面层
    logger   *common.Logger
}
 
func NewJewelryWorkflowManager() *JewelryWorkflowManager {
    return &JewelryWorkflowManager{
        identify: external.NewGemIdentifyService(),
        facade:   service.NewServiceFacade(),
        logger:   common.GetLogger("WorkflowManager"),
    }
}
 
func (j *JewelryWorkflowManager) Run(order *domain.JewelryOrder) *domain.JewelryOrder {
    j.logger.Info("开始执行订单全流程:" + order.OrderID)
 
    executor := common.NewDeadlineExecutor[*domain.GemIdentifyResult](config.GemIdentifyTimeoutSeconds)
    res, err := executor.Execute(j.identify.Identify)
 
    if err != nil {
        deadlineLog := common.GetLogger("DeadlinePattern")
        deadlineLog.Error("任务超时,已终止等待,超时=3s")
        j.logger.Error("鉴定超时,启动人工复核兜底流程")
    } else {
        order.IdentifyResult = res
    }
 
    mLog := common.GetLogger("MaterialService")
    mLog.Info("原料采购审核中...")
    order.MaterialApproved = j.facade.Material.Approve()
 
    pLog := common.GetLogger("ProduceService")
    pLog.Info("工厂加工生产完成")
    order.ProduceFinished = j.facade.Produce.Produce()
 
    qLog := common.GetLogger("QualityService")
    qLog.Info("成品质检合格")
    order.QualityPassed = j.facade.Quality.Check()
 
    dLog := common.GetLogger("DeliverService")
    dLog.Info("订单已交付")
    order.Delivered = j.facade.Deliver.Deliver()
 
    j.logger.Info("订单全流程执行完成:" + order.OrderID)
    return order
}
 
/*
workflow_manager.go 放在Server包时用。
type JewelryWorkflowManager struct {
    identify *external.GemIdentifyService
    material *internal.MaterialService
    produce  *internal.ProduceService
    quality  *internal.QualityService
    deliver  *internal.DeliverService
    logger   *common.Logger // 现在 common.Logger 已定义,编译正常
}
 
func NewJewelryWorkflowManager() *JewelryWorkflowManager {
    return &JewelryWorkflowManager{
        identify: external.NewGemIdentifyService(),
        material: internal.NewMaterialService(),
        produce:  internal.NewProduceService(),
        quality:  internal.NewQualityService(),
        deliver:  internal.NewDeliverService(),
        logger:   common.GetLogger("WorkflowManager"),
    }
}
 
func (j *JewelryWorkflowManager) Run(order *domain.JewelryOrder) *domain.JewelryOrder {
    j.logger.Info("开始执行订单全流程:" + order.OrderID)
 
    executor := common.NewDeadlineExecutor[*domain.GemIdentifyResult](config.GemIdentifyTimeoutSeconds)
    res, err := executor.Execute(j.identify.Identify)
 
    if err != nil {
        // 独立DeadlinePattern日志输出超时ERROR
        deadlineLog := common.GetLogger("DeadlinePattern")
        deadlineLog.Error("任务超时,已终止等待,超时=3s")
        j.logger.Error("鉴定超时,启动人工复核兜底流程")
    } else {
        order.IdentifyResult = res
    }
 
    // 各内部服务单独打印日志
    mLog := common.GetLogger("MaterialService")
    mLog.Info("原料采购审核中...")
    order.MaterialApproved = j.material.Approve()
 
    pLog := common.GetLogger("ProduceService")
    pLog.Info("工厂加工生产完成")
    order.ProduceFinished = j.produce.Produce()
 
    qLog := common.GetLogger("QualityService")
    qLog.Info("成品质检合格")
    order.QualityPassed = j.quality.Check()
 
    dLog := common.GetLogger("DeliverService")
    dLog.Info("订单已交付")
    order.Delivered = j.deliver.Deliver()
 
    j.logger.Info("订单全流程执行完成:" + order.OrderID)
    return order
}
*/
  

调用:

Go 复制代码
/*
# 版权所有  2026 ©涂聚文有限公司™ ®
# 许可信息查看:言語成了邀功盡責的功臣,還需要行爲每日來值班嗎
# 描述:Deadline Pattern 截止期限模式
# Author    : geovindu,Geovin Du 涂聚文.
# IDE       : goLang 2024.3.6 go 26.2
# os        : windows 10
# database  : mysql 9.0 sql server 2019, postgreSQL 17.0  Oracle 21c Neo4j
# Datetime  : 2026/6/29 21:55
# User      :  geovindu
# Product   : GoLand
# Project   : godesginpattern
# File      : deadlinebll.go
*/
package bll
 
import (
    "fmt"
    "godesginpattern/deadline/common"
    "godesginpattern/deadline/config"
    "godesginpattern/deadline/core"
    "godesginpattern/deadline/domain"
    "math/rand"
    "time"
)
 
func DeadlineMain() {
    rand.Seed(time.Now().UnixNano())
    fmt.Println("===== 展示【Deadline Pattern(截止期限模式)】示例 =====")
 
    logger := common.GetLogger("DeadlineBll")
    logger.Info("=== 珠宝定制系统启动 ===")
 
    orderID := fmt.Sprintf("%s_%d", config.OrderIDPrefix, rand.Intn(9000)+1000)
    order := &domain.JewelryOrder{OrderID: orderID}
    logger.Info(fmt.Sprintf("订单创建:%+v", order))
 
    manager := core.NewJewelryWorkflowManager()
    final := manager.Run(order)
 
    logger.Info("============================================================")
    logger.Info(fmt.Sprintf("最终订单状态:%+v", final))
    logger.Info("=== 系统运行完成 ===")
}
  

输出: