How to Migrate deepseek-chat and deepseek-reasoner to DeepSeek V4

To migrate deepseek-chat to DeepSeek V4 without changing its behavior, use deepseek-v4-flash and explicitly disable thinking. To migrate deepseek-reasoner, use deepseek-v4-flash and explicitly enable thinking.

Official cutoff: DeepSeek says deepseek-chat and deepseek-reasoner become fully retired and inaccessible after July 24, 2026 at 15:59 UTC. Do not keep either alias as a production fallback.

Last verified: July 22, 2026. During the transition period before the cutoff, DeepSeek routes deepseek-chat to the non-thinking mode of deepseek-v4-flash and deepseek-reasoner to the thinking mode of deepseek-v4-flash. Your application may therefore already be receiving V4 Flash responses through the old names, but the aliases themselves are disappearing.

Chat-Deep.ai is an independent guide and is not affiliated with DeepSeek. We checked the examples against DeepSeek’s official API documentation and syntax-checked the JavaScript and Python. We did not send a live request because no test API key was used. Run the smoke tests below in your own non-production environment before changing production traffic.

Behavior-preserving migration map

Legacy requestExplicit DeepSeek V4 replacementBehavior preserved
model: "deepseek-chat"model: "deepseek-v4-flash"
thinking: { type: "disabled" }
Non-thinking chat
model: "deepseek-reasoner"model: "deepseek-v4-flash"
thinking: { type: "enabled" }
Thinking response

Do not treat deepseek-v4-pro as the automatic successor to either alias. Pro is a deliberate model upgrade that should be selected after quality, latency, cost, and concurrency testing. Both V4 Flash and V4 Pro support thinking and non-thinking modes. See the separate DeepSeek V4 model guide before choosing between them.

DeepSeek’s official quick-start table
DeepSeek’s official quick-start table lists the V4 model IDs, unchanged base URLs, legacy aliases, mapping, and July 24, 2026 cutoff. Source: DeepSeek API Docs; verified July 22, 2026.

Migration steps

What changes—and what does not

ConfigurationMigration action
OpenAI-format base URLKeep https://api.deepseek.com
Raw chat operationKeep POST /chat/completions
DeepSeek API keyKeep the existing server-side key; DeepSeek does not document a new key type for V4
messagesKeep the supported system, user, assistant, and tool message structure
modelReplace the legacy alias with deepseek-v4-flash or a deliberately selected deepseek-v4-pro
thinkingSet it explicitly to preserve the old alias’s mode
Response parserVerify reasoning_content, streaming deltas, tool calls, finish reasons, and usage fields

DeepSeek lists a 1M context length and a maximum output of 384K for both V4 models. The output figure is a maximum, not a default, and the combined input plus generated tokens must fit within the model context. Keep a realistic max_tokens value and handle finish_reason: "length" rather than assuming every response reaches your requested endpoint.

1. Find every use of the legacy aliases

Search more than application source files. Model names are commonly stored in environment variables, YAML, JSON, deployment manifests, gateway routing rules, observability dashboards, test fixtures, fallback arrays, database configuration, and agent model registries.

rg -n --hidden \
  --glob '!node_modules' \
  --glob '!.git' \
  'deepseek-chat|deepseek-reasoner' .

Classify every match by intended behavior:

  • Fast or ordinary chat: map to V4 Flash with thinking disabled.
  • Reasoning workflow: map to V4 Flash with thinking enabled.
  • Quality-first workload: evaluate V4 Pro separately; do not assume it is a one-for-one replacement.
  • Fallback: replace or remove the legacy name. A retired alias is not a safe rollback target.

Store the model and mode together

The legacy names encoded both a model route and a thinking choice. V4 separates those decisions. Do not keep a single environment variable that changes the model while leaving the mode implicit. Define an application-level profile that changes both values atomically:

const DEEPSEEK_PROFILES = {
  chat: {
    model: "deepseek-v4-flash",
    thinking: { type: "disabled" },
  },
  reasoner: {
    model: "deepseek-v4-flash",
    thinking: { type: "enabled" },
  },
};

const profileName = process.env.DEEPSEEK_PROFILE ?? "chat";
const profile = DEEPSEEK_PROFILES[profileName];

if (!profile) {
  throw new Error("DEEPSEEK_PROFILE must be chat or reasoner.");
}

This pattern prevents a partial deployment in which the canonical V4 name is updated but the intended thinking mode is lost. If different routes need Flash and Pro, create separate reviewed profiles rather than letting arbitrary model strings pass from user input.

2. Migrate Node.js requests

The examples use the OpenAI JavaScript package with DeepSeek’s unchanged base URL. Keep the API key on the server.

npm install openai

Replace deepseek-chat

Before:

const response = await client.chat.completions.create({
  model: "deepseek-chat",
  messages,
});

After, preserving non-thinking behavior:

import OpenAI from "openai";

const apiKey = process.env.DEEPSEEK_API_KEY;

if (!apiKey) {
  throw new Error("Set DEEPSEEK_API_KEY before starting the app.");
}

const client = new OpenAI({
  apiKey,
  baseURL: "https://api.deepseek.com",
});

const messages = [
  {
    role: "user",
    content: "Return a one-sentence deployment summary.",
  },
];

const response = await client.chat.completions.create({
  model: "deepseek-v4-flash",
  messages,
  thinking: { type: "disabled" },
  max_tokens: 300,
  stream: false,
});

console.log(response.choices[0].message.content);

The explicit thinking: { type: "disabled" } is essential. DeepSeek documents thinking as enabled by default for explicit V4 model IDs. Changing only the model name can therefore alter response fields, latency, token use, and the effect of sampling parameters.

Replace deepseek-reasoner

Before:

const response = await client.chat.completions.create({
  model: "deepseek-reasoner",
  messages,
});

After, preserving thinking behavior:

const response = await client.chat.completions.create({
  model: "deepseek-v4-flash",
  messages,
  thinking: { type: "enabled" },
  max_tokens: 1200,
  stream: false,
});

const message = response.choices[0].message;

console.log("Reasoning:", message.reasoning_content);
console.log("Answer:", message.content);

You may set reasoning_effort: "high" or "max" when you deliberately want to pin an effort level. Omitting it retains DeepSeek’s documented defaults: high for regular thinking requests, with some complex agent requests automatically using max.

For project structure, TypeScript considerations, and error handling, use the dedicated DeepSeek Node.js and TypeScript guide.

3. Migrate Python requests

DeepSeek instructs Python OpenAI SDK users to pass the thinking object through extra_body.

Python replacement for deepseek-chat

import os
from openai import OpenAI

client = OpenAI(
    api_key=os.environ["DEEPSEEK_API_KEY"],
    base_url="https://api.deepseek.com",
)

response = client.chat.completions.create(
    model="deepseek-v4-flash",
    messages=[
        {
            "role": "user",
            "content": "Return a one-sentence deployment summary.",
        }
    ],
    max_tokens=300,
    stream=False,
    extra_body={"thinking": {"type": "disabled"}},
)

print(response.choices[0].message.content)

Python replacement for deepseek-reasoner

response = client.chat.completions.create(
    model="deepseek-v4-flash",
    messages=[
        {
            "role": "user",
            "content": "Compare two deployment options and explain the tradeoffs.",
        }
    ],
    max_tokens=1200,
    stream=False,
    extra_body={"thinking": {"type": "enabled"}},
)

message = response.choices[0].message
print("Reasoning:", message.reasoning_content)
print("Answer:", message.content)

See the DeepSeek Python SDK guide for environment setup and a larger production structure.

4. Verify the migration with cURL

A small non-production request confirms that the new model ID and mode reach the API. This example tests the behavior-preserving replacement for deepseek-chat:

curl https://api.deepseek.com/chat/completions \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer ${DEEPSEEK_API_KEY}" \
  -d '{
    "model": "deepseek-v4-flash",
    "messages": [
      {
        "role": "user",
        "content": "Return exactly: V4 migration test passed"
      }
    ],
    "thinking": {
      "type": "disabled"
    },
    "max_tokens": 30,
    "stream": false
  }'

Do not publish the response as proof that every workflow is compatible. A simple request verifies connectivity; it does not validate streaming, JSON Output, tools, multi-turn state, rate limits, or production behavior.

Check canonical model IDs

curl https://api.deepseek.com/models \
  -H "Authorization: Bearer ${DEEPSEEK_API_KEY}"

DeepSeek’s List Models reference documents deepseek-v4-flash and deepseek-v4-pro. Add a deployment check or configuration allowlist that rejects deepseek-chat and deepseek-reasoner before release.

5. Account for thinking-mode differences

Official DeepSeek V4 thinking mode toggle and reasoning effort controls
DeepSeek documents an explicit thinking toggle, high/max effort controls, and a default of enabled for V4. Source: DeepSeek Thinking Mode documentation; verified July 22, 2026.
AreaNon-thinking migrationThinking migration
Togglethinking.type: "disabled"thinking.type: "enabled"
Final answerRead message.contentRead message.content
ReasoningDo not require a reasoning fieldHandle message.reasoning_content separately
StreamingHandle delta.contentHandle delta.reasoning_content and delta.content
Sampling controlstemperature and top_p can affect generationtemperature, top_p, presence_penalty, and frequency_penalty are accepted but have no effect
EffortNot applicablereasoning_effort: "high" or "max"

Compatibility mappings also accept low and medium as high, and xhigh as max. Prefer DeepSeek’s native documented values in new configuration. The full DeepSeek Thinking Mode guide explains reasoning responses and multi-turn handling.

6. Test streaming, tools, and structured workflows

Streaming

A parser built for deepseek-chat may only collect delta.content. In thinking mode, DeepSeek returns reasoning through delta.reasoning_content separately from final-answer content. Test both streams and confirm your UI, logs, and token accounting do not merge reasoning into the user-facing answer.

Tool-call history

For a thinking-mode turn that performs a tool call, DeepSeek requires the assistant’s reasoning_content to be passed back in subsequent requests. The safest documented pattern is to preserve and append the complete assistant message object before adding the tool result. Missing reasoning history can produce HTTP 400.

// Preserve content, reasoning_content, and tool_calls together.
messages.push(response.choices[0].message);

messages.push({
  role: "tool",
  tool_call_id: toolCall.id,
  content: JSON.stringify(toolResult),
});

Test a complete tool loop, not only the first model response. See the DeepSeek Tool Calls guide for validation and execution boundaries.

JSON Output and FIM

DeepSeek lists JSON Output and Tool Calls for both V4 models. FIM Completion is listed only for non-thinking mode. Regression-test every specialized workflow rather than treating a successful text prompt as complete migration coverage.

Cache and usage fields

DeepSeek context caching is enabled automatically; the model-name migration does not require a cache flag. Log usage.prompt_cache_hit_tokens, usage.prompt_cache_miss_tokens, output tokens, and reasoning tokens during the canary. A cache hit is best effort and should not be assumed from one repeated request.

7. Production migration and validation plan

  1. Inventory both aliases. Search code, environment values, proxies, manifests, agent settings, tests, dashboards, and fallback lists.
  2. Map by behavior. Use Flash plus thinking disabled for deepseek-chat; use Flash plus thinking enabled for deepseek-reasoner.
  3. Validate configuration in CI. Fail the build when either legacy string remains in deployable configuration.
  4. Deploy behind configuration control. Use a model setting or feature flag so the canonical ID can be changed without a code release.
  5. Canary non-production traffic. Compare answer format, latency, token usage, cache fields, finish reasons, and errors.
  6. Test both response paths. Run non-streaming and SSE tests for non-thinking and thinking requests.
  7. Run a full tool loop. Preserve the complete assistant message and verify that multi-turn tool calls do not return HTTP 400.
  8. Regression-test specialized features. Include JSON Output, Tool Calls, FIM where used, stop sequences, and realistic context lengths.
  9. Load-test the selected model. Flash and Pro have different documented account concurrency, so do not replace an alias with Pro without capacity testing.
  10. Remove the old fallback. Roll back to the previous application build with canonical V4 configuration—not to a retired model alias.

What to monitor during the canary

SignalWhy it matters
Requested model and thinking typeProves the application sent the intended atomic profile
Returned model fieldDetects unexpected routing or configuration
HTTP status and provider request IDSupports error grouping and escalation without logging prompts
Latency to first token and total durationReveals accidental thinking activation or a tier change
finish_reasonDetects truncation, tool calls, filtering, or resource interruption
Input, output, reasoning, cache-hit, and cache-miss tokensMeasures the actual cost and cache behavior of the selected profile
Tool-loop HTTP 400 rateDetects missing reasoning_content history
HTTP 429 rate and retry countShows whether the selected model exceeds account concurrency

Log metadata needed for operations, but do not place API keys, private prompts, raw customer documents, or unredacted personal data in observability systems. Compare the canary with a dated baseline; do not judge migration success from one hand-picked prompt.

Minimum test matrix

TestExpected check
Flash, thinking disabledFinal content is parsed and the application does not depend on reasoning output
Flash, thinking enabledreasoning_content and final content are handled separately
Streaming, both modesReasoning and answer deltas are routed correctly; stream completion is detected
Two-turn chatConversation history remains valid
Thinking plus toolsComplete assistant reasoning/tool history is replayed; no HTTP 400
JSON OutputOutput parses and satisfies application validation
Context boundaryfinish_reason and partial output are handled safely
Usage and cacheToken and cache fields are recorded without assuming every retry hits cache
Concurrency429 retry and backoff behavior works at expected load
Model allowlistDeployment contains only canonical V4 model IDs

Compare Flash and Pro on your prompts before changing tiers. Use the dedicated DeepSeek API pricing page for dated pricing and concurrency values rather than copying a price snapshot into long-lived migration code.

Migration troubleshooting

SymptomLikely causeAction
Legacy model stops responding after the cutoffThe alias was not replacedUse a canonical V4 ID and explicit thinking mode. DeepSeek does not document a guaranteed post-retirement error code.
deepseek-chat replacement is slower or returns reasoningdeepseek-v4-flash defaulted to thinking enabledAdd thinking: { type: "disabled" }
No effect from temperature or penaltiesThinking mode is enabledDisable thinking when those controls are required
HTTP 400 during a tool loopPrior assistant reasoning_content was not preservedAppend the complete assistant message before tool results
HTTP 401Missing or invalid DeepSeek API keyVerify the server environment and authorization header
HTTP 422Invalid request parametersCompare the request with the V4 Chat Completion schema
HTTP 429Account or model concurrency exceededApply backoff and test against the selected model’s concurrency
Answer is cut offmax_tokens or total context limit reachedInspect finish_reason and adjust the request safely
Unexpected cost or latency after moving to ProPro was treated as a direct alias replacementReturn the canary to Flash and evaluate Pro as a separate upgrade

For status-specific diagnostics, see the DeepSeek API error codes guide. For the request and response structure, use the Chat Completion guide.

Frequently asked questions

What is the direct replacement for deepseek-chat?

The behavior-preserving replacement is deepseek-v4-flash with thinking.type explicitly set to disabled.

What is the direct replacement for deepseek-reasoner?

The behavior-preserving replacement is deepseek-v4-flash with thinking.type explicitly set to enabled.

Is deepseek-v4-pro the new name for deepseek-reasoner?

No. DeepSeek documents the legacy reasoner alias as mapping to the thinking mode of V4 Flash during the transition. V4 Pro is an optional model choice that needs separate quality, cost, latency, and capacity evaluation.

Can I replace only the model string?

Not safely for deepseek-chat. Explicit V4 models default to thinking enabled, so you must disable thinking to preserve non-thinking behavior. For deepseek-reasoner, the default aligns with thinking mode, but setting it explicitly makes the migration auditable and prevents configuration ambiguity.

Do I need a new base URL or API key?

No change is documented for the canonical OpenAI-format base URL or DeepSeek API key. Keep https://api.deepseek.com and your existing secured DeepSeek key.

Which error will the retired aliases return?

DeepSeek says the aliases become inaccessible after the cutoff but does not specify a guaranteed HTTP status for retired-name requests. Do not build a fallback around an assumed 404 or 422 response.

Should I keep the old aliases as rollback values?

No. A rollback should restore a known application version while retaining canonical V4 model IDs. The retired aliases cannot provide a dependable post-cutoff rollback path.

Official sources

After publishing, add this migration guide to the API & Developers section of the DeepSeek documentation hub.