Golang如何将消息分割成多个部分

Golang如何将消息分割成多个部分 大家好,

我是Go语言的新手,如果能得到你们的指导,我将不胜感激:

这是formatter.go文件:

package formatters
import (
	"go.thethings.network/lorawan-stack/pkg/ttnpb"
)

// Formatter格式化上行和下行消息。
type Formatter interface {
	FromUp(*ttnpb.ApplicationUp) ([]byte, error)
	ToDownlinks([]byte) (*ttnpb.ApplicationDownlinks, error)
	ToDownlinkQueueRequest([]byte) (*ttnpb.DownlinkQueueRequest, error)
}

这是json.go文件:

package formatters

import (
	"go.thethings.network/lorawan-stack/pkg/jsonpb"
	"go.thethings.network/lorawan-stack/pkg/ttnpb"
)

type json struct {
}

func (json) FromUp(msg *ttnpb.ApplicationUp) ([]byte, error) {
	return jsonpb.TTN().Marshal(msg)
}

func (json) ToDownlinks(data []byte) (*ttnpb.ApplicationDownlinks, error) {
	res := &ttnpb.ApplicationDownlinks{}
	if err := jsonpb.TTN().Unmarshal(data, &res); err != nil {
		return nil, err
	}
	return res, nil
}

func (json) ToDownlinkQueueRequest(data []byte) (*ttnpb.DownlinkQueueRequest, error) {
	res := &ttnpb.DownlinkQueueRequest{}
	if err := jsonpb.TTN().Unmarshal(data, &res); err != nil {
		return nil, err
	}
	return res, nil
}

// JSON是使用JSON序列化的格式化器。
var JSON Formatter = &json{}

现在,我想在*ttnpb.ApplicationUp中返回[][]byte,而不仅仅是[]byte。我该如何实现呢? 提前非常感谢。


更多关于Golang如何将消息分割成多个部分的实战教程也可以访问 https://www.itying.com/category-94-b0.html

2 回复

我猜你希望在 FromUp 方法中返回 [][]byte 而不是 []byte。 你可以做的是分割返回的字节切片。你在问题中没有说明你想如何分割大小?你想要固定大小的切片吗?多大尺寸?还是你想要其他规则?

将切片分割成更小的切片很简单。考虑下面的代码,它将一个切片分割成固定大小(sz)的更小切片,最后一个除外。

func split(data []byte, sz int) [][]byte {
    var r = make([][]byte, 0, (len(data)+sz-1)/sz)
    var i int
    for i = 0; i+sz < len(data); i += sz {
        r = append(r, data[i:i+sz])
    }
    return append(r, data[i:])
}

更多关于Golang如何将消息分割成多个部分的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


根据你的需求,要在FromUp方法中返回[][]byte而不是[]byte,你需要修改Formatter接口和json结构体的实现。以下是具体的实现方式:

首先修改formatter.go中的接口定义:

package formatters

import (
	"go.thethings.network/lorawan-stack/pkg/ttnpb"
)

// Formatter格式化上行和下行消息。
type Formatter interface {
	FromUp(*ttnpb.ApplicationUp) ([][]byte, error)  // 修改返回类型为[][]byte
	ToDownlinks([]byte) (*ttnpb.ApplicationDownlinks, error)
	ToDownlinkQueueRequest([]byte) (*ttnpb.DownlinkQueueRequest, error)
}

然后修改json.go中的实现:

package formatters

import (
	"go.thethings.network/lorawan-stack/pkg/jsonpb"
	"go.thethings.network/lorawan-stack/pkg/ttnpb"
)

type json struct {
}

func (json) FromUp(msg *ttnpb.ApplicationUp) ([][]byte, error) {
	// 首先将消息序列化为JSON
	data, err := jsonpb.TTN().Marshal(msg)
	if err != nil {
		return nil, err
	}
	
	// 这里是一个示例:将数据分割成多个部分
	// 你可以根据实际需求调整分割逻辑
	chunkSize := 1024 // 每个部分的大小
	var chunks [][]byte
	
	for i := 0; i < len(data); i += chunkSize {
		end := i + chunkSize
		if end > len(data) {
			end = len(data)
		}
		chunks = append(chunks, data[i:end])
	}
	
	return chunks, nil
}

func (json) ToDownlinks(data []byte) (*ttnpb.ApplicationDownlinks, error) {
	res := &ttnpb.ApplicationDownlinks{}
	if err := jsonpb.TTN().Unmarshal(data, &res); err != nil {
		return nil, err
	}
	return res, nil
}

func (json) ToDownlinkQueueRequest(data []byte) (*ttnpb.DownlinkQueueRequest, error) {
	res := &ttnpb.DownlinkQueueRequest{}
	if err := jsonpb.TTN().Unmarshal(data, &res); err != nil {
		return nil, err
	}
	return res, nil
}

// JSON是使用JSON序列化的格式化器。
var JSON Formatter = &json{}

如果你需要基于消息内容进行更智能的分割,可以这样实现:

func (json) FromUp(msg *ttnpb.ApplicationUp) ([][]byte, error) {
	// 序列化整个消息
	data, err := jsonpb.TTN().Marshal(msg)
	if err != nil {
		return nil, err
	}
	
	// 根据消息类型或内容决定分割策略
	var chunks [][]byte
	
	// 示例1:固定大小分割
	// chunks = splitBySize(data, 1024)
	
	// 示例2:基于消息字段分割
	if msg.UplinkMessage != nil {
		// 处理上行消息的分割逻辑
		chunks = splitUplinkMessage(data)
	} else if msg.JoinAccept != nil {
		// 处理加入接受消息的分割逻辑
		chunks = splitJoinAccept(data)
	} else {
		// 默认分割方式
		chunks = [][]byte{data}
	}
	
	return chunks, nil
}

// 辅助函数:按大小分割
func splitBySize(data []byte, chunkSize int) [][]byte {
	var chunks [][]byte
	for i := 0; i < len(data); i += chunkSize {
		end := i + chunkSize
		if end > len(data) {
			end = len(data)
		}
		chunks = append(chunks, data[i:end])
	}
	return chunks
}

这样修改后,FromUp方法就会返回一个字节切片数组,每个元素代表消息的一个部分。你可以根据实际需求调整分割逻辑。

回到顶部