{"record":{"id":"8636e52a9ff91f01","repo":"mattermost-community/focalboard","slug":"block-fields-size-limit-exceeded","errorCode":null,"errorMessage":"block fields size limit exceeded","messagePattern":"block fields size limit exceeded","errorType":"validation","errorClass":null,"httpStatus":400,"severity":"error","filePath":"server/model/block.go","lineNumber":22,"sourceCode":"\t\"encoding/json\"\n\t\"errors\"\n\t\"io\"\n\t\"strconv\"\n\t\"unicode/utf8\"\n\n\t\"github.com/mattermost/focalboard/server/services/audit\"\n)\n\nconst (\n\tBlockTitleMaxBytes  = 65535                  // Maximum size of a TEXT column in MySQL\n\tBlockTitleMaxRunes  = BlockTitleMaxBytes / 4 // Assume a worst-case representation\n\tBlockFieldsMaxRunes = 800000\n)\n\nvar (\n\tErrBlockEmptyBoardID            = errors.New(\"boardID is empty\")\n\tErrBlockTitleSizeLimitExceeded  = errors.New(\"block title size limit exceeded\")\n\tErrBlockFieldsSizeLimitExceeded = errors.New(\"block fields size limit exceeded\")\n)\n\n// Block is the basic data unit\n// swagger:model\ntype Block struct {\n\t// The id for this block\n\t// required: true\n\tID string `json:\"id\"`\n\n\t// The id for this block's parent block. Empty for root blocks\n\t// required: false\n\tParentID string `json:\"parentId\"`\n\n\t// The id for user who created this block\n\t// required: true\n\tCreatedBy string `json:\"createdBy\"`\n\n\t// The id for user who last modified this block","sourceCodeStart":4,"sourceCodeEnd":40,"githubUrl":"https://github.com/mattermost-community/focalboard/blob/a84bbb65e32edf972856b329417096ac413518e9/server/model/block.go#L4-L40","documentation":"ErrBlockFieldsSizeLimitExceeded is a sentinel validation error in the Focalboard server model layer. It is returned when a Block's fields JSON payload exceeds BlockFieldsMaxRunes (800,000 runes). It guards the database and API against oversized block payloads.","triggerScenarios":"Calling block IsValid() (and thus any API that inserts/updates a block, e.g. POST/PUT /api/v2/blocks or boards-and-blocks import) with a block whose 'fields' map serializes to more than 800000 runes.","commonSituations":"Clients importing large table/card contents, plugins or migrations writing huge custom field payloads, or copying blocks with embedded images/base64 data into the fields map.","solutions":["Reduce the data stored in the block's fields map (trim text content, move large blobs to attachments or separate blocks)","Split an oversized block (e.g. a huge table or text card) into multiple smaller blocks","If you legitimately need larger blocks, raise BlockFieldsMaxRunes in server/model/block.go and any matching client-side limit, understanding the storage impact","Check the server response for IsErrBadRequest handling — the API returns this as a 400 bad request, so inspect which block in a batch failed"],"exampleFix":"// before\nblock.Fields = bigFieldsMap // >800k runes, IsValid() fails\n// after\nif uniseg.GraphemeClusterCount(string(fieldsJSON)) > model.BlockFieldsMaxRunes {\n    bigFieldsMap = trimOrSplitFields(bigFieldsMap)\n}\nblock.Fields = bigFieldsMap // now under limit","handlingStrategy":"validation","validationCode":"function isBlockWithinSizeLimit(fields) {\n  const runes = uniseg ? uniseg.GraphemeClusterCount(JSON.stringify(fields)) : JSON.stringify(fields).length\n  return runes <= 800000\n}","typeGuard":null,"tryCatchPattern":"try {\n  await client.insertBlock(block)\n} catch (err) {\n  if (err.response?.status === 400 && /fields size limit/.test(err.message)) {\n    console.error('Block fields exceed 800k runes; split or trim the block', block.id)\n  } else throw err\n}","preventionTips":["Measure the serialized size of fields before insert/update","Split large content (tables, long text) into multiple blocks","Avoid storing base64/binary data in block fields","Keep a client-side constant mirroring BlockFieldsMaxRunes so limits stay in sync"],"tags":["go","validation","payload-size","bad-request"],"backgroundTag":"payload-size-limit-exceeded","analyzedSha":"a84bbb65e32edf972856b329417096ac413518e9","analyzedAt":"2026-08-30T09:22:20.720Z","schemaVersion":2},"datasetVersion":"2026-08-30T13:17:10.514Z"}