{
  "id": "javareader",
  "title": "JavaReader",
  "url": "https://redis.io/docs/latest/operate/oss_and_stack/stack-with-enterprise/deprecated-features/gears-v1/jvm/classes/readers/javareader/",
  "summary": "A template for creating custom readers.",
  "tags": [
    "docs",
    "operate",
    "stack"
  ],
  "last_updated": "2026-04-22T11:55:45+02:00",
  "page_type": "content",
  "content_hash": "7339257d06d346b73aeee10507ef36f575b003462a85b4e488acdcb9d28052e8",
  "sections": [
    {
      "id": "overview",
      "title": "Overview",
      "role": "overview",
      "text": "The `JavaReader` is an abstract class that allows you to create a custom reader in Java."
    },
    {
      "id": "create-a-custom-reader",
      "title": "Create a custom reader",
      "role": "content",
      "text": "To create a custom reader:\n\n- Extend the `JavaReader` class\n- Override the `iterator()` function"
    },
    {
      "id": "custom-reader-example",
      "title": "Custom reader example",
      "role": "content",
      "text": "The implementation of the [`KeysOnlyReader`](https://redis.io/docs/latest/operate/oss_and_stack/stack-with-enterprise/deprecated-features/gears-v1/jvm/classes/readers/keysonlyreader) class shows how to create a custom reader with `JavaReader`:\n\n[code example]"
    }
  ],
  "examples": [
    {
      "id": "custom-reader-example-ex0",
      "language": "java",
      "code": "import java.util.Iterator;\n\nimport gears.GearsBuilder;\n\n/**\n * A reader that only reads key names from the key space\n *\n */\npublic class KeysOnlyReader extends JavaReader<String> {\n\n\t/**\n\t * \n\t */\n\tprivate static final long serialVersionUID = 1L;\n\t\n\tprivate String scanSize;\n\tprivate String pattern;\n\t\n\t/**\n\t * Create a new KeysOnlyReader reader\n\t * @param scanSize - the size to use with the scan command\n\t * @param pattern - the pattern of the keys to read\n\t */\n\tpublic KeysOnlyReader(int scanSize, String pattern) {\n\t\tthis.scanSize = Integer.toString(scanSize);\n\t\tthis.pattern = pattern;\n\t}\n\t\n\t/**\n\t * Create a new KeysOnlyReader reader with default pattern (*) and default\n\t * scan size (10000)\n\t */\n\tpublic KeysOnlyReader() {\n\t\tthis(10000, \"*\");\n\t}\n\n\t@Override\n\tpublic Iterator<String> iterator() {\n\t\treturn new Iterator<String>() {\n\n\t\t\tString cursor = \"0\";\n\t\t\tint currIndex = 0;\n\t\t\tObject[] keys = null;\n\t\t\tboolean isDone = false;\n\t\t\tString nextKey = null;\n\t\t\t\n\t\t\tprivate String innerNext() {\n\t\t\t\twhile(!isDone) {\n\t\t\t\t\tif(keys == null) {\n\t\t\t\t\t\tObject[] res = (Object[]) GearsBuilder.execute(\"scan\", \n\t\t\t\t\t\t\t\t\t\tcursor == null ? \"0\" : cursor,\n\t\t\t\t\t\t\t\t\t\t\"MATCH\", pattern, \"COUNT\", scanSize);\n\t\t\t\t\t\tkeys = (Object[])res[1];\n\t\t\t\t\t\tcursor = (String)res[0];\n\t\t\t\t\t\tcurrIndex = 0;\n\t\t\t\t\t}\n\t\t\t\t\tif(currIndex < keys.length) {\n\t\t\t\t\t\treturn (String) keys[currIndex++];\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tkeys = null;\n\t\t\t\t\tif(cursor.charAt(0) == '0') {\n\t\t\t\t\t\tisDone = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\t\n\t\t\t@Override\n\t\t\tpublic boolean hasNext() {\n\t\t\t\tif(nextKey == null) {\n\t\t\t\t\tnextKey = innerNext();\n\t\t\t\t}\n\t\t\t\treturn !isDone;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic String next() {\n\t\t\t\tString temp = nextKey != null ? nextKey : innerNext();\n\t\t\t\tnextKey = innerNext();\n\t\t\t\treturn temp;\n\t\t\t}\n\t\t\t\n\t\t};\n\t}\n\n}",
      "section_id": "custom-reader-example"
    }
  ]
}
