dtx9763 2017-05-16 05:13 采纳率: 100%
浏览 44
已采纳

通过GoCQL在ScyllaDB上进行阻止/一致/可预测的答复/请求

Sometimes when running a command it shows a timeout (gocql: no response received from cassandra within timeout period), for example:

package main

import "fmt"
import "github.com/gocql/gocql"
import "time"
import "log"

func main() {
    clust := gocql.NewCluster(`172.17.0.2`) // docker@localhost
    clust.Keyspace = `test4`
    clust.RetryPolicy = &gocql.SimpleRetryPolicy{NumRetries: 3}
    db, err := clust.CreateSession()
    defer db.Close()
    if err != nil {
        log.Fatal(err)
        return
    }
    fmt.Println(`test4: scylladb`)

    if err := db.Query(`DROP TABLE test4`).Exec(); err != nil {
        log.Println(err)
    }
    if err := db.Query(`CREATE TABLE test4 (bucket text, k text, v TEXT, PRIMARY KEY(bucket,k))`).Exec(); err != nil {
        log.Fatal(err)
        return
    }

    const max = 999
    const jump = 40
    t := time.Now()
    for x := 1; x <= max; x++ {
        err = db.Query(fmt.Sprintf(`INSERT INTO test4(bucket,k,v)VALUES('foo','%05d','%05d')`, x, x)).Exec()
        if err != nil {
            log.Fatal(err)
            return
        }
        if x % 200 == 0 {
            fmt.Print(`.`)
        }
    }
    dur := time.Now().Sub(t)
    fmt.Printf("INSERT: %v (%.2f ms/op)
", dur, float64(dur.Nanoseconds()) / 1000000 / max)

    t = time.Now()
    for x := 1; x <= max; x++ {
        err = db.Query(fmt.Sprintf(`UPDATE test4 SET v = '%06d' WHERE bucket = 'foo' AND k = '%05d'`, x, x)).Exec()
        if err != nil {
            log.Fatal(err)
            return
        }
        if x % 200 == 0 {
            fmt.Print(`.`)
        }
    }
    dur = time.Now().Sub(t)
    fmt.Printf("UPDATE: %v (%.2f ms/op)
", dur, float64(dur.Nanoseconds()) / 1000000 / max)

    t = time.Now()
    ops := int64(0)
    for y := 2; y < jump; y++ {
        for x := max - 1; x > 0; x -= y {
            ops++
            iter := db.Query(fmt.Sprintf(`SELECT k, v FROM test4 WHERE bucket = 'foo' AND  k >= '%05d' ORDER BY k ASC LIMIT %d`, x, y * y)).Iter()
            for {
                m := map[string]interface{}{}
                if !iter.MapScan(m) {
                    break
                }
            }
            iter.Close()
            if ops % 500 == 0 {
                fmt.Print(`.`)
            }
        }
        for x := 1; x < max; x += y {
            ops++
            iter := db.Query(fmt.Sprintf(`SELECT k, v FROM test4 WHERE bucket = 'foo' AND k <= '%05d' ORDER BY k DESC LIMIT %d`, x, y * y)).Iter()
            for {
                m := map[string]interface{}{}
                if !iter.MapScan(m) {
                    break
                }
            }
            iter.Close()
            if ops % 500 == 0 {
                fmt.Print(`.`)
            }
        }
    }
    dur = time.Now().Sub(t)
    fmt.Printf("SELECT: %v (%.2f ms/op)
", dur, float64(dur.Nanoseconds()) / 1000000 / float64(ops))

}

It shows inconsistent output:

$ go run scylla.go
test4: scylladb
2017/05/16 12:09:05 gocql: no response received from cassandra within timeout period
2017/05/16 12:09:05 gocql: no response received from cassandra within timeout period
exit status 1

$ go run scylla.go 
test4: scylladb
....INSERT: 188.277521ms (0.19 ms/op)
....UPDATE: 150.403282ms (0.15 ms/op)
.............SELECT: 5.357779756s (0.82 ms/op)

$ go run scylla.go 
test4: scylladb
2017/05/16 12:09:50 gocql: no response received from cassandra within timeout period
....INSERT: 142.91132ms (0.14 ms/op)
....UPDATE: 144.272872ms (0.14 ms/op)
.............SELECT: 5.268130283s (0.81 ms/op)

$ go run scylla.go 
test4: scylladb
2017/05/16 12:10:00 gocql: no response received from cassandra within timeout period
2017/05/16 12:10:00 gocql: no response received from cassandra within timeout period
exit status 1

$ go run scylla.go 
test4: scylladb
....INSERT: 184.402052ms (0.18 ms/op)
....UPDATE: 158.200184ms (0.16 ms/op)
.............SELECT: 5.345212835s (0.82 ms/op)

How to make it consistent? I need to be sure if a command completed successfully.. Or should I loop the DROP TABLE/CREATE TABLE command manually?

  • 写回答

1条回答 默认 最新

  • dongshi9489 2017-05-16 09:28
    关注

    DROP TABLE and CREATE TABLE can take a lot longer than ordinary queries. You can try to increase the timeouts for these queries.

    For example: clust.Timeout = 8 * time.Second

    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 关于#matlab#的问题:在模糊控制器中选出线路信息,在simulink中根据线路信息生成速度时间目标曲线(初速度为20m/s,15秒后减为0的速度时间图像)我想问线路信息是什么
  • ¥15 banner广告展示设置多少时间不怎么会消耗用户价值
  • ¥16 mybatis的代理对象无法通过@Autowired装填
  • ¥15 可见光定位matlab仿真
  • ¥15 arduino 四自由度机械臂
  • ¥15 wordpress 产品图片 GIF 没法显示
  • ¥15 求三国群英传pl国战时间的修改方法
  • ¥15 matlab代码代写,需写出详细代码,代价私
  • ¥15 ROS系统搭建请教(跨境电商用途)
  • ¥15 AIC3204的示例代码有吗,想用AIC3204测量血氧,找不到相关的代码。