{"record":{"id":"9a8c1d24af477e1f","repo":"apache/beam","slug":"the-current-element-is-unavailable-because-either-the-reader","errorCode":null,"errorMessage":"The current element is unavailable because either the reader is at the beginning of the input and start() or advance() wasn't called, or the last start() or advance() returned false.","messagePattern":"The current element is unavailable because either the reader is at the beginning of the input and start\\(\\) or advance\\(\\) wasn't called, or the last start\\(\\) or advance\\(\\) returned false\\.","errorType":"exception","errorClass":"NoSuchElementException","httpStatus":null,"severity":"error","filePath":"sdks/java/io/synthetic/src/main/java/org/apache/beam/sdk/io/synthetic/SyntheticBoundedSource.java","lineNumber":195,"sourceCode":"      this.readerDelay = new ReaderDelay(source.sourceOptions);\n      this.currentKvPair = null;\n      this.splitPointFrequencyRecords = source.sourceOptions.splitPointFrequencyRecords;\n    }\n\n    @Override\n    public synchronized SyntheticBoundedSource getCurrentSource() {\n      return (SyntheticBoundedSource) super.getCurrentSource();\n    }\n\n    @Override\n    protected long getCurrentOffset() throws IllegalStateException {\n      return currentOffset;\n    }\n\n    @Override\n    public KV<byte[], byte[]> getCurrent() throws NoSuchElementException {\n      if (currentKvPair == null) {\n        throw new NoSuchElementException(\n            \"The current element is unavailable because either the reader is \"\n                + \"at the beginning of the input and start() or advance() wasn't called, \"\n                + \"or the last start() or advance() returned false.\");\n      }\n      return currentKvPair;\n    }\n\n    @Override\n    public boolean allowsDynamicSplitting() {\n      return splitPointFrequencyRecords > 0;\n    }\n\n    @Override\n    protected final boolean startImpl() throws IOException {\n      this.currentOffset = getCurrentSource().getStartOffset();\n      if (splitPointFrequencyRecords > 0) {\n        while (currentOffset % splitPointFrequencyRecords != 0) {\n          ++currentOffset;","sourceCodeStart":177,"sourceCodeEnd":213,"githubUrl":"https://github.com/apache/beam/blob/12126d8942aaf848030c478b4c6a28c6af861c66/sdks/java/io/synthetic/src/main/java/org/apache/beam/sdk/io/synthetic/SyntheticBoundedSource.java#L177-L213","documentation":"SyntheticBoundedSource's BoundedReader.getCurrent() follows the Beam reader contract: the current element only exists after start() succeeds or advance() returns true. The synthetic source (used by Beam's Nexmark/performance tests to generate deterministic byte payloads) throws NoSuchElementException when getCurrent() is called before the reader is positioned on an element.","triggerScenarios":"Calling reader.getCurrent() immediately after createReader() without calling start(); or calling it after advance()/start() returned false (end of input). Typically only hit by custom runner code or tests driving the reader directly.","commonSituations":"Custom BoundedSource harnesses or unit tests that iterate readers manually and forget the start()/advance() protocol; runners that mis-handle empty synthetic sources where start() returns false immediately.","solutions":["Call start() once after obtaining the reader, and only call getCurrent()/getCurrentTimestamp() when it returned true.","After each advance(), check its boolean result before reading the current element.","Handle the empty-source case: if start() returns false, treat the source as exhausted and skip reading."],"exampleFix":"// before\nBoundedSource.BoundedReader<KV<byte[], byte[]>> r = source.createReader(pipelineOptions);\nKV<byte[], byte[]> kv = r.getCurrent();\n// after\nBoundedSource.BoundedReader<KV<byte[], byte[]>> r = source.createReader(pipelineOptions);\nif (r.start()) {\n  KV<byte[], byte[]> kv = r.getCurrent();\n}","handlingStrategy":"type-guard","validationCode":null,"typeGuard":"boolean hasCurrent(BoundedSource.BoundedReader<?> r) { return r.start() || false; } // only true while start()/advance() returned true","tryCatchPattern":"try {\n  KV<byte[], byte[]> kv = reader.getCurrent();\n} catch (NoSuchElementException e) {\n  // reader not positioned or exhausted: call start()/advance() first\n}","preventionTips":["Always follow the start()/advance() protocol before getCurrent().","Treat start()==false as an exhausted reader, never as an error.","Write reader-contract tests for any custom synthetic source usage."],"tags":["apache-beam","java","source-reader","synthetic-source"],"backgroundTag":"invalid-state-transition","analyzedSha":"12126d8942aaf848030c478b4c6a28c6af861c66","analyzedAt":"2026-09-13T01:50:10.254Z","contentChangedAt":"2026-09-13T01:50:10.254Z","schemaVersion":2},"datasetVersion":"2026-09-20T03:17:13.778Z"}