{"record":{"id":"e17d529b26aa95c7","repo":"jstedfast/MailKit","slug":"the-imap-server-does-not-support-the-metadata-extension","errorCode":null,"errorMessage":"The IMAP server does not support the METADATA extension.","messagePattern":"The IMAP server does not support the METADATA extension\\.","errorType":"exception","errorClass":"NotSupportedException","httpStatus":null,"severity":"error","filePath":"MailKit/Net/Imap/ImapClient.cs","lineNumber":2455,"sourceCode":"\t\t{\n\t\t\tif (path == null)\n\t\t\t\tthrow new ArgumentNullException (nameof (path));\n\n\t\t\tCheckDisposed ();\n\t\t\tCheckConnected ();\n\t\t\tCheckAuthenticated ();\n\n\t\t\treturn engine.GetFolder (path, cancellationToken);\n\t\t}\n\n\t\tImapCommand QueueGetMetadataCommand (MetadataTag tag, CancellationToken cancellationToken)\n\t\t{\n\t\t\tCheckDisposed ();\n\t\t\tCheckConnected ();\n\t\t\tCheckAuthenticated ();\n\n\t\t\tif ((engine.Capabilities & (ImapCapabilities.Metadata | ImapCapabilities.MetadataServer)) == 0)\n\t\t\t\tthrow new NotSupportedException (\"The IMAP server does not support the METADATA extension.\");\n\n\t\t\tvar ic = new ImapCommand (engine, cancellationToken, null, \"GETMETADATA \\\"\\\" %S\\r\\n\", tag.Id);\n\t\t\tic.RegisterUntaggedHandler (\"METADATA\", ImapUtils.UntaggedMetadataHandler);\n\t\t\tvar metadata = new MetadataCollection ();\n\t\t\tic.UserData = metadata;\n\n\t\t\tengine.QueueCommand (ic);\n\n\t\t\treturn ic;\n\t\t}\n\n\t\tstring? ProcessGetMetadataResponse (ImapCommand ic, MetadataTag tag)\n\t\t{\n\t\t\tic.ThrowIfNotOk (\"GETMETADATA\");\n\n\t\t\tvar metadata = (MetadataCollection) ic.UserData!;\n\t\t\tstring? value = null;\n","sourceCodeStart":2437,"sourceCodeEnd":2473,"githubUrl":"https://github.com/jstedfast/MailKit/blob/9d3859a7855e3e17582c07fd01972b8e262bf176/MailKit/Net/Imap/ImapClient.cs#L2437-L2473","documentation":"ImapClient.GetMetadata throws this NotSupportedException when the connected server did not advertise the METADATA or METADATA-SERVER capability (RFC 5464). MailKit checks engine.Capabilities before sending the GETMETADATA command rather than letting the server return a BAD response. It means the server simply cannot serve IMAP metadata entries.","triggerScenarios":"Calling ImapClient.GetMetadata on a connection whose server lacks both ImapCapabilities.Metadata and ImapCapabilities.MetadataServer; the check happens after CheckDisposed/CheckConnected/CheckAuthenticated, so it fires only on a live authenticated session.","commonSituations":"Connecting to IMAP servers that never implemented RFC 5464 (many older Courier/Dovecot builds without metadata enabled, Exchange in some configurations); assuming all servers support per-server metadata like /shared/comment.","solutions":["Check client.Capabilities.HasFlag(ImapCapabilities.Metadata) || HasFlag(ImapCapabilities.MetadataServer) before calling GetMetadata and skip or branch when absent.","Use server-level fallbacks: read the server vendor/info via the ID extension (ImapCapabilities.Id) instead of metadata entries like /shared/comment.","If you control the server, enable the METADATA extension (e.g. Dovecot: imap_metadata=yes plus metadata storage config).","Cache the capability check per connection to avoid repeated probes."],"exampleFix":"// before\nvar metadata = client.GetMetadata(cancellationToken);\n\n// after\nif (client.Capabilities.HasFlag(ImapCapabilities.Metadata) || client.Capabilities.HasFlag(ImapCapabilities.MetadataServer)) {\n    var metadata = client.GetMetadata(cancellationToken);\n} else {\n    var metadata = null; // server does not support METADATA; use ID/fallbacks\n}","handlingStrategy":"validation","validationCode":"bool canGetMetadata = (client.Capabilities & (ImapCapabilities.Metadata | ImapCapabilities.MetadataServer)) != 0;\nif (!canGetMetadata) return null; // skip metadata path","typeGuard":null,"tryCatchPattern":"try { return client.GetMetadata(token); } catch (NotSupportedException) { return null; }","preventionTips":["Always probe Capabilities after Connect/Authenticate before using extension commands.","Centralize capability checks in a helper instead of calling extension APIs directly.","Log unsupported extensions per server to plan feature fallbacks."],"tags":["imap","metadata","unsupported-feature","capability-check"],"backgroundTag":"unsupported-operation","analyzedSha":"9d3859a7855e3e17582c07fd01972b8e262bf176","analyzedAt":"2026-09-15T15:46:11.592Z","contentChangedAt":"2026-09-15T15:46:11.592Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}