ব্লগে ফিরে যান

API ও SDKগাইড

OpenAI-সামঞ্জস্যপূর্ণ API দিয়ে Python-এ ফাংশন কলিং

টুল পাঠান, tool_calls পড়ুন এবং role tool দিয়ে ফলাফল ফেরত দিন: MiniMax-M2.7 দিয়ে Python-এ দুই-ধাপের ফাংশন কলিং লুপ।

CheapTokens Team দ্বারাপ্রকাশিত হয়েছে আপডেট করা হয়েছে 10 মিনিট পড়ার সময়

দুই-ধাপের টুল কল লুপের ডায়াগ্রাম: টুল পাঠান, tool_calls পড়ুন, ফলাফল একটি টুল মেসেজ হিসেবে ফেরত দিন
এই পৃষ্ঠায়
  1. ফাংশন কলিং কীভাবে কাজ করে
  2. ক্লায়েন্ট সেট আপ করুন
  3. একটি ফাংশন ঘোষণা করুন এবং প্রথম অনুরোধ পাঠান
  4. আপনি যা দেখতে পাবেন
  5. একাধিক কল এবং দীর্ঘ লুপ
  6. কেন MiniMax-M2.7 টুল লুপের জন্য উপযুক্ত
  7. যদি এটি কাজ না করে
  8. পরবর্তী ধাপ

ফাংশন কলিং (টুল কলিং) মডেলকে আপনার কোডে একটি ফাংশন চালানোর অনুরোধ করতে দেয়। আপনি অনুরোধের সাথে একটি tools তালিকা পাঠান, মডেল টেক্সটের বদলে tool_calls দিয়ে উত্তর দেয়, আপনি নিজেই ফাংশনটি চালান এবং role: tool সহ একটি মেসেজে এর ফলাফল ফেরত পাঠান। এরপর মডেল চূড়ান্ত উত্তর লেখে। এই গাইডটি OpenAI-সামঞ্জস্যপূর্ণ এন্ডপয়েন্ট https://api.cheaptokens.dev/v1/chat/completions এর বিরুদ্ধে MiniMax-M2.7 (আইডি MiniMaxAI/MiniMax-M2.7, 180K কনটেক্সট, প্রতি উত্তরে সর্বোচ্চ 8,192 আউটপুট টোকেন) দিয়ে Python-এ সম্পূর্ণ লুপটি দেখায়।

ক্যাটালগের প্রতিটি মডেলের জন্য টুল কলিং সমর্থিত হিসেবে তালিকাভুক্ত (CheapTokens ডকস, 22 অক্টোবর 2026-এ যাচাই করা)। আপনার একটি API কী প্রয়োজন; যদি আপনি এখনও কোনো অনুরোধ না করে থাকেন, তাহলে আপনার প্রথম API অনুরোধ দিয়ে শুরু করুন।

ফাংশন কলিং কীভাবে কাজ করে#

মডেল কখনোই কিছু চালায় না। এটি শুধু একটি কাঠামোবদ্ধ অনুরোধ তৈরি করে: "get_weather কে {\"city\": \"Paris\"} দিয়ে কল করো"। আপনার প্রোগ্রাম আসল কাজটি করে এবং রিপোর্ট করে। এতে দুটি অনুরোধের একটি লুপ তৈরি হয়:

  1. অনুরোধ ১। আপনি ব্যবহারকারীর মেসেজ এবং tools তালিকা পাঠান। মডেল হয় টেক্সটে উত্তর দেয়, নয়তো এক বা একাধিক tool_calls ফেরত দেয়।
  2. আপনার কোড। আপনি প্রতিটি কল পার্স করেন, সংশ্লিষ্ট ফাংশন চালান এবং ফলাফল সংগ্রহ করেন।
  3. অনুরোধ ২। আপনি সম্পূর্ণ কথোপকথন আবার পাঠান: মূল মেসেজগুলো, tool_calls সহ অ্যাসিস্ট্যান্ট মেসেজ, এবং প্রতিটি কলেের জন্য একটি করে role: tool মেসেজ। মডেল ফলাফলগুলো ব্যবহার করে চূড়ান্ত উত্তর লেখে।

প্রতিটি অনুরোধ সম্পূর্ণ ইতিহাস আবার পাঠায়, তাই টুল লুপে একটি একক প্রশ্নের তুলনায় বেশি ইনপুট টোকেন ব্যবহৃত হয়। এটি যদি আপনার কাছে নতুন হয়, তাহলে টোকেন কী পড়ুন।

ক্লায়েন্ট সেট আপ করুন#

OpenAI SDK (pip install openai) ইনস্টল করুন এবং আপনার কী সোর্স কোডের বদলে একটি এনভায়রনমেন্ট ভেরিয়েবলে রাখুন:

bash
export CHEAPTOKENS_API_KEY="your-key-here"

বেস URL হলো https://api.cheaptokens.dev/v1। CheapTokens ডকুমেন্টেশন থেকে মডেল আইডি নিন: বিভিন্ন প্রোভাইডার একই মডেলের নাম ভিন্নভাবে দেয়। এই গাইডে MiniMaxAI/MiniMax-M2.7 ব্যবহার করা হয়েছে।

একটি ফাংশন ঘোষণা করুন এবং প্রথম অনুরোধ পাঠান#

একটি ফাংশন tools অ্যারেতে বর্ণনা করা হয়। প্রতিটি এন্ট্রিতে type: function এবং একটি function অবজেক্ট থাকে যাতে name, description এবং JSON Schema হিসেবে লেখা parameters থাকে। বর্ণনাটিই মডেল পড়ে সিদ্ধান্ত নেয় কখন ফাংশনটি কল করবে, তাই এটি একটি সংক্ষিপ্ত, নির্দিষ্ট বাক্য হিসেবে লিখুন।

নিচে একটি সম্পূর্ণ স্ক্রিপ্ট। আবহাওয়া ফাংশনটি ভুয়া ডেটাসহ একটি স্টাব, তাই উদাহরণটির জন্য অতিরিক্ত কোনো সেবা প্রয়োজন নেই:

python
import json
import os

from openai import OpenAI

client = OpenAI(
    base_url='https://api.cheaptokens.dev/v1',
    api_key=os.environ['CHEAPTOKENS_API_KEY'],
)
MODEL = 'MiniMaxAI/MiniMax-M2.7'


def get_weather(city: str) -> dict:
    # Stub with fake data: replace with a real lookup
    fake = {'Paris': 14, 'Tokyo': 19}
    return {'city': city, 'temp_c': fake.get(city, 10)}


FUNCTIONS = {'get_weather': get_weather}

tools = [
    {
        'type': 'function',
        'function': {
            'name': 'get_weather',
            'description': 'Get the current temperature in Celsius for a city.',
            'parameters': {
                'type': 'object',
                'properties': {
                    'city': {'type': 'string', 'description': 'City name, for example Paris'},
                },
                'required': ['city'],
            },
        },
    }
]

messages = [{'role': 'user', 'content': 'What is the weather in Paris right now?'}]

# Step 1: the model decides whether to call a function
first = client.chat.completions.create(model=MODEL, messages=messages, tools=tools)
message = first.choices[0].message

if not message.tool_calls:
    print(message.content)
    raise SystemExit

# Step 2: run every requested call and send the results back
messages.append(message)
for call in message.tool_calls:
    args = json.loads(call.function.arguments)
    result = FUNCTIONS[call.function.name](**args)
    messages.append({
        'role': 'tool',
        'tool_call_id': call.id,
        'content': json.dumps(result),
    })

final = client.chat.completions.create(model=MODEL, messages=messages, tools=tools)
print(final.choices[0].message.content)

তিনটি বিষয় লুপটি কাজ করবে কিনা তা নির্ধারণ করে:

  • call.function.arguments একটি JSON স্ট্রিং, ডিকশনারি নয়। এটি json.loads দিয়ে পার্স করুন।
  • প্রতিটি role: tool মেসেজে যে কলের উত্তর দিচ্ছে তার tool_call_id থাকতে হবে, যা call.id।
  • একটি টুল মেসেজের content একটি স্ট্রিং। কাঠামোবদ্ধ ফলাফলের জন্য json.dumps ব্যবহার করুন।

আপনি যা দেখতে পাবেন#

প্রথম অনুরোধের পর আপনি যদি ফিল্ডগুলো প্রিন্ট করেন, সেগুলো এমন দেখাবে (কল আইডি প্রতিবার আলাদা হয়):

text
finish_reason: tool_calls
call.id: call_abc123
call.function.name: get_weather
call.function.arguments: {"city": "Paris"}

এরপর স্ক্রিপ্টটি চূড়ান্ত উত্তর প্রিন্ট করে, একটি সাধারণ বাক্য যেমন "It is currently 14 °C in Paris." শব্দচয়ন প্রতিবার পরিবর্তিত হয়; সংখ্যাটি আপনার ফাংশন থেকে আসে।

একাধিক কল এবং দীর্ঘ লুপ#

একটি মডেল একটি উত্তরে একাধিক কল ফেরত দিতে পারে, উদাহরণস্বরূপ যখন আপনি দুটি শহরের আবহাওয়া সম্পর্কে জিজ্ঞাসা করেন। এজন্যই উদাহরণটি message.tool_calls এর উপর লুপ করে এবং প্রতিটি কলের নিজস্ব আইডি দিয়ে উত্তর দেয়। OpenAI-এর ফাংশন কলিং গাইড একই আচরণ বর্ণনা করে: ডিফল্ট tool_choice এর মান auto হলে মডেল শূন্য, এক বা একাধিক ফাংশন কল করতে পারে (OpenAI ডকস, 22 অক্টোবর 2026-এ যাচাই করা; পৃষ্ঠাটিতে সর্বশেষ আপডেটের তারিখ নেই এবং এটি নতুন Responses API আকৃতি বর্ণনা করে, যেখানে এই গাইডটি /v1/chat/completions এন্ডপয়েন্টের Chat Completions আকৃতি ব্যবহার করে)।

এজেন্টরা দুটি ধাপ পুনরাবৃত্তি করে যতক্ষণ না মডেল টুল চাওয়া বন্ধ করে। অনুরোধগুলো একটি লুপে মোড়ান এবং সর্বদা একটি ধাপ সীমা সেট করুন:

python
for _ in range(5):  # safety limit against endless loops
    response = client.chat.completions.create(model=MODEL, messages=messages, tools=tools)
    message = response.choices[0].message
    if not message.tool_calls:
        print(message.content)
        break
    messages.append(message)
    for call in message.tool_calls:
        args = json.loads(call.function.arguments)
        result = FUNCTIONS[call.function.name](**args)
        messages.append({'role': 'tool', 'tool_call_id': call.id, 'content': json.dumps(result)})

আপনি যদি উত্তরটি টোকেন বাই টোকেন দেখতে চান, তাহলে এটি Python-এ স্ট্রিমিং এর সাথে মিলিত করুন।

কেন MiniMax-M2.7 টুল লুপের জন্য উপযুক্ত#

একটি টুল লুপ ক্রমবর্ধমান ইতিহাসসহ অনেক অনুরোধ পাঠায়। এই প্যাটার্নের জন্য CheapTokens MiniMax-M2.7 অফার করে: 180K কনটেক্সট, প্রতি উত্তরে সর্বোচ্চ 8,192 আউটপুট টোকেন, দিনের যেকোনো সময় একই দাম পিক আওয়ার ছাড়াই, এবং সব মডেলের জন্য একটি ব্যালেন্স। ইনপুট ও আউটপুট একসাথে গণনা করলে এটি OpenRouter-এর রেফারেন্স দামের চেয়ে সস্তা (CheapTokens মূল্য তুলনা, 31 অক্টোবর 2026-এ যাচাই করা)।

প্রতি 1M টোকেনে বর্তমান দাম: ইনপুট $0.05, আউটপুট $0.15। একটি উদাহরণ ওয়ার্কলোড হিসেবে (পরিমাপ নয়), উপরের দুই-অনুরোধের রাউন্ড ট্রিপে মোট প্রায় 2,700 ইনপুট এবং 350 আউটপুট টোকেনে খরচ হয় $0.00019। সম্পূর্ণ মূল্য তালিকা মূল্য পৃষ্ঠায় আছে।

অন্য মডেল চেষ্টা করতে শুধু আইডি পরিবর্তন করুন; আইডিগুলোর তালিকা মডেল পৃষ্ঠায় আছে।

যদি এটি কাজ না করে#

  • message.tool_calls হলো None। মডেল টেক্সটে উত্তর দিয়েছে। ফাংশন description আরও নির্দিষ্ট করুন, এবং নিশ্চিত করুন যে প্রশ্নটির সত্যিই ফাংশনটি প্রয়োজন।
  • arguments-এ json.JSONDecodeError। মডেল অবৈধ JSON তৈরি করেছে। json.loads কে try/except এ মোড়ান এবং ত্রুটির টেক্সট টুল ফলাফল হিসেবে ফেরত পাঠান, যাতে মডেল সংশোধিত আর্গুমেন্ট দিয়ে আবার চেষ্টা করতে পারে।
  • দ্বিতীয় অনুরোধ ব্যর্থ হয় বা মডেল ফলাফল উপেক্ষা করে। পরীক্ষা করুন যে প্রতিটি কলেের জন্য ঠিক একটি role: tool মেসেজ আছে যার tool_call_id মিলে যায়, এবং tool_calls সহ অ্যাসিস্ট্যান্ট মেসেজ তাদের আগে ইতিহাসে আছে।
  • FUNCTIONS[...]-এ KeyError। মডেল এমন একটি ফাংশনের নাম দিয়েছে যা আপনি নিবন্ধন করেননি। ক্র্যাশ করার বদলে টুল ফলাফল হিসেবে একটি সংক্ষিপ্ত ত্রুটি স্ট্রিং ফেরত দিন।
  • উত্তর কেটে গেছে। finish_reason পরীক্ষা করুন: length মানে আউটপুট টোকেন সীমা পৌঁছে গেছে। দেখুন কেন একটি AI উত্তর মাঝপথে থেমে যায়।
  • 401 বা প্রমাণীকরণ ত্রুটি। পরীক্ষা করুন যে কী CHEAPTOKENS_API_KEY এ আছে এবং বেস URL /v1 দিয়ে শেষ হয়।

পরবর্তী ধাপ#

স্টাবটিকে একটি আসল ফাংশন দিয়ে প্রতিস্থাপন করুন: একটি ডেটাবেস কোয়েরি, একটি সার্চ কল বা একটি ক্যালকুলেটর। tools এবং FUNCTIONS এ আরও এন্ট্রি যোগ করুন, এবং প্রতিটি ফাংশনের ফলাফল সংক্ষিপ্ত রাখুন, কারণ এটি প্রতিটি পরবর্তী অনুরোধে ইতিহাসে ফিরে যায়। একটি কী পেতে এবং প্রথম কল করতে, CheapTokens ডকস খুলুন।