Skip to content

Rows.Next panic due to index out of range #1253

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
microyahoo opened this issue Jul 14, 2022 · 12 comments
Closed

Rows.Next panic due to index out of range #1253

microyahoo opened this issue Jul 14, 2022 · 12 comments

Comments

@microyahoo
Copy link

microyahoo commented Jul 14, 2022

The version of pgx, gorm and golang

github.com/jackc/pgx/v4 v4.15.0
gorm.io/gorm v1.23.4
go version go1.17.3 linux/amd64

The following code will be panic due to panic: runtime error: index out of range [0] with length 0

 13 type Disk struct {                                                                                    
 14     gorm.Model `diff:"-"`                                                                             
 15                                                                                                     
 16     HostID      uint   `diff:"host_id"`                                                               
 17     Host        *Host  `diff:"-"`                                                                   
 18     Name        string `diff:"name"`                                                                  
 19     WWN         string `gorm:"column:wwn" diff:"wwn"`                                               
 20     UUID        string `gorm:"column:uuid" diff:"uuid"`                                               
 21     PathID      string `gorm:"column:path_id" diff:"path_id"`                                         
 22     Serial      string `diff:"serial"`                                                                
 23     Type        string `diff:"type"`                                                                  
 24     Rotational  bool   `diff:"rotational"`                                                            
 25     Filesystem  string `diff:"filesystem"`                                                            
 26     Vendor      string `diff:"vendor"`                                                              
 27     RealPath    string `diff:"real_path"`                                                             
 28     DeviceModel string `diff:"device_model"`                                                          
 29     IsRoot      bool   `diff:"is_root"`                                                               
 30     Encrypted   bool   `diff:"encrypted"`                                                           
 31     MBytes      uint64 `gorm:"column:mbytes" diff:"mbytes"`                                           
 32     HasChildren bool   `diff:"has_children"`                                                          
 33     Empty       bool   `diff:"empty"`                                                                 
 34     Cache       bool   `diff:"-"`                                                                   
 35                                                                                                     
 36     Osd *Osd `diff:"-"`                                                                             
 37 }
 78 func (m *Model) GetDisk(id uint) (*Disk, error) {                                                      
 79     var r Disk                                                                                        
 80     // SELECT * FROM "disks" WHERE id = <id> AND "disks"."deleted_at" IS NULL ORDER BY "disks"."id" LIMIT 1
 81     err := m.DB().Where("id = ?", id).First(&r).Error                                                 
 82     if err != nil {                                                                                 
 83         if errors.Is(err, gorm.ErrRecordNotFound) {                                                   
 84             return nil, nil                                                                           
 85         }                                                                                             
 86         return nil, err                                                                                                                  
 87     }                                                                                                 
 88     // SELECT * FROM "osds" WHERE "osds"."disk_id" = <id> AND "osds"."deleted_at" IS NULL             
 89     err = m.DB().Model(&r).Association("Osd").Find(&r.Osd)                                          
 90     if err == nil {                                                                                   
 91         // https://gorm.io/zh_CN/docs/associations.html#%E6%9F%A5%E6%89%BE%E5%85%B3%E8%81%94          
 92         // SELECT * FROM "hosts" WHERE "hosts"."id" = <id> AND "hosts"."deleted_at" IS NULL           
 93         err = m.DB().Model(&r).Association("Host").Find(&r.Host)                                    
 94     }                                                                                                 
 95     if err != nil {                                                                                   
 96         return nil, err                                                                               
 97     }                                                                                               
 98                                                                                                     
 99     return &r, nil                                                                                  
100 }

The log snippet is as follows:

2022/07/14 14:18:53 /root/go/src/deeproute.ai/smd/pkg/models/disk.go:81 conn busy                                                            
[1.749ms] [rows:0] SELECT * FROM "disks" WHERE id = 5 AND "disks"."deleted_at" IS NULL ORDER BY "disks"."id" LIMIT 1                         
panic: runtime error: index out of range [0] with length 0
                                                                      
goroutine 225 [running]:                                              
github.com/jackc/pgx/v4/stdlib.(*Rows).Next(0xc0004f6140, {0x2f6e480, 0x0, 0x0})
        /root/go/src/deeproute.ai/smd/vendor/github.com/jackc/pgx/v4/stdlib/sql.go:763 +0x370
database/sql.(*Rows).nextLocked(0xc000562600)  
        /usr/local/go/src/database/sql/sql.go:2967 +0x111
database/sql.(*Rows).Next.func1()                                     
        /usr/local/go/src/database/sql/sql.go:2945 +0x2f
database/sql.withLock({0x1fb6e98, 0xc000562630}, 0xc000a21568)
        /usr/local/go/src/database/sql/sql.go:3396 +0x8c
database/sql.(*Rows).Next(0xc000562600)        
        /usr/local/go/src/database/sql/sql.go:2944 +0x6f
gorm.io/gorm.Scan({0x1ff0320, 0xc000562600}, 0xc00051de60, 0x0)
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/scan.go:275 +0xc23
gorm.io/gorm/callbacks.Query(0xc00051de60)     
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/callbacks/query.go:26 +0x105
gorm.io/gorm.(*processor).Execute(0xc000480280, 0xc000a21e70)
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/callbacks.go:130 +0x433
gorm.io/gorm.(*DB).Find(0xc00047c640, {0x1912aa0, 0xc0002282e0}, {0x0, 0x0, 0x0})
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/finisher_api.go:166 +0x13c
gorm.io/gorm.(*Association).Find(0xc00047c640, {0x1912aa0, 0xc0002282e0}, {0x0, 0x0, 0x0})
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/association.go:45 +0x6f
deeproute.ai/smd/pkg/models.(*Model).GetDisk(0xc000606ad8, 0x0)
        /root/go/src/deeproute.ai/smd/pkg/models/disk.go:93 +0x205
deeproute.ai/smd/pkg/server/routes.(*CrushRootController).DeleteCrushRoot.func1(0xc0005c49a0)
        /root/go/src/deeproute.ai/smd/pkg/server/routes/crush_root.go:291 +0x135
created by deeproute.ai/smd/pkg/server/routes.(*CrushRootController).DeleteCrushRoot
        /root/go/src/deeproute.ai/smd/pkg/server/routes/crush_root.go:288 +0x8b5
2022/07/14 15:23:36 /root/go/src/deeproute.ai/smd/pkg/models/disk.go:81 conn busy                                                            
[0.962ms] [rows:0] SELECT * FROM "disks" WHERE id = 3 AND "disks"."deleted_at" IS NULL ORDER BY "disks"."id" LIMIT 1                         

2022/07/14 15:23:36 /root/go/src/deeproute.ai/smd/pkg/models/disk.go:81 conn busy
[0.978ms] [rows:0] SELECT * FROM "disks" WHERE id = 5 AND "disks"."deleted_at" IS NULL ORDER BY "disks"."id" LIMIT 1
panic: runtime error: index out of range [0] with length 0

goroutine 313 [running]:
github.com/jackc/pgx/v4/stdlib.(*Rows).Next(0xc000862780, {0xc00016de40, 0x16, 0x340})
        /root/go/src/deeproute.ai/smd/vendor/github.com/jackc/pgx/v4/stdlib/sql.go:763 +0x370
database/sql.(*Rows).nextLocked(0xc000725d00)
        /usr/local/go/src/database/sql/sql.go:2967 +0x111
database/sql.(*Rows).Next.func1()
        /usr/local/go/src/database/sql/sql.go:2945 +0x2f
database/sql.withLock({0x1fb6eb8, 0xc000725d30}, 0xc000a37568)
        /usr/local/go/src/database/sql/sql.go:3396 +0x8c
database/sql.(*Rows).Next(0xc000725d00)
        /usr/local/go/src/database/sql/sql.go:2944 +0x6f
gorm.io/gorm.Scan({0x1ff0340, 0xc000725d00}, 0xc0007c98c0, 0x0)
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/scan.go:275 +0xc23
gorm.io/gorm/callbacks.Query(0xc0007c98c0)
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/callbacks/query.go:26 +0x105
gorm.io/gorm.(*processor).Execute(0xc00060f900, 0x1b6b900)
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/callbacks.go:130 +0x433
gorm.io/gorm.(*DB).First(0x0, {0x1aca000, 0xc00029d540}, {0x0, 0x0, 0x0})
        /root/go/src/deeproute.ai/smd/vendor/gorm.io/gorm/finisher_api.go:125 +0x1c5
deeproute.ai/smd/pkg/models.(*Model).GetDisk(0xc0007ba340, 0x0)
        /root/go/src/deeproute.ai/smd/pkg/models/disk.go:81 +0xc5
deeproute.ai/smd/pkg/server/routes.(*CrushRootController).DeleteCrushRoot.func1(0xc0008171e0)
        /root/go/src/deeproute.ai/smd/pkg/server/routes/crush_root.go:291 +0x135
created by deeproute.ai/smd/pkg/server/routes.(*CrushRootController).DeleteCrushRoot
        /root/go/src/deeproute.ai/smd/pkg/server/routes/crush_root.go:288 +0x8b8
@jackc
Copy link
Owner

jackc commented Jul 16, 2022

I've never used gorm. Can you reproduce with just pgx?

@R2D2Dan
Copy link

R2D2Dan commented Sep 20, 2022

I have a similar issue when calling rows.Values ​​I get a panic

My code

package http

import (
	config "http_client3/package/config"
	"http_client3/package/db"
	"log"
)



// Connection db and exec proc
func (obj *GetPostOgbject) exec(sql string, args string) error {
	//Get Params for connection db
	params, err := config.GetFullParam([]string{"db_user", "db_password", "db_host", "db_port", "db_dbname", "db_sslmode"})
	if err != nil {
		obj.set_response("", &ErrorObject{"DB", "9", "server side error"})
		return err
	}
	// Connection to data base
	db, err := db.Connection(params)
	if err != nil {
		obj.set_response("", &ErrorObject{"DB", "9", "server side error"})
		return err
	}
	log.Println("sql:", sql)
	log.Println("args:", args)
	row, err := db.PostgreSQL.Query(sql, args)
	if err != nil {
		obj.set_response("", &ErrorObject{"DB", "9", "server side error"})
		return err
	}
	
	//Connection db close
	defer func() {
		if err := db.PostgreSQL.Close(); err != nil {
			log.Println("error close connection db", err)
		}

	}()

	s, err := row.Values()
	if err != nil {
		obj.set_response("", &ErrorObject{"DB", "9", "server side error"})
		return err
	}
	log.Println(s)

	

	return nil
}

Result

2022/09/20 13:39:42 sql: select * from fn_load_customers($1)
2022/09/20 13:39:42 args: {"data":1}
2022/09/20 13:39:42 http: panic serving [::1]:54535: runtime error: index out of range [0] with length 0
goroutine 19 [running]:
net/http.(*conn).serve.func1()
        C:/Program Files/Go/src/net/http/server.go:1850 +0xbf
panic({0x571dc0, 0xc000091548})
        C:/Program Files/Go/src/runtime/panic.go:890 +0x262
github.com/jackc/pgx.(*Rows).nextColumn(0xc0000a2e10?)
        C:/Users/dlazutkin/go/pkg/mod/github.com/jackc/[email protected]+incompatible/query.go:198 +0xe5
github.com/jackc/pgx.(*Rows).Values(0xc00021a890)
        C:/Users/dlazutkin/go/pkg/mod/github.com/jackc/[email protected]+incompatible/query.go:303 +0x12c
http_client3/package/http.(*GetPostOgbject).exec(0xc000119948, {0x59bf0c, 0x23}, {0xc0000d8c00, 0xa})
        C:/Users/dlazutkin/Go/src/http_client3/package/http/exec_db.go:39 +0x672
http_client3/package/http.(*GetPostOgbject).respone(0xc000119948, {0x59bf0c, 0x23}, {0x626c10, 0xc0000f00e0}, 0xc0000da200)
        C:/Users/dlazutkin/Go/src/http_client3/package/http/response.go:60 +0x36c
http_client3/package/http.(*GetPostOgbject).fn_load_customers(...)
        C:/Users/dlazutkin/Go/src/http_client3/package/http/response.go:81
http_client3/package/http.Load_Costumers({0x626c10, 0xc0000f00e0}, 0xc0000b3a10?)
        C:/Users/dlazutkin/Go/src/http_client3/package/http/costumers_r.go:11 +0x12a
net/http.HandlerFunc.ServeHTTP(0xc0000da100?, {0x626c10?, 0xc0000f00e0?}, 0x800?)
        C:/Program Files/Go/src/net/http/server.go:2109 +0x2f
github.com/gorilla/mux.(*Router).ServeHTTP(0xc0000b4000, {0x626c10, 0xc0000f00e0}, 0xc00005e000)
        C:/Users/dlazutkin/go/pkg/mod/github.com/gorilla/[email protected]/mux.go:210 +0x1cf
net/http.serverHandler.ServeHTTP({0x624f10?}, {0x626c10, 0xc0000f00e0}, 0xc00005e000)
        C:/Program Files/Go/src/net/http/server.go:2947 +0x30c
net/http.(*conn).serve(0xc00011b540, {0x627290, 0xc0000b3800})
        C:/Program Files/Go/src/net/http/server.go:1991 +0x607
created by net/http.(*Server).Serve
        C:/Program Files/Go/src/net/http/server.go:3102 +0x4db

@jackc
Copy link
Owner

jackc commented Sep 24, 2022

@R2D2Dan I do not see a call to Next() before the call to Values().

@R2D2Dan
Copy link

R2D2Dan commented Sep 28, 2022

@R2D2DanЯ не вижу вызова Next()перед вызовом Values().

And you should always call Next() before Values()?
Unfortunately, I did not find any examples of use, so I'm asking.

@jackc
Copy link
Owner

jackc commented Oct 1, 2022

Yes. You always must call Next() before Scan() or Values().

@bfontaine
Copy link
Contributor

I’m closing this one since we don’t have a reproducible example with just pgx.

@bfontaine bfontaine closed this as not planned Won't fix, can't repro, duplicate, stale Nov 4, 2022
@syed-shah-zepto
Copy link

@microyahoo were you able to find the reason for the reported issue? Facing the same issue with gorm, would appreciate any pointers.

@microyahoo
Copy link
Author

hi @syed-shah-zepto, If I remember correctly, if multiple goroutines access the database at the same time under the one transaction, an error will be reported

@syed-shah-zepto
Copy link

thanks @microyahoo. How did you get around this?

@microyahoo
Copy link
Author

microyahoo commented Mar 5, 2023

@syed-shah-zepto After moving the access to the database outside the goroutines, the problem did not reappear.

@Froctnow
Copy link

Froctnow commented Feb 3, 2024

@syed-shah-zepto @bfontaine
It is not a problem of this library. It is a global problem, I've caught this problem with INSERT INTO ... RETURNING in one transaction and many gorutines, therefore I get a error[ panic](panic: runtime error: index out of range [0] with length 0). I've removed RETURNING from inserting queries in gorutines and it's okay.
Be careful with transaction and queries. Try to exclude such queries and change your code.

@hellwen
Copy link

hellwen commented Apr 19, 2024

@Froctnow I doesn't have INSERT INTO ... RETURNING in one transaction, but i have many goroutines to using UPDATE in the same transaction. I always meeting the error. But if a only have SELECT the error doesn't appear.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

7 participants