Returns the collision set from storage for the given tree, optionally for only the list of TSUIDs provided. Note: This can potentially be a large list if the rule set was written poorly and there were many timeseries so only call this without a list of TSUIDs if you feel confident the number
(final TSDB tsdb,
final int tree_id, final List<String> tsuids)
| 632 | * @throws IllegalArgumentException if the tree ID was invalid |
| 633 | */ |
| 634 | public static Deferred<Map<String, String>> fetchCollisions(final TSDB tsdb, |
| 635 | final int tree_id, final List<String> tsuids) { |
| 636 | if (tree_id < 1 || tree_id > 65535) { |
| 637 | throw new IllegalArgumentException("Invalid Tree ID"); |
| 638 | } |
| 639 | |
| 640 | final byte[] row_key = new byte[TREE_ID_WIDTH + 1]; |
| 641 | System.arraycopy(idToBytes(tree_id), 0, row_key, 0, TREE_ID_WIDTH); |
| 642 | row_key[TREE_ID_WIDTH] = COLLISION_ROW_SUFFIX; |
| 643 | |
| 644 | final GetRequest get = new GetRequest(tsdb.treeTable(), row_key); |
| 645 | get.family(TREE_FAMILY); |
| 646 | |
| 647 | // if the caller provided a list of TSUIDs, then we need to compile a list |
| 648 | // of qualifiers so we only fetch those columns. |
| 649 | if (tsuids != null && !tsuids.isEmpty()) { |
| 650 | final byte[][] qualifiers = new byte[tsuids.size()][]; |
| 651 | int index = 0; |
| 652 | for (String tsuid : tsuids) { |
| 653 | final byte[] qualifier = new byte[COLLISION_PREFIX.length + |
| 654 | (tsuid.length() / 2)]; |
| 655 | System.arraycopy(COLLISION_PREFIX, 0, qualifier, 0, |
| 656 | COLLISION_PREFIX.length); |
| 657 | final byte[] tsuid_bytes = UniqueId.stringToUid(tsuid); |
| 658 | System.arraycopy(tsuid_bytes, 0, qualifier, COLLISION_PREFIX.length, |
| 659 | tsuid_bytes.length); |
| 660 | qualifiers[index] = qualifier; |
| 661 | index++; |
| 662 | } |
| 663 | get.qualifiers(qualifiers); |
| 664 | } |
| 665 | |
| 666 | /** |
| 667 | * Called after issuing the row get request to parse out the results and |
| 668 | * compile the list of collisions. |
| 669 | */ |
| 670 | final class GetCB implements Callback<Deferred<Map<String, String>>, |
| 671 | ArrayList<KeyValue>> { |
| 672 | |
| 673 | @Override |
| 674 | public Deferred<Map<String, String>> call(final ArrayList<KeyValue> row) |
| 675 | throws Exception { |
| 676 | if (row == null || row.isEmpty()) { |
| 677 | final Map<String, String> empty = new HashMap<String, String>(0); |
| 678 | return Deferred.fromResult(empty); |
| 679 | } |
| 680 | |
| 681 | final Map<String, String> collisions = |
| 682 | new HashMap<String, String>(row.size()); |
| 683 | |
| 684 | for (KeyValue column : row) { |
| 685 | if (column.qualifier().length > COLLISION_PREFIX.length && |
| 686 | Bytes.memcmp(COLLISION_PREFIX, column.qualifier(), 0, |
| 687 | COLLISION_PREFIX.length) == 0) { |
| 688 | final byte[] parsed_tsuid = Arrays.copyOfRange(column.qualifier(), |
| 689 | COLLISION_PREFIX.length, column.qualifier().length); |
| 690 | collisions.put(UniqueId.uidToString(parsed_tsuid), |
| 691 | new String(column.value(), CHARSET)); |