Files
obitools4/pkg/obiformats/fastseq_json_header.go
Eric Coissac 93f9dcb95f Reducing memory allocation events
Former-commit-id: c94e79ba116464504580fc397270ead154063971
2024-06-22 22:32:31 +02:00

114 lines
2.3 KiB
Go

package obiformats
import (
"bytes"
"math"
"strings"
"unsafe"
log "github.com/sirupsen/logrus"
"git.metabarcoding.org/obitools/obitools4/obitools4/pkg/obiseq"
"git.metabarcoding.org/obitools/obitools4/obitools4/pkg/obiutils"
"github.com/goccy/go-json"
)
func _parse_json_header_(header string, annotations obiseq.Annotation) string {
start := -1
stop := -1
level := 0
lh := len(header)
inquote := false
for i := 0; (i < lh) && (stop < 0); i++ {
// fmt.Printf("[%d,%d-%d] : %d (%c) (%d,%c)\n", i, start, stop, header[i], header[i], '{', '{')
if level == 0 && header[i] == '{' && !inquote {
start = i
}
// TODO: escaped double quotes are not considered
if start > -1 && header[i] == '"' {
inquote = !inquote
}
if header[i] == '{' && !inquote {
level++
}
if header[i] == '}' && !inquote {
level--
}
if start >= 0 && level == 0 {
stop = i
}
}
if start < 0 || stop < 0 {
return header
}
stop++
err := json.Unmarshal([]byte(header)[start:stop], &annotations)
for k, v := range annotations {
switch vt := v.(type) {
case float64:
if vt == math.Floor(vt) {
annotations[k] = int(vt)
}
{
annotations[k] = vt
}
}
}
if err != nil {
log.Fatalf("annotation parsing error on %s : %v\n", header, err)
}
return strings.TrimSpace(header[stop:])
}
func ParseFastSeqJsonHeader(sequence *obiseq.BioSequence) {
definition := sequence.Definition()
sequence.SetDefinition("")
definition_part := _parse_json_header_(
definition,
sequence.Annotations())
if len(definition_part) > 0 {
if sequence.HasDefinition() {
definition_part = sequence.Definition() + " " + definition_part
}
sequence.SetDefinition(definition_part)
}
}
func WriteFastSeqJsonHeader(buffer *bytes.Buffer, sequence *obiseq.BioSequence) {
annotations := sequence.Annotations()
if len(annotations) > 0 {
err := obiutils.JsonMarshalByteBuffer(buffer, sequence.Annotations())
if err != nil {
log.Fatal(err)
}
}
}
func FormatFastSeqJsonHeader(sequence *obiseq.BioSequence) string {
annotations := sequence.Annotations()
buffer := bytes.Buffer{}
if len(annotations) > 0 {
obiutils.JsonMarshalByteBuffer(&buffer, sequence.Annotations())
return unsafe.String(unsafe.SliceData(buffer.Bytes()), len(buffer.Bytes()))
}
return ""
}