Heim > Backend-Entwicklung > Golang > Wie füge ich eine Schnittstelle zu einer nicht-nativen Struktur in Golang hinzu?

Wie füge ich eine Schnittstelle zu einer nicht-nativen Struktur in Golang hinzu?

王林
Freigeben: 2024-02-06 08:18:11
nach vorne
1114 Leute haben es durchsucht

Wie füge ich eine Schnittstelle zu einer nicht-nativen Struktur in Golang hinzu?

Frageninhalt

Ich verwende https://github.com/lib/pq, um Daten von Postgres abzurufen. Um die Daten zu extrahieren, verwende ich eine Drittanbieterstruktur, die das Protobuf-Zeitstempelfeld https://pkg.go.dev/google.golang.org/protobuf/types/known/timestamppb#timestamp enthält Also Das Problem besteht also darin, den Job zum Scannen von time.time nach timestamppb.timestamp

zu bringen
type stuff struct { //this struct non-local, this is from third-party package
  date *timestamppb.timestamp
}

stuff = stuff{}

scanerr := rows.scan(&stuff.date)
Nach dem Login kopieren

Ich versuche, die Struktur zu scannen, die die sql.scanner-Schnittstelle implementiert. Das ist einfach. Ich habe die Scan-Funktion gerade so implementiert:

type test struct {
}


func (t test) scan(src any) error {
//convert value
}
Nach dem Login kopieren

Aber es funktioniert nicht mit timestamppb.timestamp, da es sich um einen nicht nativen Typ handelt. Dann habe ich versucht, einen lokalen Typ zu definieren und dasselbe zu tun

type timestamppb timestamppb.timestamp

func (t timestamppb) scan(src any) error {
//convert value
}
Nach dem Login kopieren

Aber dieser Trick hat nicht funktioniert. Außerdem erhalte ich die Warnung „‚Scan‘ übergibt die Sperre nach Wert: Typ ‚timestamppb‘ enthält ‚protoimpl.messagestate‘ enthält ‚sync.mutex‘, d. h. ‚sync.locker‘“ Dies funktioniert nicht, wenn ich einen Zeiger für timestampppb

angebe
func (t *timestamppb) scan(src any) error {
Nach dem Login kopieren

Ich möchte also wissen, wie man eine timestamppb.timestamp-Instanz von sql.scanner erstellt. Ist es möglich?

Update 1 Kleines Beispiel von dem, was ich versucht habe

type TimestampPb timestamppb.Timestamp

type test struct { //third-party struct, I can't modify it
    date *timestamppb.Timestamp
}

func (s *Storage) test() {
    rows, _ := s.db.Query("SELECT \"test_date\" FROM \"test_table\" LIMIT 1")

    defer func() {
        if rows != nil {
            _ = rows.Close()
        }
    }()

    for rows.Next() {
        //var value *TimestampPb //works
        //var value TimestampPb //works
        //var value *timestamppb.Timestamp //doesn't work
        //testStruct := test{} //doesn't work

        //err := rows.Scan(&value) //scan to variable
        //err := rows.Scan(&testStruct.date) //scan to field in the struct
        if err != nil {
            log.Fatalln(err)
        }
    }
}

func (tpb *TimestampPb) Scan(src any) error {
    return nil
}
Nach dem Login kopieren

Ich möchte wissen, ob ich case mit teststruct verwenden kann?


Richtige Antwort


pq 库不支持 *timestamppb.timestamp als Zeitstempeltyp. Informationen zu den unterstützten Datumstypen finden Sie in der Dokumentation.

Beim Scannen sind verschiedene Typen erforderlich.

Normalerweise verwende ich dazu Hilfstypen in Funktionen. Zum Beispiel:

type row struct {
  Date *timestamppb.Timestamp
  // ... more fields here
}

func Query() ([]row, error) {
    rows, err := s.db.Query(...)
  if err != nil {
    return nil, err
  }
  defer rows.Close()

  var rows []row
  for rows.Next() {
    type aux struct {
      Date time.Time
      // ... more fields here
    }
    var value aux
    if err := rows.Scan(&value); err != nil {
      return nil, err
    }
    rows = append(rows, row{
      Date: timestamppb.New(value.Date),
      // ... more fields here
    }
  }
  return rows, nil
}
Nach dem Login kopieren

Das obige ist der detaillierte Inhalt vonWie füge ich eine Schnittstelle zu einer nicht-nativen Struktur in Golang hinzu?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Quelle:stackoverflow.com
Erklärung dieser Website
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn
Beliebte Tutorials
Mehr>
Neueste Downloads
Mehr>
Web-Effekte
Quellcode der Website
Website-Materialien
Frontend-Vorlage