Class: Apipurse::Client

Inherits:
Object
  • Object
show all
Defined in:
lib/apipurse.rb

Instance Method Summary collapse

Constructor Details

#initialize(ingest_token:, provider_id:, base_url: "http://localhost:3000", silent: true) ⇒ Client

Returns a new instance of Client.



29
30
31
32
33
34
# File 'lib/apipurse.rb', line 29

def initialize(ingest_token:, provider_id:, base_url: "http://localhost:3000", silent: true)
  @ingest_token = ingest_token
  @provider_id = provider_id
  @base_url = base_url.chomp("/")
  @silent = silent
end

Instance Method Details

#track_completion(model:, input_tokens:, output_tokens:, request_count: 1) ⇒ Object

Reports one completion's token usage. Computes and stores the exact dollar cost immediately (via APIPurse's model price table) and checks your budget right away — no waiting for a scheduled sync.



39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
# File 'lib/apipurse.rb', line 39

def track_completion(model:, input_tokens:, output_tokens:, request_count: 1)
  uri = URI("#{@base_url}/api/track/completion")
  body = {
    provider_id: @provider_id,
    model: model,
    input_tokens: input_tokens,
    output_tokens: output_tokens,
    request_count: request_count,
  }.to_json

  response = Net::HTTP.start(
    uri.host, uri.port,
    use_ssl: uri.scheme == "https",
    open_timeout: 10, read_timeout: 10
  ) do |http|
    request = Net::HTTP::Post.new(uri)
    request["Content-Type"] = "application/json"
    request["Authorization"] = "Bearer #{@ingest_token}"
    request.body = body
    http.request(request)
  end

  payload = JSON.parse(response.body)

  unless response.is_a?(Net::HTTPSuccess)
    message = payload["error"] || "HTTP #{response.code}"
    return TrackCompletionResult.new(ok: false, error: message) if @silent

    raise "APIPurse tracking failed: #{message}"
  end

  TrackCompletionResult.new(
    ok: payload["ok"] || false,
    cost_usd: payload["cost_usd"],
    alert_triggered: payload["alert_triggered"]
  )
rescue StandardError => e
  raise if !@silent

  TrackCompletionResult.new(ok: false, error: e.message)
end