Go / Golang Integration Guide
Integrate OilPriceAPI into your Go applications to access real-time crude oil prices, Brent crude data, natural gas rates, and commodity market information.
Installation
No external dependencies required. Go's standard library provides everything needed for HTTP requests and JSON parsing.
# Initialize your Go module (if not already done)
go mod init your-project-name
Quick Start
package main
import (
"encoding/json"
"fmt"
"io"
"net/http"
"os"
)
func main() {
apiKey := os.Getenv("OILPRICE_API_KEY")
req, _ := http.NewRequest("GET", "https://api.oilpriceapi.com/v1/prices/latest?by_code=WTI_USD", nil)
req.Header.Set("Authorization", "Token "+apiKey)
resp, err := http.DefaultClient.Do(req)
if err != nil {
fmt.Printf("Request failed: %v\n", err)
return
}
defer resp.Body.Close()
body, _ := io.ReadAll(resp.Body)
fmt.Println(string(body))
}
Complete API Client
Create a reusable client for all OilPriceAPI endpoints:
package oilpriceapi
import (
"encoding/json"
"fmt"
"io"
"net/http"
"net/url"
"os"
"time"
)
// Client handles API communication
type Client struct {
APIKey string
BaseURL string
HTTPClient *http.Client
}
// PriceData represents commodity price information
type PriceData struct {
Price float64 `json:"price"`
Formatted string `json:"formatted"`
Currency string `json:"currency"`
Code string `json:"code"`
CreatedAt string `json:"created_at"`
}
// PriceResponse represents the API response structure
type PriceResponse struct {
Status string `json:"status"`
Data map[string]PriceData `json:"data"`
}
// HistoricalResponse for time-series data
type HistoricalResponse struct {
Status string `json:"status"`
Data []PriceData `json:"data"`
}
// NewClient creates an OilPriceAPI client
func NewClient(apiKey string) *Client {
if apiKey == "" {
apiKey = os.Getenv("OILPRICE_API_KEY")
}
return &Client{
APIKey: apiKey,
BaseURL: "https://api.oilpriceapi.com/v1",
HTTPClient: &http.Client{
Timeout: 30 * time.Second,
},
}
}
// request performs authenticated API calls
func (c *Client) request(endpoint string, params map[string]string) ([]byte, error) {
u, _ := url.Parse(c.BaseURL + endpoint)
q := u.Query()
for k, v := range params {
q.Set(k, v)
}
u.RawQuery = q.Encode()
req, err := http.NewRequest("GET", u.String(), nil)
if err != nil {
return nil, fmt.Errorf("creating request: %w", err)
}
req.Header.Set("Authorization", "Token "+c.APIKey)
req.Header.Set("Content-Type", "application/json")
resp, err := c.HTTPClient.Do(req)
if err != nil {
return nil, fmt.Errorf("executing request: %w", err)
}
defer resp.Body.Close()
if resp.StatusCode == 401 {
return nil, fmt.Errorf("invalid API key")
}
if resp.StatusCode == 429 {
return nil, fmt.Errorf("rate limit exceeded")
}
if resp.StatusCode != 200 {
return nil, fmt.Errorf("API error: status %d", resp.StatusCode)
}
return io.ReadAll(resp.Body)
}
// GetLatestPrice fetches current commodity prices
func (c *Client) GetLatestPrice(codes string) (*PriceResponse, error) {
body, err := c.request("/prices/latest", map[string]string{"by_code": codes})
if err != nil {
return nil, err
}
var result PriceResponse
if err := json.Unmarshal(body, &result); err != nil {
return nil, fmt.Errorf("parsing response: %w", err)
}
return &result, nil
}
// GetHistoricalPrices fetches price history
func (c *Client) GetHistoricalPrices(code string, days int) (*HistoricalResponse, error) {
endpoint := fmt.Sprintf("/prices/past_%d_days", days)
body, err := c.request(endpoint, map[string]string{"by_code": code})
if err != nil {
return nil, err
}
var result HistoricalResponse
if err := json.Unmarshal(body, &result); err != nil {
return nil, fmt.Errorf("parsing response: %w", err)
}
return &result, nil
}
Usage Examples
Fetch Multiple Commodity Prices
package main
import (
"fmt"
"log"
)
func main() {
client := oilpriceapi.NewClient("")
// Get WTI, Brent, and Natural Gas prices
prices, err := client.GetLatestPrice("WTI_USD,BRENT_CRUDE_USD,NATURAL_GAS_USD")
if err != nil {
log.Fatalf("Failed to fetch prices: %v", err)
}
for code, data := range prices.Data {
fmt.Printf("%s: %s\n", code, data.Formatted)
}
}
Historical Data Analysis
package main
import (
"fmt"
"log"
)
func main() {
client := oilpriceapi.NewClient("")
history, err := client.GetHistoricalPrices("WTI_USD", 7)
if err != nil {
log.Fatalf("Failed to fetch history: %v", err)
}
fmt.Println("WTI Price History (Past Week):")
for _, point := range history.Data {
fmt.Printf(" %s: $%.2f\n", point.CreatedAt, point.Price)
}
}
Concurrent Requests with Goroutines
package main
import (
"fmt"
"sync"
)
func main() {
client := oilpriceapi.NewClient("")
commodities := []string{"WTI_USD", "BRENT_CRUDE_USD", "DUBAI_CRUDE_USD"}
var wg sync.WaitGroup
results := make(chan string, len(commodities))
for _, code := range commodities {
wg.Add(1)
go func(c string) {
defer wg.Done()
price, err := client.GetLatestPrice(c)
if err != nil {
results <- fmt.Sprintf("%s: error - %v", c, err)
return
}
if data, ok := price.Data[c]; ok {
results <- fmt.Sprintf("%s: %s", c, data.Formatted)
}
}(code)
}
go func() {
wg.Wait()
close(results)
}()
for result := range results {
fmt.Println(result)
}
}
Error Handling
Implement robust error handling with retries:
package main
import (
"fmt"
"time"
)
func fetchWithRetry(client *oilpriceapi.Client, code string, maxRetries int) (*oilpriceapi.PriceResponse, error) {
var lastErr error
for i := 0; i < maxRetries; i++ {
price, err := client.GetLatestPrice(code)
if err == nil {
return price, nil
}
lastErr = err
// Exponential backoff
backoff := time.Duration(1<<uint(i)) * time.Second
fmt.Printf("Attempt %d failed, retrying in %v: %v\n", i+1, backoff, err)
time.Sleep(backoff)
}
return nil, fmt.Errorf("all %d attempts failed: %w", maxRetries, lastErr)
}
func main() {
client := oilpriceapi.NewClient("")
price, err := fetchWithRetry(client, "WTI_USD", 3)
if err != nil {
fmt.Printf("Failed: %v\n", err)
return
}
fmt.Printf("Success: %+v\n", price)
}
Best Practices
Environment Configuration
// Use environment variables for API keys
apiKey := os.Getenv("OILPRICE_API_KEY")
if apiKey == "" {
log.Fatal("OILPRICE_API_KEY environment variable not set")
}
Connection Pooling
// Reuse HTTP client for connection pooling
var defaultClient = &http.Client{
Timeout: 30 * time.Second,
Transport: &http.Transport{
MaxIdleConns: 100,
MaxIdleConnsPerHost: 10,
IdleConnTimeout: 90 * time.Second,
},
}
Context Support
import "context"
func (c *Client) RequestWithContext(ctx context.Context, endpoint string) ([]byte, error) {
req, _ := http.NewRequestWithContext(ctx, "GET", c.BaseURL+endpoint, nil)
req.Header.Set("Authorization", "Token "+c.APIKey)
resp, err := c.HTTPClient.Do(req)
if err != nil {
return nil, err
}
defer resp.Body.Close()
return io.ReadAll(resp.Body)
}
Common Commodity Codes
| Code | Description |
|---|---|
WTI_USD | West Texas Intermediate Crude Oil |
BRENT_CRUDE_USD | Brent Crude Oil |
NATURAL_GAS_USD | Natural Gas (Henry Hub) |
HEATING_OIL_USD | Heating Oil No. 2 |
DIESEL_USD | Ultra Low Sulfur Diesel |
Next Steps
- Authentication Guide - API key management
- API Reference - Complete endpoint documentation
- Historical Data - Time-series queries
- WebSocket Streaming - Real-time price updates