File size: 3,384 Bytes
04f1444
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
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
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
// Code generated by @openmeter/typespec-go. DO NOT EDIT.

package openmeter

import (
	"fmt"
	"net/http"
	"net/url"
	"strings"
)

type Client struct {
	baseURL       *url.URL
	httpClient    *http.Client
	token         string
	userAgent     string
	Events        *EventsService
	Meters        *MetersService
	Customers     *CustomersService
	Entitlements  *EntitlementsService
	Subscriptions *SubscriptionsService
	Apps          *AppsService
	Billing       *BillingService
	Invoices      *InvoicesService
	Tax           *TaxService
	Currencies    *CurrenciesService
	Features      *FeaturesService
	LLMCost       *LLMCostService
	Plans         *PlansService
	Addons        *AddonsService
	PlanAddons    *PlanAddonsService
	Defaults      *DefaultsService
	Governance    *GovernanceService
}

func New(baseURL string, opts ...Option) (*Client, error) {
	if baseURL == "" {
		return nil, fmt.Errorf("openmeter: baseURL is required")
	}

	u, err := url.Parse(baseURL)
	if err != nil {
		return nil, fmt.Errorf("openmeter: invalid baseURL %q: %w", baseURL, err)
	}

	if u.Scheme == "" || u.Host == "" {
		return nil, fmt.Errorf("openmeter: baseURL %q must be absolute (scheme and host)", baseURL)
	}

	c := &Client{
		baseURL:   u,
		userAgent: defaultUserAgent,
	}

	for _, opt := range opts {
		opt(c)
	}

	if c.httpClient == nil {
		c.httpClient = defaultHTTPClient()
	}

	c.Events = &EventsService{client: c}
	c.Meters = &MetersService{client: c}
	c.Customers = &CustomersService{client: c}
	c.Entitlements = &EntitlementsService{client: c}
	c.Subscriptions = &SubscriptionsService{client: c}
	c.Apps = &AppsService{client: c}
	c.Billing = &BillingService{client: c}
	c.Invoices = &InvoicesService{client: c}
	c.Tax = &TaxService{client: c}
	c.Currencies = &CurrenciesService{client: c}
	c.Features = &FeaturesService{client: c}
	c.LLMCost = &LLMCostService{client: c}
	c.Plans = &PlansService{client: c}
	c.Addons = &AddonsService{client: c}
	c.PlanAddons = &PlanAddonsService{client: c}
	c.Defaults = &DefaultsService{client: c}
	c.Governance = &GovernanceService{client: c}
	c.Customers.Billing = &CustomersBillingService{client: c}
	c.Customers.Credits = &CustomersCreditsService{client: c}
	c.Customers.Charges = &CustomersChargesService{client: c}
	c.Customers.Credits.Grants = &CustomersCreditsGrantsService{client: c}
	c.Customers.Credits.Balance = &CustomersCreditsBalanceService{client: c}
	c.Customers.Credits.Adjustments = &CustomersCreditsAdjustmentsService{client: c}
	c.Customers.Credits.Transactions = &CustomersCreditsTransactionsService{client: c}

	return c, nil
}

// resolve joins the client base URL with an API path, preserving any base path
// prefix and base query present on the base URL. apiPath is parsed so percent
// escapes already present in a segment, such as an ID escaped by
// replacePathParam, are carried through on RawPath instead of being
// re-escaped.
func (c *Client) resolve(apiPath string) *url.URL {
	base := *c.baseURL

	if !strings.HasSuffix(base.Path, "/") {
		base.Path += "/"
	}

	trimmed := strings.TrimPrefix(apiPath, "/")
	ref, err := url.Parse(trimmed)
	if err != nil {
		ref = &url.URL{Path: trimmed}
	}

	resolved := base.ResolveReference(ref)
	resolved.RawQuery = base.RawQuery
	return resolved
}

func replacePathParam(path, name, value string) string {
	return strings.ReplaceAll(path, "{"+name+"}", url.PathEscape(value))
}