HScan incrementally iterate hash fields and associated values
(ctx *Context, txn *db.Transaction)
| 323 | |
| 324 | //HScan incrementally iterate hash fields and associated values |
| 325 | func HScan(ctx *Context, txn *db.Transaction) (OnCommit, error) { |
| 326 | var ( |
| 327 | key []byte |
| 328 | cursor []byte |
| 329 | lastCursor = []byte("0") |
| 330 | count = uint64(defaultScanCount) |
| 331 | kvs = [][]byte{} |
| 332 | pattern []byte |
| 333 | prefix []byte |
| 334 | isAll bool |
| 335 | err error |
| 336 | ) |
| 337 | key = []byte(ctx.Args[0]) |
| 338 | if strings.Compare(ctx.Args[1], "0") != 0 { |
| 339 | cursor = []byte(ctx.Args[1]) |
| 340 | } |
| 341 | |
| 342 | // define return result |
| 343 | result := func() { |
| 344 | if _, err := resp.ReplyArray(ctx.Out, 2); err != nil { |
| 345 | return |
| 346 | } |
| 347 | resp.ReplyBulkString(ctx.Out, string(lastCursor)) |
| 348 | if _, err := resp.ReplyArray(ctx.Out, len(kvs)); err != nil { |
| 349 | return |
| 350 | } |
| 351 | for i := range kvs { |
| 352 | resp.ReplyBulkString(ctx.Out, string(kvs[i])) |
| 353 | } |
| 354 | } |
| 355 | hash, err := txn.Hash(key) |
| 356 | if err != nil { |
| 357 | if err == db.ErrTypeMismatch { |
| 358 | return nil, ErrTypeMismatch |
| 359 | } |
| 360 | return nil, errors.New("ERR " + err.Error()) |
| 361 | } |
| 362 | |
| 363 | //check if hash is not exits return result |
| 364 | if !hash.Exists() { |
| 365 | return result, nil |
| 366 | } |
| 367 | |
| 368 | if len(ctx.Args)%2 != 0 { |
| 369 | return nil, ErrSyntax |
| 370 | } |
| 371 | |
| 372 | for i := 2; i < len(ctx.Args); i += 2 { |
| 373 | arg := strings.ToLower(ctx.Args[i]) |
| 374 | next := ctx.Args[i+1] |
| 375 | switch arg { |
| 376 | case "count": |
| 377 | if count, err = strconv.ParseUint(next, 10, 64); err != nil { |
| 378 | return nil, ErrInteger |
| 379 | } |
| 380 | if count > ScanMaxCount { |
| 381 | count = ScanMaxCount |
| 382 | } |
nothing calls this directly
no test coverage detected