{"record":{"id":"8aef78da5a539da5","repo":"apache/iceberg","slug":"malformed-input-partial-character-at-end-8aef78","errorCode":null,"errorMessage":"malformed input: partial character at end","messagePattern":"malformed input: partial character at end","errorType":"exception","errorClass":"UTFDataFormatException","httpStatus":null,"severity":"error","filePath":"flink/v2.3/flink/src/main/java/org/apache/iceberg/flink/util/SerializerHelper.java","lineNumber":134,"sourceCode":"      switch (ch >> 4) {\n        case 0:\n        case 1:\n        case 2:\n        case 3:\n        case 4:\n        case 5:\n        case 6:\n        case 7:\n          /* 0xxxxxxx */\n          count++;\n          chararr[chararrCount++] = (char) ch;\n          break;\n        case 12:\n        case 13:\n          /* 110x xxxx 10xx xxxx */\n          count += 2;\n          if (count > utflen) {\n            throw new UTFDataFormatException(\"malformed input: partial character at end\");\n          }\n          char2 = bytearr[count - 1];\n          if ((char2 & 0xC0) != 0x80) {\n            throw new UTFDataFormatException(\"malformed input around byte \" + count);\n          }\n          chararr[chararrCount++] = (char) (((ch & 0x1F) << 6) | (char2 & 0x3F));\n          break;\n        case 14:\n          /* 1110 xxxx 10xx xxxx 10xx xxxx */\n          count += 3;\n          if (count > utflen) {\n            throw new UTFDataFormatException(\"malformed input: partial character at end\");\n          }\n          char2 = bytearr[count - 2];\n          char3 = bytearr[count - 1];\n          if (((char2 & 0xC0) != 0x80) || ((char3 & 0xC0) != 0x80)) {\n            throw new UTFDataFormatException(\"malformed input around byte \" + (count - 1));\n          }","sourceCodeStart":116,"sourceCodeEnd":152,"githubUrl":"https://github.com/apache/iceberg/blob/86d9c8fc543e7c56c9f624eb725f76c9baff9570/flink/v2.3/flink/src/main/java/org/apache/iceberg/flink/util/SerializerHelper.java#L116-L152","documentation":"readLongUTF decodes a modified-UTF-8 byte stream. When a 2-byte lead byte (0xC0-0xDF) signals a continuation but the stream ends before the second byte, the decoder throws UTFDataFormatException 'malformed input: partial character at end'. The byte array is truncated or corrupt.","triggerScenarios":"Reading a byte[] whose length-prefix (utflen) is larger than the actual trailing bytes available, or the array was truncated mid multi-byte sequence.","commonSituations":"Corrupt or truncated serialized payloads (network cut, partial file write); hand-crafted byte arrays not produced by writeLongUTF; version-incompatible encoding of the length prefix.","solutions":["Verify the producer wrote with the same SerializerHelper.writeLongUTF and that the payload is intact.","Check byte array length vs the written utflen prefix before decoding.","Re-read the source data / re-run the job; if persistent, suspect corruption or a serialization version mismatch."],"exampleFix":"// before\nString s = helper.readLongUTF(in);\n// after\nint expected = in.readInt();\nbyte[] buf = new byte[expected];\nint n = in.readFully(buf);\nif (n != expected) { throw new IOException(\"truncated payload\"); }","handlingStrategy":"try-catch","validationCode":"// java\nint len = readLengthPrefix(buf);\nif (buf.remaining() < len) { throw new IOException(\"truncated payload: need \" + len + \" bytes\"); }","typeGuard":"boolean isCompleteUtfPayload(byte[] bytes) {\n  // last lead byte must not be a bare multi-byte lead (0xC0-0xF7)\n  if (bytes.length == 0) return true;\n  int lead = bytes[bytes.length - 1] & 0xFF;\n  return lead < 0x80 || (lead >= 0xC0 && bytes.length >= 2);\n}","tryCatchPattern":"try {\n  String s = helper.readLongUTF(in);\n} catch (UTFDataFormatException e) {\n  if (e.getMessage().contains(\"partial character at end\")) {\n    // re-read source or mark payload corrupt\n  } else { throw e; }\n}","preventionTips":["Pair every writeLongUTF with readLongUTF from the same helper.","Integrity-check payloads (checksum) before deserializing.","Verify length prefix matches available bytes before decode.","Watch for truncation across network/file boundaries."],"tags":["flink","serialization","utf","corruption"],"backgroundTag":"json-unmarshal-failed","analyzedSha":"86d9c8fc543e7c56c9f624eb725f76c9baff9570","analyzedAt":"2026-09-12T00:46:39.097Z","contentChangedAt":"2026-09-12T00:46:39.097Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}