TOpenAI / TChatGPT
Source: source/classes/topenai.prg (TOpenAI), source/classes/chatgpt.prg (TChatGPT)
FiveWin provides two classes for integrating with the OpenAI API: TOpenAI (full-featured
with vision, streaming, and image support) and TChatGPT (simpler wrapper for basic chat
completions). Both use Harbour's hb_curl library for HTTPS communication.
Architecture
HTTPS] end subgraph "OpenAI API" D["/v1/chat/completions"] E[Vision API] end A --> C B --> C C --> D C --> E
TOpenAI Class
DATA Members
| DATA | Type | Default | Description |
|---|---|---|---|
cKey | Character | "" | OpenAI API key |
cModel | Character | "gpt-4o-mini" | Model to use |
cPrompt | Character | Last prompt sent | |
cResponse | Character | Raw JSON response from API | |
cUrl | Character | API endpoint URL | |
hCurl | Handle | libcurl easy handle | |
nError | Numeric | 0 | curl error code (0 = success) |
nHttpCode | Numeric | 0 | HTTP response status code |
nTemperature | Numeric | 0.5 | Sampling temperature (0.0 - 2.0) |
Methods
| Method | Description |
|---|---|
New( cKey, cModel ) | Create instance. If cKey is empty, reads OPENAI_API_KEY env var. |
Send( cPrompt ) | Send a text prompt, return raw JSON response |
SendStream( cPrompt, bCallback ) | Send prompt with streaming; bCallback receives chunks |
SendImage( cImageFileName, cPrompt ) | Send a local image file with a prompt (Vision API) |
SendImageURL( cImageUrl, cPrompt ) | Send an image URL with a prompt (Vision API) |
GetValue() | Extract the text response from cResponse JSON |
End() | Clean up curl handle |
TChatGPT Class
TChatGPT is a simpler alternative with fewer features, suitable for basic prompt/response interactions.
DATA Members
| DATA | Type | Default | Description |
|---|---|---|---|
cKey | Character | "" | OpenAI API key |
cModel | Character | "gpt-4o-mini" | Model name |
cUrl | Character | "https://api.openai.com/v1/chat/completions" | API endpoint |
cPrompt | Character | Prompt text to send | |
cResponse | Character | Raw JSON response | |
hCurl | Handle | libcurl handle | |
nError | Numeric | 0 | curl error code |
nHttpCode | Numeric | HTTP status code |
Methods
| Method | Description |
|---|---|
New( cKey ) | Create instance with API key |
Send() | Send cPrompt, store response in cResponse |
GetValue( cKey1, cKey2, ... ) | Navigate JSON response by key path. Variable args. |
Reset() | Reset curl state for next request |
End() | Clean up curl handle |
Example: Basic Prompt/Response (TOpenAI)
#include "FiveWin.ch"
function Main()
local oAI, cAnswer
// API key from environment variable OPENAI_API_KEY
oAI := TOpenAI():New()
// Or with explicit key and model:
// oAI := TOpenAI():New( "sk-...", "gpt-4o" )
oAI:Send( "What is the capital of France? Answer in one word." )
if oAI:nError == 0 .and. oAI:nHttpCode == 200
cAnswer := oAI:GetValue()
MsgInfo( cAnswer ) // "Paris"
else
MsgStop( "Error: " + oAI:cResponse )
endif
oAI:End()
return nil
Example: Streaming Response
#include "FiveWin.ch"
function Main()
local oAI, cBuffer := ""
oAI := TOpenAI():New()
oAI:cModel := "gpt-4o"
// Stream callback receives chunks of data as they arrive
oAI:SendStream( "Write a short poem about coding.", ;
{ |cChunk| cBuffer += cChunk, QOut( cChunk ) } )
if oAI:nError == 0
MsgInfo( "Complete response:" + CRLF + cBuffer )
endif
oAI:End()
return nil
Example: Vision (Analyze an Image)
#include "FiveWin.ch"
function Main()
local oAI
oAI := TOpenAI():New( , "gpt-4o" )
// Send a local image file
oAI:SendImage( "C:\photos\chart.png", "Describe what you see in this image." )
if oAI:nError == 0
MsgInfo( oAI:GetValue() )
endif
// Send an image by URL
oAI:SendImageURL( ;
"https://example.com/photo.jpg", ;
"What objects are in this photo?" )
if oAI:nError == 0
MsgInfo( oAI:GetValue() )
endif
oAI:End()
return nil
Example: TChatGPT (Simple Wrapper)
#include "FiveWin.ch"
function Main()
local oChat
oChat := TChatGPT():New( "sk-your-api-key-here" )
// Set the prompt and send
oChat:cPrompt := "Translate 'Hello, how are you?' to Spanish"
oChat:Send()
if oChat:nError == 0
// Navigate the JSON response
? oChat:GetValue( "choices", "message", "content" )
// Output: "Hola, como estas?"
endif
// Send another prompt (reset first)
oChat:Reset()
oChat:cPrompt := "Now translate it to French"
oChat:Send()
if oChat:nError == 0
? oChat:GetValue( "choices", "message", "content" )
endif
oChat:End()
return nil
Example: Adjusting Temperature
#include "FiveWin.ch"
function Main()
local oAI
oAI := TOpenAI():New()
// Low temperature = more deterministic
oAI:nTemperature := 0.1
oAI:Send( "What is 2 + 2?" )
? "Precise:", oAI:GetValue()
// High temperature = more creative
oAI:nTemperature := 1.5
oAI:Send( "Write a creative product name for a new coffee brand" )
? "Creative:", oAI:GetValue()
oAI:End()
return nil
Supported Models
| Model | Description |
|---|---|
gpt-4o | Most capable model, supports text + vision |
gpt-4o-mini | Fast, cost-effective (default in FWH) |
gpt-4-turbo | GPT-4 Turbo with large context window |
gpt-3.5-turbo | Legacy fast model |
Tips
- Store your API key in the
OPENAI_API_KEYenvironment variable rather than hardcoding it. - TOpenAI:New() automatically reads from the environment if no key is passed.
- The
hb_curllibrary must be linked. Use#include "hbcurl.ch"for constants. - SSL verification is disabled by default (
HB_CURLOPT_SSL_VERIFYPEER = .F.) for compatibility. - Use
SendStream()for long responses to get real-time output instead of waiting for the complete response. - The
GetValue()method handles JSON parsing internally. For TOpenAI it returnschoices[1].message.content. For TChatGPT, pass the key path as arguments.
TOLlama (Local AI)
Source: source/classes/tollama.prg
Local AI Connects to a local Ollama server. No API key needed - runs AI models on your own machine.
| DATA | Default | Description |
|---|---|---|
cModel | Model name (e.g. "llama3", "mistral", "codellama") | |
cUrl | "http://localhost:11434" | Ollama server URL |
cPrompt | Current prompt | |
cResponse | API response | |
aAgents | Array of agent definitions |
| Method | Parameters | Description |
|---|---|---|
New() | cModel | Constructor. Sets model name. |
Send() | cPrompt | Send prompt and wait for full response |
SendStream() | cPrompt, bCallback | Send with streaming - bCallback receives chunks in real-time |
SendImage() | cImageFile, cPrompt | Send image + prompt (for vision models like llava) |
GetValue() | Extract response text from JSON | |
End() | Cleanup CURL handle |
local oAI := TOLlama():New( "llama3" )
oAI:Send( "Explain what FiveWin is in one paragraph" )
MsgInfo( oAI:GetValue() )
// Streaming response
oAI:SendStream( "Write a Harbour function", ;
{| cChunk | QOut( cChunk ) } )
oAI:End()
TDeepSeek
Source: source/classes/tdeepseek.prg
Cloud AI DeepSeek API client. Known for strong coding and reasoning capabilities.
| DATA | Default | Description |
|---|---|---|
cKey | "" | API key from DeepSeek |
cModel | "deepseek-chat" | Model: "deepseek-chat" or "deepseek-reasoner" |
cUrl | API endpoint |
local oAI := TDeepSeek():New( "your-api-key" )
oAI:Send( "Write a Harbour function to calculate factorial" )
MsgInfo( oAI:GetValue() )
oAI:End()
TGemini (Google)
Source: source/classes/tgemini.prg
Cloud AI Google Gemini API client. Supports text, images, and file uploads.
| DATA | Default | Description |
|---|---|---|
cKey | "" | Google API key |
cModel | "gemini-2.0-flash" | Model name |
cUrl | googleapis.com/v1beta/models | API endpoint |
cUploadUrl | googleapis.com/upload/v1beta/files | File upload endpoint |
nTemperature | 0 | Response creativity (0-2) |
| Method | Parameters | Description |
|---|---|---|
New() | cKey, cModel | Constructor |
Send() | uContent, cPrompt, bCallback | Send text, image or file with prompt |
UploadFile() | cFileName, lDeleteAfter | Upload file to Gemini for analysis |
GetTokens() | cBuffer | Count tokens in text |
GetValue() | Extract response text |
local oAI := TGemini():New( "your-google-api-key" )
oAI:Send( "Analyze this image", "photo.jpg" )
MsgInfo( oAI:GetValue() )
oAI:End()
TGrok (xAI)
Source: source/classes/tgrok.prg
Cloud AI xAI Grok API client. Supports text, images, and streaming.
| DATA | Default | Description |
|---|---|---|
cKey | "" | xAI API key |
cModel | "grok-3-latest" | Model name |
nTemperature | 0.5 | Response creativity |
| Method | Parameters | Description |
|---|---|---|
Send() | cPrompt | Send text prompt |
SendStream() | cPrompt, bCallback | Streaming response |
SendImage() | cImageFile, cPrompt | Send image file + prompt |
SendImageURL() | cImageUrl, cPrompt | Send image URL + prompt |
local oAI := TGrok():New( "your-xai-key" )
oAI:Send( "What are the benefits of Harbour language?" )
MsgInfo( oAI:GetValue() )
oAI:End()
TKimi (Moonshot)
Source: source/classes/tkimi.prg
Cloud AI Moonshot Kimi API client. Strong multilingual capabilities.
| DATA | Default | Description |
|---|---|---|
cKey | "" | Moonshot API key |
cModel | "moonshot-v1-8k" | Model: moonshot-v1-8k, -32k, -128k |
nTemperature | 0.5 | Response creativity |
local oAI := TKimi():New( "your-moonshot-key" )
oAI:Send( "Translate this to Chinese: Hello World" )
MsgInfo( oAI:GetValue() )
oAI:End()
AI Classes Comparison
| Class | Provider | Local/Cloud | Vision | Streaming | Default Model |
|---|---|---|---|---|---|
TOpenAI | OpenAI | Cloud | Yes | Yes | gpt-4o-mini |
TChatGPT | OpenAI | Cloud | No | No | gpt-4o-mini |
TOLlama | Local (Ollama) | Local | Yes | Yes | (user choice) |
TDeepSeek | DeepSeek | Cloud | No | No | deepseek-chat |
TGemini | Cloud | Yes | Yes | gemini-2.0-flash | |
TGrok | xAI | Cloud | Yes | Yes | grok-3-latest |
TKimi | Moonshot | Cloud | No | No | moonshot-v1-8k |
llama3, mistral, codellama] B -->|OpenAI| D[TOpenAI / TChatGPT
gpt-4o, gpt-4o-mini] B -->|Google| E[TGemini
gemini-2.0-flash] B -->|xAI| F[TGrok
grok-3] B -->|DeepSeek| G[TDeepSeek
deepseek-chat] B -->|Moonshot| H[TKimi
moonshot-v1] style C fill:#238636,stroke:#3fb950,color:#fff style D fill:#1f6feb,stroke:#58a6ff,color:#fff style E fill:#d29922,stroke:#e3b341,color:#000 style F fill:#6e40c9,stroke:#bc8cff,color:#fff style G fill:#da3633,stroke:#f85149,color:#fff style H fill:#bf8700,stroke:#d29922,color:#fff
Transformer (Neural Network in Harbour)
Source: source/classes/transformer.prg
Advanced A full Transformer neural network implemented in pure Harbour. Supports training, forward/backward propagation, multi-head attention, and text prediction.
| DATA | Description |
|---|---|
d_model | Model dimension (embedding size) |
n_heads | Number of attention heads |
num_layers | Number of transformer layers |
vocab_size | Vocabulary size |
max_seq_len | Maximum sequence length |
aVocab | Vocabulary array (words) |
Embedding, Positional | Embedding and positional encoding matrices |
| Method | Description |
|---|---|
New() | Constructor: num_layers, d_model, n_heads, vocab_size, max_seq_len, hEmbeddings, aVocab |
Forward() | Forward pass: src_indices, pos_indices → output |
Backward() | Backward pass: compute gradients for training |
zero_grad() | Reset all gradients to zero |
Example: Next Word Prediction (transf1.prg)
local vocab := { "hola", "mundo", "adios", "gato", "perro" }
local oT := Transformer():New( 1, 6, 2, Len(vocab), 8,, vocab )
// Train on sequences
for e = 1 to 60
for i = 1 to Len(train_src)
output := oT:Forward( train_src[i], train_pos[i] )
oT:Backward( output, train_tgt[i], train_src[i], train_pos[i] )
next
next
// Predict next word
output := oT:Forward( { 1, 2 }, { 1, 2 } ) // "hola mundo" -> ?
Example: Sentiment Classification (transf2.prg)
// Classify phrases as Positive or Negative
local vocab := { "buen", "dia", "malo", "trabajo", "feliz", "triste", "excelente", "horrible" }
local oT := TransformerClassifier():New( 1, 6, 2, 2, vocab )
// Train: "buen dia" -> Positive, "malo trabajo" -> Negative
// After training, classify new phrases
TNeuralNetwork (Classic Neural Network)
Source: source/classes/tneuralnet.prg
Classic feedforward neural network with backpropagation. Good for simple pattern recognition.
// XOR training example
local oNN := TNeuralNetwork():New( 2, { 2 }, 1 ) // 2 inputs, 1 hidden layer with 2 neurons, 1 output
for n = 1 to 30000
oNN:Learn( { 0, 0 }, { 0 }, .F. )
oNN:Learn( { 1, 0 }, { 1 }, .F. )
oNN:Learn( { 0, 1 }, { 1 }, .F. )
oNN:Learn( { 1, 1 }, { 0 }, .F. )
next
? oNN:Predict( { 1, 0 } ) // -> ~1.0
? oNN:Predict( { 1, 1 } ) // -> ~0.0
TEmbeddings (Semantic Similarity)
Source: source/classes/tembeddings.prg
Text embeddings for semantic similarity comparison. Uses HuggingFace or OpenAI APIs.
local oE1 := TEmbeddings():New()
local oE2 := TEmbeddings():New()
local oE3 := TEmbeddings():New()
oE1:GetEmbeddings( "I feel very well" )
oE2:GetEmbeddings( "How are you?" )
oE3:GetEmbeddings( "I saw Peter" )
? oE1 - oE2 // High similarity (both about feelings)
? oE1 - oE3 // Low similarity (different topics)
AI Agents (TOLlama + TAgent)
AI agents combine LLMs with tools (functions) that the AI can call. The AI decides which tool to use based on the user's request.
local oLlama := TOLlama():New()
local oAgent
// Agent for date/time
oAgent := TAgent():New( "datetime", { ;
{ "get_time", {|hParams| GetCurrentTime(hParams) } }, ;
{ "get_date", {|hParams| GetDate(hParams) } } } )
AAdd( oLlama:aAgents, oAgent )
// Agent for filesystem
oAgent := TAgent():New( "filesystem", { ;
{ "create_folder", {|hParams| CreateFolder(hParams) } }, ;
{ "create_file", {|hParams| CreateFile(hParams) } } } )
AAdd( oLlama:aAgents, oAgent )
// AI decides which tool to use
oLlama:Send( "What time is it?" ) // -> calls get_time
oLlama:Send( "Create a folder test" ) // -> calls create_folder
AI Samples Reference
All AI samples are in the samples/ai/ folder:
| Sample | Description | AI Class |
|---|---|---|
ollama1.prg - ollama5.prg | Local AI: basic chat, streaming, image analysis | TOLlama |
openai1.prg, openai2.prg | OpenAI: text and image prompts | TOpenAI |
chatgpt.prg | Interactive ChatGPT dialog with voice | TChatGPT |
deepseek1.prg | DeepSeek: SQL code generation | TDeepSeek |
gemini1.prg - gemini6.prg | Google Gemini: text, images, files, tokens | TGemini |
grok1.prg | xAI Grok: basic prompt | TGrok |
kimi1.prg | Moonshot Kimi: multilingual | TKimi |
ai.prg | Interactive AI dialog with voice synthesis (64-bit) | TOpenAI |
vision.prg | Visual forms IDE with AI | Multiple |
agents.prg | AI agents with tool calling | TOLlama + TAgent |
agentdb.prg, agentdb2.prg | AI agents for database operations | TOLlama + TAgent |
agentdoc.prg, agentdoc2.prg | AI agents for document creation | TOLlama + TAgent |
agentweb.prg | AI agent for web operations | TOLlama + TAgent |
autogpt.prg | Autonomous AI task execution | TOpenAI |
transf1.prg - transf5.prg | Transformer: next word, sentiment, training | Transformer |
transformer.prg | Complete transformer demo | Transformer |
neural.prg | Neural network: XOR training | TNeuralNetwork |
neuralnet.prg | Neural network visualization | TNet |
nn.prg - nn4c.prg | Various neural network examples | TNeuralNetwork |
perceptron.prg | Basic perceptron | Custom |
embeddings1.prg, embeddings2.prg | Text similarity with embeddings | TEmbeddings |
llm.prg | LLM integration example | TOLlama |
llama3.prg | Llama 3 specific features | TOLlama |
llava.prg | LLaVA vision model | TOLlama |
phi4.prg | Microsoft Phi-4 model | TOLlama |