{"record":{"id":"93eab0325844afa7","repo":"gitroomhq/postiz-app","slug":"x-could-not-create-the-article-draft","errorCode":null,"errorMessage":"X could not create the article draft","messagePattern":"X could not create the article draft","errorType":"exception","errorClass":"BadBody","httpStatus":null,"severity":"error","filePath":"libraries/nestjs-libraries/src/integrations/social/x.provider.ts","lineNumber":1115,"sourceCode":"          : {}),\n      }),\n    });\n    const draftJson = (await draftResponse.json()) as {\n      data?: { id: string };\n      errors?: any[];\n    };\n\n    // The articles endpoints can return 2xx with an errors array (e.g. a\n    // rejected cover) - don't swallow it.\n    if (draftJson?.errors?.length) {\n      console.log(\n        'X article draft returned errors:',\n        JSON.stringify(draftJson.errors)\n      );\n    }\n\n    if (!draftJson?.data?.id) {\n      throw new BadBody(\n        this.identifier,\n        JSON.stringify(draftJson),\n        Buffer.from('{}'),\n        'X could not create the article draft'\n      );\n    }\n\n    if (settings.article_status !== 'published') {\n      return {\n        status: 'completed',\n        postId: draftJson.data.id,\n        releaseURL: `https://x.com/i/articles`,\n      };\n    }\n\n    const publishUrl = `https://api.x.com/2/articles/${draftJson.data.id}/publish`;\n    const publishResponse = await this.fetch(publishUrl, {\n      method: 'POST',","sourceCodeStart":1097,"sourceCodeEnd":1133,"githubUrl":"https://github.com/gitroomhq/postiz-app/blob/0f1647f7491a217d43eb5ae7a480484bdf0aff3e/libraries/nestjs-libraries/src/integrations/social/x.provider.ts#L1097-L1133","documentation":"When publishing an X (Twitter) article/long-form post, the draft-creation response has no data.id. The provider logs any returned errors and throws BadBody 'X could not create the article draft', meaning the article never entered draft state.","triggerScenarios":"X's article draft endpoint returns errors array (auth scope missing, validation error on the article payload) or an unexpected envelope without data.id.","commonSituations":"App/user token lacks the article (long-form) scope; article payload (title/body/markdown) fails X's validation; X Articles feature not enabled for the account; X API change to the article endpoint shape.","solutions":["Inspect draftJson (attached to the BadBody) for the errors array details","Verify the connected X account has Articles access enabled","Ensure the OAuth app requests the article/long-form write scopes","Simplify the article payload (plain text first) to isolate validation failures"],"exampleFix":null,"handlingStrategy":"validation","validationCode":"// before publishing, confirm the account can use articles\nconst me = await client.get('users/me');\nif (!(me.data as any)?.is_article_supported) { /* fall back to a regular post */ }","typeGuard":"const hasArticleDraftId = (j: unknown): j is { data: { id: string } } => Boolean((j as any)?.data?.id);","tryCatchPattern":"catch (e) { if (e instanceof BadBody && e.message.includes('article draft')) { /* inspect errors array, fall back to normal post if unsupported */ } throw e; }","preventionTips":["Request article write scopes in the OAuth flow","Validate article title/body length limits before submitting","Gate the article path on account capability, with a regular-post fallback"],"tags":["x-twitter","articles","draft-creation","validation"],"backgroundTag":"social-media-api-error","analyzedSha":"0f1647f7491a217d43eb5ae7a480484bdf0aff3e","analyzedAt":"2026-08-27T12:09:55.020Z","schemaVersion":2},"datasetVersion":"2026-08-27T13:17:12.746Z"}