github.com/wfusion/gofusion@v1.1.14/common/infra/watermill/pubsub/redis/marshaller.go (about)

     1  package redis
     2  
     3  import (
     4  	"github.com/pkg/errors"
     5  	"github.com/vmihailenco/msgpack/v5"
     6  	"github.com/wfusion/gofusion/common/infra/watermill"
     7  
     8  	"github.com/wfusion/gofusion/common/infra/watermill/message"
     9  )
    10  
    11  const UUIDHeaderKey = "_watermill_message_uuid"
    12  
    13  type Marshaller interface {
    14  	Marshal(topic string, msg *message.Message) (map[string]any, error)
    15  }
    16  
    17  type Unmarshaller interface {
    18  	Unmarshal(values map[string]any) (msg *message.Message, err error)
    19  }
    20  
    21  type MarshallerUnmarshaller interface {
    22  	Marshaller
    23  	Unmarshaller
    24  }
    25  
    26  type DefaultMarshallerUnmarshaller struct {
    27  	AppID string
    28  }
    29  
    30  func (d DefaultMarshallerUnmarshaller) Marshal(_ string, msg *message.Message) (map[string]any, error) {
    31  	if value := msg.Metadata.Get(UUIDHeaderKey); value != "" {
    32  		return nil, errors.Errorf("metadata %s is reserved by watermill for message UUID", UUIDHeaderKey)
    33  	}
    34  
    35  	var (
    36  		md  []byte
    37  		err error
    38  	)
    39  
    40  	msg.Metadata[watermill.MessageHeaderAppID] = d.AppID
    41  	if len(msg.Metadata) > 0 {
    42  		if md, err = msgpack.Marshal(msg.Metadata); err != nil {
    43  			return nil, errors.Wrapf(err, "marshal metadata fail")
    44  		}
    45  	}
    46  
    47  	return map[string]any{
    48  		UUIDHeaderKey:                msg.UUID,
    49  		watermill.MessageHeaderAppID: d.AppID,
    50  		"metadata":                   md,
    51  		"payload":                    []byte(msg.Payload),
    52  	}, nil
    53  }
    54  
    55  func (DefaultMarshallerUnmarshaller) Unmarshal(values map[string]any) (msg *message.Message, err error) {
    56  	msg = message.NewMessage(values[UUIDHeaderKey].(string), []byte(values["payload"].(string)))
    57  
    58  	mdv, ok1 := values["metadata"]
    59  	mds, ok2 := mdv.(string)
    60  	if ok1 && ok2 && mds != "" {
    61  		metadata := make(message.Metadata)
    62  		if err := msgpack.Unmarshal([]byte(mds), &metadata); err != nil {
    63  			return nil, errors.Wrapf(err, "unmarshal metadata fail")
    64  		}
    65  		msg.Metadata = metadata
    66  	}
    67  
    68  	return msg, nil
    69  }