{
  "version": 1,
  "slug": "openai-flex-mode-csv-processing-costs",
  "title": "OpenAI Flex Mode: Cut CSV AI Processing Costs by 50%",
  "excerpt": "Use OpenAI Flex Mode in Datablist to run row-level AI prompts on CSV or Excel files at lower cost when the job can wait longer.",
  "cover": {
    "src": "/howto_images/openai-flex-mode-csv-processing-costs/openai-flex-mode-csv-processing-costs-cover.png",
    "optimized": "https://www.datablist.com/_next/image?url=%2Fhowto_images%2Fopenai-flex-mode-csv-processing-costs%2Fopenai-flex-mode-csv-processing-costs-cover.png&w=1200&q=75"
  },
  "url": "https://www.datablist.com/how-to/openai-flex-mode-csv-processing-costs",
  "contentMarkdown": "\nAn OpenAI prompt can look cheap when you test one row. Repeat it across 10,000 or 100,000 spreadsheet rows, and the token bill becomes much harder to ignore. **OpenAI Flex Mode** lowers that processing cost for supported models when your job can accept slower, less predictable responses.\n\nDatablist makes this tradeoff practical. You can import a CSV or Excel file, run one prompt per row with the Ask ChatGPT/OpenAI enrichment, preview the output, enable Flex, and review failures without building an API pipeline. If you need the broader setup first, use the guide to [run ChatGPT prompts on CSV or Excel rows](/how-to/run-chatgpt-prompt-on-excel-csv-rows).\n\nIn this guide, I’ll use a support-ticket classification job to show how I decide whether Flex fits, estimate Standard versus Flex costs, configure the run, and handle delayed or failed rows. The goal is not a faster model or better answers. It is the same row-level task at a lower token price when time matters less than cost.\n\n## Quick links {#quick-links}\n- [What OpenAI Flex Mode changes](#what-openai-flex-mode-changes)\n- [When Flex Mode is the right tradeoff](#when-flex-mode-is-the-right-tradeoff)\n- [Example CSV and prompt](#example-csv-and-prompt)\n- [Estimate Standard vs Flex cost before you run](#estimate-standard-vs-flex-cost-before-you-run)\n- [Configure Ask ChatGPT/OpenAI in Datablist](#configure-ask-chatgptopenai-in-datablist)\n- [Preview, run, and review the results](#preview-run-and-review-the-results)\n\n## What OpenAI Flex Mode changes {#what-openai-flex-mode-changes}\nFlex is a service tier for supported OpenAI API models. A request still goes through the Responses API or Chat Completions API, but it uses `service_tier: \"flex\"`. In return for accepting slower processing and occasional capacity shortages, you pay the Flex token rates.\n\nOpenAI says Flex tokens use Batch API rates. On the [OpenAI pricing page](https://developers.openai.com/api/docs/pricing) checked on July 16, 2026, the listed Flex rates matched Batch rates. For `gpt-5.4-mini`, Flex input and output prices were 50% below Standard prices.\n\nThis is a processing choice, not a different model. Your prompt, input rows, and output schema can stay the same. The tradeoff is operational:\n\n- responses can take longer\n- completion time is less predictable\n- request timeouts are more likely\n- OpenAI may return `429 Resource Unavailable` when Flex capacity is unavailable\n\nOpenAI’s [Flex processing guide](https://developers.openai.com/api/docs/guides/flex-processing) says resource-unavailable requests are not charged. You can retry them later or switch the failed rows to Standard processing when completion matters more than savings.\n\nFlex is also separate from the OpenAI Batch API. Batch is a dedicated asynchronous API for submitted jobs. Flex is a service tier on supported normal API requests. Datablist handles the row-by-row workflow around those requests, so you do not need to create and monitor a Batch job yourself.\n\nIt is not part of the ChatGPT web subscription either. API usage and ChatGPT app usage have separate billing and workflows. In Datablist, you can use your own OpenAI API key or Datablist credits for supported models.\n\n> 🔑 **The key rule**\n>\n> Flex changes processing cost and timing. It does not improve output quality, and it is not available for every model.\n\nFor more background on running repeated prompts at scale, see [batch LLM processing](/learn/ai-automation/batch-llm-processing).\n\n## When Flex Mode is the right tradeoff {#when-flex-mode-is-the-right-tradeoff}\nI start with one question: **Can this run wait longer if it costs less?**\n\nIf the answer is yes, Flex is worth considering. Good candidates include overnight ticket classification, review summarization, structured extraction from text, and background lead categorization. A large, non-urgent job to [translate ecommerce catalogs with ChatGPT](/how-to/translate-ecommerce-catalog-chatgpt) can also fit, provided the selected model supports Flex.\n\nThese tasks share three traits. They repeat a stable prompt across many rows, produce an output you can review later, and do not leave a person waiting for each response.\n\nStay on Standard processing when:\n\n- someone needs the result during the same session\n- a failed or delayed row blocks an urgent workflow\n- your selected model does not support Flex\n- the job needs predictable latency more than lower cost\n\nI also avoid moving a new prompt directly to Flex for a large run. First, I stabilize the prompt and output schema on a small preview. Flex makes processing cheaper, but it cannot rescue vague instructions, unnecessary input text, or oversized outputs.\n\n> 💡 **Use Flex after the prompt is stable**\n>\n> Test 10 to 20 rows first. Once the labels, summaries, and review rules look right, Flex becomes a sensible default for the background run.\n\nDatablist’s [Ask ChatGPT/OpenAI enrichment](/enrichments/run-chatgpt-bulk) suits this pattern because it runs one prompt per row, stores the response in properties, and keeps row-level processing states for review.\n\n## Example CSV and prompt {#example-csv-and-prompt}\nI’ll use Datablist’s Support tickets AI sample. You can find it in the [sample CSV file library](/learn/csv/download-sample-csv-files). The 100-row version is small enough for setup and screenshots, while the [10,000-row version](https://drive.google.com/uc?id=1XkRTXRcmZg4f5LmTrf1IlAi6ddqKwD1g&export=download) makes the cost difference easier to see.\n\nThe input contains these useful columns:\n\n- `Ticket Subject`\n- `Ticket Text`\n- `Customer Plan`\n- `Priority Hint`\n\nEach row needs the same job: classify the ticket, assign urgency, summarize the issue, and flag uncertain cases for review. This is a strong Flex candidate because the run can happen in the background and each output stays short.\n\nHere is the prompt I would start with:\n\n> Classify this support ticket for operational reporting.\n>\n> Ticket subject: {{Ticket Subject}}\n>\n> Ticket text: {{Ticket Text}}\n>\n> Customer plan: {{Customer Plan}}\n>\n> Priority hint: {{Priority Hint}}\n>\n> Return short structured values only.\n\nThe expressions inside double braces are [prompt variables](/learn/ai-automation/prompt-variables). Datablist replaces them with values from the row being processed.\n\n![Prompt variables insert ticket fields into the OpenAI request](/howto_images/chatgpt-csv-excel/call_properties_in_prompt.png)\n\nI prefer four [structured outputs](/learn/ai-automation/structured-llm-output) instead of one block of prose:\n\n- `Ticket Topic`: Billing, Bug, Feature Request, Account Access, Cancellation, or Other\n- `Urgency`: Low, Medium, or High\n- `One Sentence Summary`: one concise sentence\n- `Needs Review`: Yes when the ticket is ambiguous, incomplete, conflicts with the priority hint, or returns no result\n\nThis schema makes the result easier to filter and keeps output tokens under control. It also separates uncertain rows from the normal queue instead of hiding doubt inside a paragraph.\n\n![Configure separate output properties for the structured OpenAI response](/howto_images/chatgpt-csv-excel/add_new_property.png)\n\n## Estimate Standard vs Flex cost before you run {#estimate-standard-vs-flex-cost-before-you-run}\nCost estimation belongs before the full setup. You want to know whether the savings justify slower processing for your actual row count.\n\nThe calculation uses two parts:\n\n- input cost = rows × average input tokens per row × input price per token\n- output cost = rows × average output tokens per row × output price per token\n- total cost = input cost + output cost\n\nFor this example, I’ll use `gpt-5.4-mini` with 250 input tokens and 30 output tokens per row. The prices below were checked on July 16, 2026:\n\n<div class=\"preview-table\">\n<div class=\"table-wrapper\">\n<table>\n<thead>\n<tr>\n<th>Service tier</th>\n<th>Input price per 1M tokens</th>\n<th>Output price per 1M tokens</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td>Standard</td>\n<td>$0.75</td>\n<td>$4.50</td>\n</tr>\n<tr>\n<td>Flex</td>\n<td>$0.375</td>\n<td>$2.25</td>\n</tr>\n</tbody>\n</table>\n</div>\n</div>\n\nFor 1,000 rows, the Standard input cost is 250,000 × $0.75 / 1,000,000, or $0.1875. The output cost is 30,000 × $4.50 / 1,000,000, or $0.135. Together, the run costs about $0.32.\n\nFlex halves both rates in this example, so the same workload costs about $0.16.\n\n<div class=\"preview-table\">\n<div class=\"table-wrapper\">\n<table>\n<thead>\n<tr>\n<th>Rows</th>\n<th>Standard estimate</th>\n<th>Flex estimate</th>\n<th>Estimated savings</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td>1,000</td>\n<td>$0.32</td>\n<td>$0.16</td>\n<td>$0.16</td>\n</tr>\n<tr>\n<td>10,000</td>\n<td>$3.23</td>\n<td>$1.61</td>\n<td>$1.61</td>\n</tr>\n<tr>\n<td>100,000</td>\n<td>$32.25</td>\n<td>$16.13</td>\n<td>$16.13</td>\n</tr>\n</tbody>\n</table>\n</div>\n</div>\n\nThe individual numbers are small because the prompt and outputs are compact. Replace a short ticket with a long transcript, product description, or scraped page, and the input cost grows quickly. Ask for a detailed response instead of four short fields, and the output cost rises too.\n\nI use this table as a method, not a quote. Before a real run, update four inputs: model, service tier prices, average input tokens, and average output tokens. Model availability and pricing change, so recheck OpenAI’s page rather than copying an old estimate.\n\nIf you use your own API key, OpenAI bills your account. If you use Datablist credits, Datablist converts the processing usage into credits for supported models. The exact credit usage depends on the model and token consumption, so I still keep prompts and outputs compact.\n\n> ⚠️ **Pricing changes**\n>\n> The 50% saving applies to the checked supported model and prices above. Treat the calculation as a reusable template, not a permanent price list or a promise for every model.\n\n## Configure Ask ChatGPT/OpenAI in Datablist {#configure-ask-chatgptopenai-in-datablist}\nOnce the workload and savings make sense, configure the enrichment. I keep the setup deliberate because one loose setting gets multiplied by every row.\n\n### 1. Import the CSV or open a collection {#1-import-the-csv-or-open-a-collection}\nImport the CSV or Excel file into Datablist, or open a collection where the rows already exist. Confirm the four input columns contain useful values. I filter out blank ticket text before calling the model because paying for rows with no meaningful input helps nobody.\n\n### 2. Select Ask ChatGPT/OpenAI {#2-select-ask-chatgptopenai}\nOpen **Enrich** and choose **Ask ChatGPT/OpenAI**. This enrichment sends one request per selected row and writes the answer into the output properties you configure.\n\n### 3. Choose how to pay for processing {#3-choose-how-to-pay-for-processing}\nUse your own OpenAI API key for direct OpenAI billing, or choose Datablist credits when supported for your selected model and account. The processing tier decision stays separate from the payment method.\n\n### 4. Add the row-level prompt {#4-add-the-row-level-prompt}\nPaste the support-ticket prompt and insert each field through the variable picker. I keep the instruction short and put the desired format at the end. Repeating background information in every row wastes input tokens.\n\nIf a ticket field is often empty, decide how the model should handle it. For example, `Needs Review = Yes` is safer than letting the model invent missing context.\n\n### 5. Configure structured output properties {#5-configure-structured-output-properties}\nEnable the structured output option and add the four properties from the example. Use short descriptions for each field and define the allowed labels where relevant.\n\nStructured output saves cleanup later, but its main value here is control. A field named `Urgency` with three allowed labels gives the model less room to return a long explanation.\n\n### 6. Select a Flex-compatible model {#6-select-a-flex-compatible-model}\nOpen the model selector and choose a model marked **flex compatible**. Datablist only shows the Flex setting when the selected model supports it.\n\n![OpenAI model selector showing Flex-compatible models in Datablist](/howto_images/openai-flex-mode-csv-processing-costs/openai-flex-compatible-models.png)\n\nFor this cost example, I use `GPT-5.4 mini`. Do not assume the same list will remain available. Check the label in Datablist and the current OpenAI pricing page when you start a new workflow.\n\n### 7. Enable Flex Mode {#7-enable-flex-mode}\nTurn on **Advanced Settings**, then enable **Use Flex Mode**.\n\n![Use Flex Mode enabled in Datablist advanced settings](/howto_images/openai-flex-mode-csv-processing-costs/enable-openai-flex-mode-settings.png)\n\nIf the toggle does not appear, the selected model is not marked as Flex compatible in Datablist. Pick a supported model or keep Standard processing.\n\n### 8. Start with the default timeout {#8-start-with-the-default-timeout}\nDatablist’s current default Flex timeout is 360 seconds, or 6 minutes. I leave it unchanged for the first preview. Increase it only after timeout failures and only when the job can wait longer.\n\nThe accepted timeout range is 30 to 1,500 seconds. A higher timeout gives a slow request more time to finish, but it does not guarantee capacity or a response within a fixed time.\n\n### 9. Keep caching when duplicates may repeat {#9-keep-caching-when-duplicates-may-repeat}\nDatablist can cache identical prompts with the same settings for 48 hours. If duplicate tickets or descriptions generate the same request, a cached result avoids another paid call.\n\nCaching does not replace deduplication. I still filter unnecessary rows first, then use caching as a second layer.\n\n### 10. Limit output tokens and control concurrency {#10-limit-output-tokens-and-control-concurrency}\nSet a max-token value suited to four short fields. Do not leave room for an essay when you need labels and one sentence.\n\nIf you use your own API key, keep concurrent calls conservative. More concurrency does not make Flex capacity predictable, and it can add rate-limit errors. I prefer a steady background run over a burst followed by retries.\n\n> 📘 **No Flex toggle?**\n>\n> Check the model label first. Datablist only exposes Flex settings for models marked as compatible. Otherwise, choose another supported model or run on Standard.\n\n## Preview, run, and review the results {#preview-run-and-review-the-results}\nPreview 10 to 20 rows before you process the complete file. I still do this when the prompt looks obvious. Small wording changes can alter labels, output length, and token usage across thousands of requests.\n\nCheck these points in the preview:\n\n- every expected property receives a value\n- `Ticket Topic` uses consistent labels\n- `Urgency` considers the ticket text instead of copying `Priority Hint`\n- summaries stay to one sentence\n- `Needs Review` catches missing or conflicting information\n- input and output lengths remain close to your cost assumptions\n\nA representative result should look like this:\n\n<div class=\"preview-table\">\n<div class=\"table-wrapper\">\n<table>\n<thead>\n<tr>\n<th>Ticket Subject</th>\n<th>Ticket Topic</th>\n<th>Urgency</th>\n<th>One Sentence Summary</th>\n<th>Needs Review</th>\n</tr>\n</thead>\n<tbody>\n<tr>\n<td>Cannot log in after password reset</td>\n<td>Account Access</td>\n<td>High</td>\n<td>Customer cannot access the account after resetting the password.</td>\n<td>No</td>\n</tr>\n</tbody>\n</table>\n</div>\n</div>\n\nIf the model returns inconsistent labels, tighten the allowed values before the full run. If summaries are too long, shorten the instruction and reduce max tokens. Fixing the prompt after 10 rows is cheap. Fixing it after 100,000 rows is not.\n\nWhen the preview looks stable, run the enrichment on the intended rows. Datablist tracks processed items, which helps you avoid calling OpenAI again for completed rows.\n\nAfter the run, filter rows with failed, timed-out, or no-result statuses. Review a sample from each group before retrying:\n\n- retry with Flex when the error looks temporary and the job can wait\n- increase the Flex timeout when requests consistently time out on valid long inputs\n- retry critical rows with Standard processing when completion or speed matters more than cost\n- correct missing input data before spending another request\n\n![Review row-level OpenAI results in the Datablist collection](/howto_images/chatgpt-csv-excel/results_of_running_chatgpt_on_an_excel_file.png)\n\nOnce the results pass review, export the processed collection to CSV or Excel. Keep `Needs Review` in the export if another person will validate uncertain tickets downstream.\n\n## Ways to reduce cost further {#ways-to-reduce-cost-further}\nFlex is one cost lever. In many files, the bigger savings come from sending less data and avoiding unnecessary calls.\n\n### Filter rows before processing {#filter-rows-before-processing}\nRemove blank rows, already-classified tickets, and records outside the job’s scope. The cheapest request is the one you never send.\n\n### Trim the prompt and inputs {#trim-the-prompt-and-inputs}\nInclude only fields the model needs. A customer ID may help you join results later, but the model does not need to read it. The same applies to long signatures, quoted email threads, and boilerplate text inside a ticket.\n\n### Keep outputs structured and short {#keep-outputs-structured-and-short}\nUse labels, booleans, and concise summaries. Output tokens often cost more than input tokens, so a small max-token limit can make a meaningful difference.\n\n### Cache repeated prompts {#cache-repeated-prompts}\nEnable caching when identical requests may recur. This works well for duplicated descriptions or repeated text after importing several files.\n\n### Choose the smallest model which meets the quality bar {#choose-the-smallest-model-which-meets-the-quality-bar}\nPreview the same representative rows before changing models. A cheaper model is useful only if the labels and review rate remain acceptable.\n\n### Prefer a dedicated enrichment for fixed tasks {#prefer-a-dedicated-enrichment-for-fixed-tasks}\nAn LLM is flexible, but it is not always the cheapest tool. If you only need a language label, use a [dedicated language detection workflow](/how-to/detect-language-each-row-dataset) instead of asking a general model to infer one for every row.\n\nI estimate cost after trimming the prompt and filtering the dataset. Otherwise, I am pricing a run I should not execute in the first place.\n\n## Limitations and troubleshooting {#limitations-and-troubleshooting}\nFlex introduces a few failure modes you should plan for.\n\n### The selected model does not show Flex {#the-selected-model-does-not-show-flex}\nSupport is limited and can change. If Datablist does not show the Flex toggle, switch to a model marked as compatible or use Standard processing. Do not force an unverified custom model into a large run.\n\n### Responses take longer than expected {#responses-take-longer-than-expected}\nSlower and less predictable processing is the core tradeoff. It does not indicate lower output quality. Let non-urgent rows continue, but move urgent work to Standard.\n\n### Rows time out {#rows-time-out}\nStart with Datablist’s 360-second default. If valid rows time out and the run can wait, increase the timeout within the supported range. If only a few critical rows fail, I usually retry those on Standard instead of slowing the complete job.\n\nOpenAI’s own SDK timeout is separate from Datablist’s Flex timeout setting. Follow the value shown in Datablist for this workflow.\n\n### OpenAI returns 429 Resource Unavailable {#openai-returns-429-resource-unavailable}\nFlex capacity can be unavailable. OpenAI says these requests are not charged. Retry later for the lowest cost, or use Standard processing when successful completion matters more.\n\n### Many rows hit rate limits {#many-rows-hit-rate-limits}\nFlex does not remove API rate limits. Reduce concurrent calls or process a smaller segment before retrying. A slower, controlled run is easier to review than a large wave of failures.\n\n### Flex, Batch API, and ChatGPT are getting confused {#flex-batch-api-and-chatgpt-are-getting-confused}\nKeep the boundaries simple:\n\n- Flex is a lower-cost service tier for supported API requests\n- Batch API is a separate asynchronous API\n- ChatGPT is the web and app product, not the row-level API workflow used here\n- Datablist provides the spreadsheet workflow and can use an API key or credits\n\n## Conclusion {#conclusion}\nUse Flex when the selected model supports it, cost matters more than response time, and the job can run in the background. Keep Standard processing for urgent, interactive, or failure-sensitive rows.\n\nMy preferred sequence is straightforward: estimate the token cost, filter the file, configure short structured outputs, preview 10 to 20 rows, enable Flex, run the list, and retry only the rows which need it. You keep the CSV workflow simple while cutting the checked model’s processing cost in half.\n\n## FAQ {#faq}\n### Does OpenAI Flex Mode always cut costs by 50%? {#does-openai-flex-mode-always-cut-costs-by-50}\nNo. On July 16, 2026, Flex input and output prices for `gpt-5.4-mini` were 50% below Standard prices and matched Batch API rates. Pricing and supported models can change. Check the current OpenAI pricing page for your model before calculating a large run.\n\n### Which OpenAI models support Flex Mode? {#which-openai-models-support-flex-mode}\nSupport is limited and changes over time. Check OpenAI’s current pricing list and look for the **flex compatible** label in Datablist’s model selector. The Flex toggle appears only for supported selections.\n\n### Is Flex Mode the same as the OpenAI Batch API? {#is-flex-mode-the-same-as-the-openai-batch-api}\nNo. Flex is a service tier for supported Responses or Chat Completions requests. Batch API is a separate asynchronous API for submitted batches. They can share token prices without being the same workflow.\n\n### Does Flex Mode change output quality? {#does-flex-mode-change-output-quality}\nFlex does not target a different quality level. It changes the request’s processing tier and timing. Your model, prompt, and output schema still determine the result. Preview rows because prompt quality matters regardless of tier.\n\n### What timeout should I use for Flex Mode in Datablist? {#what-timeout-should-i-use-for-flex-mode-in-datablist}\nStart with the 360-second default. Increase it only when valid rows time out and the job can wait longer. Datablist accepts values from 30 to 1,500 seconds. A longer timeout gives the request more time, but it does not guarantee availability.\n\n### Can I use Flex Mode with Datablist credits? {#can-i-use-flex-mode-with-datablist-credits}\nDatablist supports an OpenAI API key or Datablist credits for supported models and account setups. Credit use depends on the model and token usage, so preview a sample and keep inputs and outputs concise.\n\n### When should I stay on Standard processing? {#when-should-i-stay-on-standard-processing}\nUse Standard for interactive work, urgent jobs, rows someone is waiting on, unsupported models, or processes where delayed responses would cause a problem. You can also run the bulk job on Flex and retry a small critical subset on Standard.\n\n### Can I use Flex Mode with Excel files? {#can-i-use-flex-mode-with-excel-files}\nYes. Datablist imports CSV and Excel files. Flex applies to the supported OpenAI API request, not the source file type. The same row-level prompt workflow works for both formats.\n"
}