On this page
- Introduction
- Prerequisites
- Setup
- Basic Usage
- Prompt Engineering Best Practices
- 1. Be Specific and Clear
- 2. Use System Messages Effectively
- 3. Provide Examples (Few-Shot Learning)
- Advanced Features
- Streaming Responses
- Function Calling
- JSON Mode
- Error Handling
- Cost Optimization
- 1. Choose the Right Model
- 2. Limit Token Usage
- 3. Cache Responses
- Security Best Practices
- 1. Never Expose API Keys
- 2. Validate User Input
- 3. Implement Rate Limiting
- Real-World Example: Code Review Bot
- Conclusion
- Next Steps
- Resources
Introduction
OpenAI’s API provides powerful language models that can enhance your applications with natural language understanding and generation capabilities. This tutorial covers everything you need to know to integrate OpenAI’s API effectively.
Prerequisites
- Python 3.8 or higher
- Basic understanding of REST APIs
- OpenAI API key (get one here)
Setup
First, install the OpenAI Python library:
pip install openai
Set up your API key as an environment variable:
export OPENAI_API_KEY='your-api-key-here'
Basic Usage
Here’s a simple example to get started:
from openai import OpenAI
import os
client = OpenAI(api_key=os.getenv("OPENAI_API_KEY"))
response = client.chat.completions.create(
model="gpt-4-turbo-preview",
messages=[
{"role": "system", "content": "You are a helpful assistant."},
{"role": "user", "content": "Explain quantum computing in simple terms."}
]
)
print(response.choices[0].message.content)
Prompt Engineering Best Practices
1. Be Specific and Clear
Bad prompt:
"Write code"
Good prompt:
"""Write a Python function that takes a list of integers and returns
the sum of all even numbers. Include error handling for invalid inputs
and add docstring documentation."""
2. Use System Messages Effectively
The system message sets the behavior and context:
messages = [
{
"role": "system",
"content": """You are an expert Python developer who writes clean,
well-documented code following PEP 8 standards. Always include
type hints and comprehensive docstrings."""
},
{
"role": "user",
"content": "Create a function to validate email addresses"
}
]
3. Provide Examples (Few-Shot Learning)
messages = [
{"role": "system", "content": "You are a sentiment analyzer."},
{"role": "user", "content": "I love this product!"},
{"role": "assistant", "content": "Positive"},
{"role": "user", "content": "This is terrible."},
{"role": "assistant", "content": "Negative"},
{"role": "user", "content": "The weather is nice today."}
]
Advanced Features
Streaming Responses
For long responses, use streaming to improve user experience:
stream = client.chat.completions.create(
model="gpt-4-turbo-preview",
messages=[{"role": "user", "content": "Write a long story"}],
stream=True
)
for chunk in stream:
if chunk.choices[0].delta.content is not None:
print(chunk.choices[0].delta.content, end="")
Function Calling
Enable the model to call functions in your code:
functions = [
{
"name": "get_weather",
"description": "Get the current weather for a location",
"parameters": {
"type": "object",
"properties": {
"location": {
"type": "string",
"description": "City name"
},
"unit": {
"type": "string",
"enum": ["celsius", "fahrenheit"]
}
},
"required": ["location"]
}
}
]
response = client.chat.completions.create(
model="gpt-4-turbo-preview",
messages=[{"role": "user", "content": "What's the weather in Paris?"}],
functions=functions,
function_call="auto"
)
# Check if the model wants to call a function
if response.choices[0].message.function_call:
function_name = response.choices[0].message.function_call.name
arguments = json.loads(response.choices[0].message.function_call.arguments)
# Call your actual function
result = get_weather(**arguments)
# Send the result back to the model
second_response = client.chat.completions.create(
model="gpt-4-turbo-preview",
messages=[
{"role": "user", "content": "What's the weather in Paris?"},
response.choices[0].message,
{
"role": "function",
"name": function_name,
"content": json.dumps(result)
}
]
)
JSON Mode
Force the model to return valid JSON:
response = client.chat.completions.create(
model="gpt-4-turbo-preview",
messages=[
{
"role": "system",
"content": "You are a helpful assistant that outputs JSON."
},
{
"role": "user",
"content": "List 3 programming languages with their use cases"
}
],
response_format={"type": "json_object"}
)
data = json.loads(response.choices[0].message.content)
Error Handling
Always implement robust error handling:
from openai import OpenAI, OpenAIError, RateLimitError, APIError
import time
def call_openai_with_retry(messages, max_retries=3):
"""Call OpenAI API with exponential backoff retry logic"""
client = OpenAI()
for attempt in range(max_retries):
try:
response = client.chat.completions.create(
model="gpt-4-turbo-preview",
messages=messages,
temperature=0.7,
max_tokens=1000
)
return response
except RateLimitError:
if attempt < max_retries - 1:
wait_time = (2 ** attempt) * 2 # Exponential backoff
print(f"Rate limit hit. Waiting {wait_time} seconds...")
time.sleep(wait_time)
else:
raise
except APIError as e:
print(f"API error: {e}")
if attempt < max_retries - 1:
time.sleep(2)
else:
raise
except OpenAIError as e:
print(f"OpenAI error: {e}")
raise
# Usage
try:
response = call_openai_with_retry([
{"role": "user", "content": "Hello!"}
])
print(response.choices[0].message.content)
except OpenAIError as e:
print(f"Failed after retries: {e}")
Cost Optimization
1. Choose the Right Model
- GPT-4 Turbo: Most capable, higher cost
- GPT-3.5 Turbo: Faster, cheaper, good for most tasks
- GPT-4o mini: Cheapest, best for simple tasks
2. Limit Token Usage
response = client.chat.completions.create(
model="gpt-3.5-turbo",
messages=messages,
max_tokens=500, # Limit response length
temperature=0.3 # Lower temperature = more focused responses
)
# Track token usage
print(f"Tokens used: {response.usage.total_tokens}")
print(f"Cost: ${response.usage.total_tokens * 0.000002:.6f}")
3. Cache Responses
import hashlib
import json
from functools import lru_cache
@lru_cache(maxsize=100)
def cached_openai_call(messages_hash):
"""Cache OpenAI responses to avoid duplicate calls"""
messages = json.loads(messages_hash)
response = client.chat.completions.create(
model="gpt-3.5-turbo",
messages=messages
)
return response.choices[0].message.content
# Usage
messages = [{"role": "user", "content": "Hello"}]
messages_hash = json.dumps(messages, sort_keys=True)
result = cached_openai_call(messages_hash)
Security Best Practices
1. Never Expose API Keys
# ❌ Bad - hardcoded key
client = OpenAI(api_key="sk-...")
# ✅ Good - environment variable
client = OpenAI(api_key=os.getenv("OPENAI_API_KEY"))
2. Validate User Input
def sanitize_input(user_input: str) -> str:
"""Sanitize user input to prevent prompt injection"""
# Remove potential injection attempts
sanitized = user_input.replace("Ignore previous instructions", "")
# Limit length
max_length = 1000
sanitized = sanitized[:max_length]
return sanitized
user_message = sanitize_input(request.form.get("message"))
3. Implement Rate Limiting
from flask_limiter import Limiter
from flask import Flask
app = Flask(__name__)
limiter = Limiter(app, key_func=lambda: request.remote_addr)
@app.route("/api/chat", methods=["POST"])
@limiter.limit("10 per minute")
def chat():
# Your OpenAI API call here
pass
Real-World Example: Code Review Bot
Here’s a complete example that reviews code:
def review_code(code: str, language: str) -> dict:
"""Review code and provide feedback"""
client = OpenAI()
prompt = f"""Review the following {language} code and provide:
1. Potential bugs or errors
2. Performance improvements
3. Best practice suggestions
4. Security concerns
Code:
{code}
Format your response as JSON with keys: bugs, performance, best_practices, security
"""
response = client.chat.completions.create(
model="gpt-4-turbo-preview",
messages=[
{
"role": "system",
"content": "You are an expert code reviewer."
},
{
"role": "user",
"content": prompt
}
],
response_format={"type": "json_object"},
temperature=0.3
)
return json.loads(response.choices[0].message.content)
# Usage
code = """
def calculate_average(numbers):
return sum(numbers) / len(numbers)
"""
review = review_code(code, "python")
print(json.dumps(review, indent=2))
Conclusion
You now have the knowledge to integrate OpenAI’s API into your applications effectively. Remember to:
- Write clear, specific prompts
- Implement proper error handling
- Optimize for cost
- Follow security best practices
- Monitor usage and performance
Next Steps
- Explore the AI Code Reviewer project to see these concepts in action
- Read the official OpenAI documentation
- Experiment with different models and parameters
- Build your own AI-powered application