fix: rebuild MES as compilable go-zero+ent backend (renamed bj_power_mes), restore 3 workstation projects from pristine original, align naming; all Go projects go build clean
This commit is contained in:
@@ -0,0 +1,52 @@
|
||||
package station
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"time"
|
||||
)
|
||||
|
||||
// CleaningLineStation 清洗线(machineID=8),实现 PreLoadStation。
|
||||
type CleaningLineStation struct {
|
||||
ctrl RobotCleanLineController
|
||||
machineID int
|
||||
}
|
||||
|
||||
func NewCleaningLineStation(ctrl RobotCleanLineController, machineID int) *CleaningLineStation {
|
||||
return &CleaningLineStation{ctrl: ctrl, machineID: machineID}
|
||||
}
|
||||
|
||||
func (s *CleaningLineStation) Load(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.PlaceWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *CleaningLineStation) Unload(ctx context.Context, wt int, machineSlot int, dstTempSlot int) (int, error) {
|
||||
return dstTempSlot, s.ctrl.FetchWorkpieceFromMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *CleaningLineStation) Exchange(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.ExchangeWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *CleaningLineStation) PreLoad(ctx context.Context) error {
|
||||
if err := s.ctrl.RequestCleaningLoading(ctx); err != nil {
|
||||
return fmt.Errorf("load_cleaning: request cleaning loading: %w", err)
|
||||
}
|
||||
if err := s.ctrl.WaitCleaningReady(ctx); err != nil {
|
||||
return fmt.Errorf("load_cleaning: wait cleaning ready: %w", err)
|
||||
}
|
||||
time.Sleep(2 * time.Second)
|
||||
|
||||
isDone, err := s.ctrl.IsCleanLineDone(ctx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if isDone {
|
||||
return ErrActionCancelled
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *CleaningLineStation) PostLoad(ctx context.Context) error {
|
||||
return s.ctrl.CloseRequestCleaningLoading(ctx)
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package station
|
||||
|
||||
import "context"
|
||||
|
||||
// DeburrStation 去毛刺机(machineID=7),通用 Load/Exchange,下料暂存台+8偏移。
|
||||
type DeburrStation struct {
|
||||
ctrl RobotPlacerFetcher
|
||||
machineID int
|
||||
}
|
||||
|
||||
func NewDeburrStation(ctrl RobotPlacerFetcher, machineID int) *DeburrStation {
|
||||
return &DeburrStation{ctrl: ctrl, machineID: machineID}
|
||||
}
|
||||
|
||||
func (s *DeburrStation) Load(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.PlaceWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *DeburrStation) Unload(ctx context.Context, wt int, machineSlot int, dstTempSlot int) (int, error) {
|
||||
return dstTempSlot + 8, s.ctrl.FetchWorkpieceFromMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *DeburrStation) Exchange(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.ExchangeWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
package station
|
||||
|
||||
import "bj_power_mes/constants"
|
||||
|
||||
// NewByType 根据设备类型码创建对应的 Station 实现。
|
||||
// 返回 nil 表示该设备不需要 Station(如 TEMP_STORE、ROBOT)。
|
||||
func NewByType(typeCode constants.EquipmentTypeCode, machineID int, ctrl any) Station {
|
||||
if ctrl == nil {
|
||||
return nil
|
||||
}
|
||||
switch typeCode {
|
||||
case constants.EquipmentTypeCode_CleaningLine:
|
||||
return NewCleaningLineStation(ctrl.(RobotCleanLineController), machineID)
|
||||
case constants.EquipmentTypeCode_Deburr:
|
||||
return NewDeburrStation(ctrl.(RobotPlacerFetcher), machineID)
|
||||
case constants.EquipmentTypeCode_Inspection:
|
||||
return NewRollingLineStation(ctrl.(RobotPlacerFetcher), machineID)
|
||||
case constants.EquipmentTypeCode_Sampling:
|
||||
return NewSamplingStation(ctrl.(RobotPlacerFetcher), machineID)
|
||||
case constants.EquipmentTypeCode_WashingMachine:
|
||||
// FANUC 配置由 buildStations 注入(见 processor/factory.go),此处传 nil
|
||||
return NewWasherStation(ctrl.(RobotWasherController), machineID, nil)
|
||||
case constants.EquipmentTypeCode_Marking:
|
||||
return NewGenericStation(ctrl.(RobotPlacerFetcher), machineID)
|
||||
default:
|
||||
// CNC 等其他类型使用通用 Station
|
||||
return NewGenericStation(ctrl.(RobotPlacerFetcher), machineID)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,17 @@
|
||||
package station
|
||||
|
||||
import "context"
|
||||
|
||||
// FanucOption FANUC 宏变量写入配置(高压清洗机放料前先写 #666/#888 再发 PLC 命令)。
|
||||
type FanucOption struct {
|
||||
// WriteMacro 写宏变量(macroNo: 666 左工位 / 888 右工位,value: 清洗机组号 1~9)
|
||||
WriteMacro func(ctx context.Context, macroNo int, value float64) error
|
||||
// GroupNo 查询工单零件号对应的清洗机组号(jobID → washerGroupNo)
|
||||
GroupNo func(ctx context.Context, jobID int) (int, error)
|
||||
}
|
||||
|
||||
// PreLoadFanucStation 放料前需先写 FANUC 宏变量的工站(高压清洗机)。
|
||||
// 调用时机:AllocateSlot 之后、Station.Load(PLC 放料命令)之前。
|
||||
type PreLoadFanucStation interface {
|
||||
PreLoadFanuc(ctx context.Context, jobID, machineSlot int) error
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package station
|
||||
|
||||
import "context"
|
||||
|
||||
// GenericStation 通用设备(CNC 等),使用 Place/Fetch/ExchangeWorkpieceToMachine。
|
||||
type GenericStation struct {
|
||||
ctrl RobotPlacerFetcher
|
||||
machineID int
|
||||
}
|
||||
|
||||
func NewGenericStation(ctrl RobotPlacerFetcher, machineID int) *GenericStation {
|
||||
return &GenericStation{ctrl: ctrl, machineID: machineID}
|
||||
}
|
||||
|
||||
func (s *GenericStation) Load(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.PlaceWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *GenericStation) Unload(ctx context.Context, wt int, machineSlot int, dstTempSlot int) (int, error) {
|
||||
return dstTempSlot, s.ctrl.FetchWorkpieceFromMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *GenericStation) Exchange(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.ExchangeWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package station
|
||||
|
||||
import "context"
|
||||
|
||||
// RollingLineStation 滚轧线/内窥镜检测线(machineID=6),PLC 不接受 slot 参数。
|
||||
type RollingLineStation struct {
|
||||
ctrl RobotPlacerFetcher
|
||||
machineID int
|
||||
}
|
||||
|
||||
func NewRollingLineStation(ctrl RobotPlacerFetcher, machineID int) *RollingLineStation {
|
||||
return &RollingLineStation{ctrl: ctrl, machineID: machineID}
|
||||
}
|
||||
|
||||
func (s *RollingLineStation) Load(ctx context.Context, wt int, _ int) error {
|
||||
return s.ctrl.PlaceWorkpieceToRollingLine(ctx, wt)
|
||||
}
|
||||
|
||||
func (s *RollingLineStation) Unload(ctx context.Context, wt int, _ int, dstTempSlot int) (int, error) {
|
||||
return dstTempSlot, s.ctrl.FetchWorkpieceFromRollingLine(ctx, wt)
|
||||
}
|
||||
|
||||
func (s *RollingLineStation) Exchange(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.ExchangeWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package station
|
||||
|
||||
import "context"
|
||||
|
||||
// SamplingStation 抽检台(machineID=9),PLC 不接受 slot 参数,下料暂存台+8偏移。
|
||||
type SamplingStation struct {
|
||||
ctrl RobotPlacerFetcher
|
||||
machineID int
|
||||
}
|
||||
|
||||
func NewSamplingStation(ctrl RobotPlacerFetcher, machineID int) *SamplingStation {
|
||||
return &SamplingStation{ctrl: ctrl, machineID: machineID}
|
||||
}
|
||||
|
||||
func (s *SamplingStation) Load(ctx context.Context, wt int, _ int) error {
|
||||
return s.ctrl.PlaceWorkpieceToSamplingStation(ctx, wt)
|
||||
}
|
||||
|
||||
func (s *SamplingStation) Unload(ctx context.Context, wt int, _ int, dstTempSlot int) (int, error) {
|
||||
return dstTempSlot + 8, s.ctrl.FetchWorkpieceFromSamplingStation(ctx, wt)
|
||||
}
|
||||
|
||||
func (s *SamplingStation) Exchange(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.ExchangeWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
@@ -0,0 +1,97 @@
|
||||
package station
|
||||
|
||||
import (
|
||||
"context"
|
||||
"errors"
|
||||
)
|
||||
|
||||
// Station 封装设备特定的机器人取放操作。
|
||||
// RobotWorker 委托给 Station 而非 switch machineID。
|
||||
type Station interface {
|
||||
// Load 将工件放入该工站设备。
|
||||
Load(ctx context.Context, wt int, machineSlot int) error
|
||||
|
||||
// Unload 从该工站设备取出工件。返回调整后的暂存台目标槽位号。
|
||||
Unload(ctx context.Context, wt int, machineSlot int, dstTempSlot int) (adjustedTempSlot int, err error)
|
||||
|
||||
// Exchange 换料:取出卸料工件同时放入上料工件。
|
||||
Exchange(ctx context.Context, wt int, machineSlot int) error
|
||||
}
|
||||
|
||||
// PreLoadStation 需要上料前 PLC 握手的工站(清洗线)。
|
||||
type PreLoadStation interface {
|
||||
Station
|
||||
PreLoad(ctx context.Context) error // Load 前调用(请求料盘→等待就绪→检查Done)
|
||||
PostLoad(ctx context.Context) error // Load 后 defer 调用(关闭请求信号)
|
||||
}
|
||||
|
||||
// StartupStation 需要启动命令的工站(高压清洗机)。
|
||||
type StartupStation interface {
|
||||
Station
|
||||
Startup(ctx context.Context) error
|
||||
}
|
||||
|
||||
// BatchUnloadStation 支持批量卸料的工站(高压清洗机多槽位同时 Done)。
|
||||
type BatchUnloadStation interface {
|
||||
Station
|
||||
BatchUnload(ctx context.Context, wt int, slots []BatchSlot, releaser SlotReleaser) error
|
||||
}
|
||||
|
||||
// SlotReleaser 槽位释放窄接口(由 actor.MachineActor 满足)。
|
||||
type SlotReleaser interface {
|
||||
ReleaseSlot(slotNo int)
|
||||
}
|
||||
|
||||
// BatchSlot 批量卸料的单个槽位参数。
|
||||
type BatchSlot struct {
|
||||
JobID int
|
||||
SlotNo int
|
||||
TempSlot int
|
||||
}
|
||||
|
||||
// ErrActionCancelled 清洗线检测到 Done 工件,需重新调度为 Exchange。
|
||||
var ErrActionCancelled = errors.New("action cancelled: re-schedule")
|
||||
|
||||
// --- robotController 窄接口子集 ---
|
||||
|
||||
// RobotPlacer 机器人放料操作。
|
||||
type RobotPlacer interface {
|
||||
PlaceWorkpieceToMachine(ctx context.Context, wt int, machineID int, slot ...int) error
|
||||
PlaceWorkpieceToRollingLine(ctx context.Context, wt int) error
|
||||
PlaceWorkpieceToSamplingStation(ctx context.Context, wt int) error
|
||||
PlaceWorkpieceToTempStation(ctx context.Context, wt int, slot int) error
|
||||
}
|
||||
|
||||
// RobotFetcher 机器人取料操作。
|
||||
type RobotFetcher interface {
|
||||
FetchWorkpieceFromMachine(ctx context.Context, wt int, machineID int, slot ...int) error
|
||||
FetchWorkpieceFromRollingLine(ctx context.Context, wt int) error
|
||||
FetchWorkpieceFromSamplingStation(ctx context.Context, wt int) error
|
||||
}
|
||||
|
||||
// RobotExchanger 机器人换料操作。
|
||||
type RobotExchanger interface {
|
||||
ExchangeWorkpieceToMachine(ctx context.Context, wt int, machineID int, slot ...int) error
|
||||
}
|
||||
|
||||
// RobotPlacerFetcher 组合接口。
|
||||
type RobotPlacerFetcher interface {
|
||||
RobotPlacer
|
||||
RobotFetcher
|
||||
RobotExchanger
|
||||
}
|
||||
|
||||
// RobotCleanLineController 清洗线 PLC 操作。
|
||||
type RobotCleanLineController interface {
|
||||
RobotPlacerFetcher
|
||||
RequestCleaningLoading(ctx context.Context) error
|
||||
WaitCleaningReady(ctx context.Context) error
|
||||
IsCleanLineDone(ctx context.Context) (bool, error)
|
||||
CloseRequestCleaningLoading(ctx context.Context) error
|
||||
}
|
||||
|
||||
// RobotWasherController 清洗机 PLC 操作。
|
||||
type RobotWasherController interface {
|
||||
RobotPlacerFetcher
|
||||
StartupWasher(ctx context.Context) error
|
||||
}
|
||||
@@ -0,0 +1,80 @@
|
||||
package station
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"log/slog"
|
||||
)
|
||||
|
||||
// WasherStation 高压清洗机,实现 StartupStation + BatchUnloadStation + PreLoadFanucStation。
|
||||
type WasherStation struct {
|
||||
ctrl RobotWasherController
|
||||
machineID int
|
||||
fanuc *FanucOption
|
||||
}
|
||||
|
||||
func NewWasherStation(ctrl RobotWasherController, machineID int, fanuc *FanucOption) *WasherStation {
|
||||
return &WasherStation{ctrl: ctrl, machineID: machineID, fanuc: fanuc}
|
||||
}
|
||||
|
||||
// PreLoadFanuc 放料前写 FANUC 宏变量:槽位1 → #666,槽位2 → #888(值=清洗机组号 1~9)。
|
||||
// 需求:发送 PLC 放料命令前必须先通过 FANUC 写入组号,清洗机 CNC 按宏变量选择子程序。
|
||||
// 未配置 FANUC 写入(设备 ipAddress 为空)或查不到组号时跳过并记录警告,不阻塞流程。
|
||||
func (s *WasherStation) PreLoadFanuc(ctx context.Context, jobID, machineSlot int) error {
|
||||
if s.fanuc == nil || s.fanuc.WriteMacro == nil {
|
||||
return nil
|
||||
}
|
||||
var macroNo int
|
||||
switch machineSlot {
|
||||
case 1:
|
||||
macroNo = 666
|
||||
case 2:
|
||||
macroNo = 888
|
||||
default:
|
||||
return fmt.Errorf("washer fanuc: invalid machine slot %d (expected 1 or 2)", machineSlot)
|
||||
}
|
||||
groupNo, err := s.fanuc.GroupNo(ctx, jobID)
|
||||
if err != nil {
|
||||
slog.Warn("washer fanuc: group no lookup failed, skip macro write", "jobId", jobID, "error", err)
|
||||
return nil
|
||||
}
|
||||
if groupNo < 1 || groupNo > 9 {
|
||||
slog.Warn("washer fanuc: group no out of range, skip macro write", "jobId", jobID, "groupNo", groupNo)
|
||||
return nil
|
||||
}
|
||||
if err := s.fanuc.WriteMacro(ctx, macroNo, float64(groupNo)); err != nil {
|
||||
return fmt.Errorf("washer fanuc: write macro #%d=%d for job %d failed: %w", macroNo, groupNo, jobID, err)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *WasherStation) Load(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.PlaceWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *WasherStation) Unload(ctx context.Context, wt int, machineSlot int, dstTempSlot int) (int, error) {
|
||||
return dstTempSlot, s.ctrl.FetchWorkpieceFromMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *WasherStation) Exchange(ctx context.Context, wt int, machineSlot int) error {
|
||||
return s.ctrl.ExchangeWorkpieceToMachine(ctx, wt, s.machineID, machineSlot)
|
||||
}
|
||||
|
||||
func (s *WasherStation) Startup(ctx context.Context) error {
|
||||
return s.ctrl.StartupWasher(ctx)
|
||||
}
|
||||
|
||||
func (s *WasherStation) BatchUnload(ctx context.Context, wt int, slots []BatchSlot, releaser SlotReleaser) error {
|
||||
for _, js := range slots {
|
||||
if err := s.ctrl.FetchWorkpieceFromMachine(ctx, wt, s.machineID, js.SlotNo); err != nil {
|
||||
return fmt.Errorf("batch_unload: fetch from slot %d: %w", js.SlotNo, err)
|
||||
}
|
||||
releaser.ReleaseSlot(js.SlotNo)
|
||||
if js.TempSlot > 0 {
|
||||
if err := s.ctrl.PlaceWorkpieceToTempStation(ctx, wt, js.TempSlot); err != nil {
|
||||
return fmt.Errorf("batch_unload: place to temp slot %d: %w", js.TempSlot, err)
|
||||
}
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
Reference in New Issue
Block a user