# n8n Postgres Chat Memory: fixing 'Got unexpected type: user'

*Updated 2026-10-29.*

**Symptom:** an n8n AI Agent with **Postgres Chat Memory** worked for one message, then every later message in the same session fails with `Got unexpected type: user`. It happens after a **Google Gemini fallback model** answered. This is not a session-ID or connection problem. One bad row in the chat history table breaks reading the whole session.

*Disclosure: I work on MemorySync (I'm Mohammed, the founder). I drafted this page with AI assistance and checked it against the source issue and the MemorySync n8n guide. I didn't run any code on this page.*

## The question

In [n8n-io/n8n#33161](https://github.com/n8n-io/n8n/issues/33161), a self-hosted user (n8n 2.27.4) runs an AI Agent with Anthropic as the main model and Google Gemini as the fallback. When Gemini answers, the reply is stored in the Postgres Chat Memory table with `type: "user"` instead of `type: "ai"`. On the next message in that session, LangChain's `mapStoredMessageToChatMessage` throws `Got unexpected type: user` and the agent fails.

**Status (checked 2026-10-28 via the GitHub API):** open, 2 visible comments, last updated Jul 8, 2026. n8n's bot logged it internally (GHC-8825). One community comment suggests fixing it at the serialization boundary in n8n's Postgres Chat Memory node, before the message is written. No fix is linked in the issue yet.

## What you can do now

These are workarounds, not an official fix. *None of this was run for this page.*

- **Find the bad rows.** In the chat memory table your Postgres Chat Memory node writes to, look for rows in the affected session whose stored message has `type` set to `user`. The error only fires for sessions that contain one.
- **Unblock a stuck session.** Deleting or correcting those rows (back up first) lets the session load again. Changing the session ID also works, but the user loses that history.
- **Stop new bad writes.** Until the issue is fixed, avoid running Gemini as the fallback model on an agent that writes to Postgres Chat Memory, or use the same provider for primary and fallback.
- **Follow the issue** for a fix before upgrading or removing the workaround.

## Example: finding the rows and keeping the node config clean

n8n's Postgres Chat Memory uses LangChain's `PostgresChatMessageHistory`. In `@langchain/community` it creates a table with `session_id` and a JSONB `message` column, and stores the message `type` at the top level of that JSON. The default table name in the n8n node is `n8n_chat_histories`. So a read-only query to find affected rows looks like this. *I didn't run it. Change the table name if you set a different one in the node:*

```sql
SELECT id, session_id, message->>'type' AS type
FROM n8n_chat_histories
WHERE message->>'type' = 'user'
ORDER BY id;
```

On the node side, these are the parameters in the n8n source (`MemoryPostgresChat.node.ts` and the shared `descriptions.ts`). Changing the key starts a new, empty history. The bad rows stay on the old key.

```json
{
  "name": "Postgres Chat Memory",
  "type": "@n8n/n8n-nodes-langchain.memoryPostgresChat",
  "parameters": {
    "sessionIdType": "customKey",
    "sessionKey": "={{ $json.sessionId }}",
    "tableName": "n8n_chat_histories",
    "contextWindowLength": 5
  }
}
```

## Where MemorySync fits

Mostly it doesn't: this is a serialization bug in one memory node, and switching backends is a big change to dodge it. If you were already planning to move agent memory out of your own Postgres, the [MemorySync n8n guide](https://docs.memorysync.io/guides/n8n?utm_source=hashnode&utm_medium=organic_page&utm_campaign=v5_oct25&utm_content=pseo_n8n-postgres-chat-memory-unexpected-type-user) documents a MemorySync Chat Memory sub-node for the AI Agent's Memory port that keeps the conversation history in MemorySync. The node package is [memorysyncio/n8n-nodes-memorysync](https://github.com/memorysyncio/n8n-nodes-memorysync?utm_source=hashnode&utm_medium=organic_page&utm_campaign=v5_oct25&utm_content=tpl_n8n-nodes-memorysync). I haven't tested it with a Gemini fallback, so don't treat it as a confirmed fix for this error. It's also self-hosted only for now (n8n Cloud verification is in progress).

## Next step

Read the [MemorySync n8n guide](https://docs.memorysync.io/guides/n8n?utm_source=hashnode&utm_medium=organic_page&utm_campaign=v5_oct25&utm_content=pseo_n8n-postgres-chat-memory-unexpected-type-user). To see save and recall in your browser first, try the [MemorySync playground](https://memorysync.io/try?utm_source=hashnode&utm_medium=organic_page&utm_campaign=v5_oct25&utm_content=pseo_n8n-postgres-chat-memory-unexpected-type-user).

## Related pages

- [n8n WhatsApp AI agent memory: which Session ID to use](https://memorysync.hashnode.dev/n8n-whatsapp-ai-agent-memory-session-id)
- [LangGraph AsyncPostgresSaver: 'the connection is closed' in FastAPI](https://memorysync.hashnode.dev/langgraph-asyncpostgressaver-connection-is-closed-fastapi)
- [Codex CLI persistent memory with AGENTS.md and MCP](https://memorysync.hashnode.dev/codex-cli-persistent-memory-agents-md-mcp)

## Sources

- n8n-io/n8n#33161, "Postgres Chat Memory: Gemini fallback writes 'user' type messages causing 'Got unexpected type: user' deserialization error" (read 2026-10-28)
- MemorySync n8n guide: docs.memorysync.io/guides/n8n
