解组从postgresql获取的对象的Json数组
我在Postgres中有一个表,它是Jsonb解组从postgresql获取的对象的Json数组,postgresql,go,Postgresql,Go,我在Postgres中有一个表,它是Jsonb Create Table Business( id serial not null primary key, id_category integer not null, name varchar(50) not null, owner varchar(200) not null, coordinates jsonb not null, reason varchar(300) not null,
Create Table Business(
id serial not null primary key,
id_category integer not null,
name varchar(50) not null,
owner varchar(200) not null,
coordinates jsonb not null,
reason varchar(300) not null,
foreign key(id_category) references Category(id)
);
如您所见,我将坐标存储为jsonb
例:
插入业务(id\u类别、名称、所有者、坐标、原因)
价值观
(1,'MyName','Owner',[{“纬度”:12.1268142,“经度”:-86.2754}','Description')
我提取数据并分配数据的方式如下
type Business struct {
ID int `json:"id,omitempty"`
Name string `json:"name,omitempty"`
Owner string `json:"owner,omitempty"`
Category string `json:"category,omitempty"`
Departments []string `json:"departments,omitempty"`
Location []Coordinates `json:"location,omitempty"`
Reason string `json:"reason,omitempty"`
}
type Coordinates struct {
Latitude float64 `json:"latitude,omitempty"`
Longitude float64 `json:"longitude,omitempty"`
}
func (a Coordinates) Value() (driver.Value, error) {
return json.Marshal(a)
}
func (a *Coordinates) Scan(value []interface{}) error {
b, ok := value.([]byte)
if !ok {
return errors.New("type assertion to []byte failed")
}
return json.Unmarshal(b, &a)
}
然而,我一直收到这个消息
sql:列索引3上的扫描错误,名称为“坐标”:不支持
扫描并将driver.Value type[]uint8存储到type*models.Coordinates中
我用来提取信息的控制器是这个
func (b *BusinessRepoImpl) Select() ([]models.Business, error) {
business_list := make([]models.Business, 0)
rows, err := b.Db.Query("SELECT business.id, business.name, business.owner, business.coordinates, business.reason_froggy, category.category FROM business INNER JOIN category on category.id = business.id_category group by business.id, business.name, business.owner, business.coordinates, business.reason_froggy, category.category")
if err != nil {
return business_list, err
}
for rows.Next() {
business := models.Business{}
err := rows.Scan(&business.ID, &business.Name, &business.Owner, &business.Location, &business.Reason, &business.Category)
if err != nil {
break
}
business_list = append(business_list, business)
}
err = rows.Err()
if err != nil {
return business_list, err
}
return business_list, nil
}
谁能告诉我如何解决这个问题?检索对象的json数组并将其分配给Business内部的坐标字段。1。
正如您从文档中看到的,要满足该接口,需要使用该方法
Scan(src interface{}) error
但是您的*坐标
类型实现了一种不同的方法
Scan(value []interface{}) error
类型interface{}
和[]interface{}
是两种截然不同的东西
2.
Scanner接口必须在要作为参数传递给的字段类型上实现。也就是说,您已经在*坐标
上实现了扫描
方法,但是位置字段的类型是[]坐标
type CoordinatesSlice []Coordinates
func (s *CoordinatesSlice) Scan(src interface{}) error {
switch v := src.(type) {
case []byte:
return json.Unmarshal(v, s)
case string:
return json.Unmarshal([]byte(v), s)
}
return errors.New("type assertion failed")
}
// ...
type Business struct {
// ...
Location CoordinatesSlice `json:"location,omitempty"`
// ...
}
同样,类型*坐标
和[]坐标
是两个非常不同的东西
因此,解决方案是在适当的类型上正确地实现接口 请注意,由于Go不允许向未命名类型添加方法,并且
[]坐标
是未命名类型,因此需要声明一个新类型,然后使用该类型代替[]坐标
type CoordinatesSlice []Coordinates
func (s *CoordinatesSlice) Scan(src interface{}) error {
switch v := src.(type) {
case []byte:
return json.Unmarshal(v, s)
case string:
return json.Unmarshal([]byte(v), s)
}
return errors.New("type assertion failed")
}
// ...
type Business struct {
// ...
Location CoordinatesSlice `json:"location,omitempty"`
// ...
}
注意
如果业务位置始终只有一对坐标作为jsonb对象存储在db中,并将
位置
类型从坐标板
更改为坐标
,并相应地将扫描仪
实现从*坐标板
移动到*坐标
I要知道这个解决方案实际上是未优化的,但这是唯一可行的方法
type CoordinatesSlice []Coordinates
func (s *CoordinatesSlice) Scan(src interface{}) error {
switch v := src.(type) {
case []byte:
return json.Unmarshal(v, s)
case string:
return json.Unmarshal([]byte(v), s)
}
return errors.New("type assertion failed")
}
// ...
type Business struct {
// ...
Location CoordinatesSlice `json:"location,omitempty"`
// ...
}
基本上,我必须获得json,然后对Location属性进行解组
var location string = ""
if err := json.Unmarshal([]byte(location), &business.Location); err != nil { panic(err) }
这就是我使用的所有代码,或者你需要更具体的东西?