Skip to content

Commit

Permalink
Add support for the PaymentIntent resource
Browse files Browse the repository at this point in the history
  • Loading branch information
remi-stripe committed Jul 7, 2018
1 parent 67a9693 commit d7cc37d
Show file tree
Hide file tree
Showing 7 changed files with 441 additions and 1 deletion.
2 changes: 1 addition & 1 deletion .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ cache:

env:
global:
- STRIPE_MOCK_VERSION=0.16.0
- STRIPE_MOCK_VERSION=0.19.0

go:
- "1.7"
Expand Down
1 change: 1 addition & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ lint:
golint -set_exit_status ./loginlink
golint -set_exit_status ./order
golint -set_exit_status ./orderreturn
golint -set_exit_status ./paymentintent
golint -set_exit_status ./paymentsource
golint -set_exit_status ./payout
golint -set_exit_status ./plan
Expand Down
4 changes: 4 additions & 0 deletions client/api.go
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ import (
"github.com/stripe/stripe-go/loginlink"
"github.com/stripe/stripe-go/order"
"github.com/stripe/stripe-go/orderreturn"
"github.com/stripe/stripe-go/paymentintent"
"github.com/stripe/stripe-go/paymentsource"
"github.com/stripe/stripe-go/payout"
"github.com/stripe/stripe-go/plan"
Expand Down Expand Up @@ -98,6 +99,8 @@ type API struct {
Orders *order.Client
// OrderReturns is the client used to invoke /order_returns APIs.
OrderReturns *orderreturn.Client
// PaymentIntents is the client used to invoke /payment_intents APIs.
PaymentIntents *paymentintent.Client
// PaymentSource is used to invoke customer sources related APIs.
PaymentSource *paymentsource.Client
// Payouts is the client used to invoke /payouts APIs.
Expand Down Expand Up @@ -164,6 +167,7 @@ func (a *API) Init(key string, backends *Backends) {
a.LoginLinks = &loginlink.Client{B: backends.API, Key: key}
a.Orders = &order.Client{B: backends.API, Key: key}
a.OrderReturns = &orderreturn.Client{B: backends.API, Key: key}
a.PaymentIntents = &paymentintent.Client{B: backends.API, Key: key}
a.PaymentSource = &paymentsource.Client{B: backends.API, Key: key}
a.Payouts = &payout.Client{B: backends.API, Key: key}
a.Plans = &plan.Client{B: backends.API, Key: key}
Expand Down
175 changes: 175 additions & 0 deletions paymentintent.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,175 @@
package stripe

import (
"encoding/json"
)

type PaymentIntentCaptureMethod string

const (
PaymentIntentCaptureMethodAutomatic PaymentIntentCaptureMethod = "automatic"
PaymentIntentCaptureMethodManual PaymentIntentCaptureMethod = "manual"
)

type PaymentIntentConfirmationMethod string

const (
PaymentIntentConfirmationMethodPublishable PaymentIntentConfirmationMethod = "publishable"
PaymentIntentConfirmationMethodSecret PaymentIntentConfirmationMethod = "secret"
)

type PaymentIntentNextActionType string

const (
PaymentIntentNextActionAuthorizeWithURL PaymentIntentNextActionType = "authorize_with_url"
)

type PaymentIntentStatus string

const (
PaymentIntentStatusCanceled PaymentIntentStatus = "canceled"
PaymentIntentStatusProcessing PaymentIntentStatus = "processing"
PaymentIntentStatusRequiresCapture PaymentIntentStatus = "requires_capture"
PaymentIntentStatusRequiresConfirmation PaymentIntentStatus = "requires_confirmation"
PaymentIntentStatusRequiresSource PaymentIntentStatus = "requires_source"
PaymentIntentStatusRequiresSourceAction PaymentIntentStatus = "requires_source_action"
PaymentIntentStatusSucceeded PaymentIntentStatus = "succeeded"
)

type PaymentIntentTransferDataParams struct {
Amount *int64 `form:"amount"`
}

// PaymentIntentParams is the set of parameters that can be used when handling a payment intent.
type PaymentIntentParams struct {
Params `form:"*"`
AllowedSourceTypes []*string `form:"allowed_source_types"`
Amount *int64 `form:"amount"`
ApplicationFee *int64 `form:"application_fee"`
AttemptConfirmation *bool `form:"attempt_confirmation"`
CaptureMethod *string `form:"capture_method"`
Currency *string `form:"currency"`
Customer *string `form:"customer"`
Description *string `form:"description"`
OnBehalfOf *string `form:"on_behalf_of"`
ReceiptEmail *string `form:"receipt_email"`
ReturnURL *string `form:"return_url"`
SaveSourceToCustomer *bool `form:"save_source_to_customer"`
Shipping *ShippingDetailsParams `form:"shipping"`
Source *string `form:"source"`
StatementDescriptor *string `form:"statement_descriptor"`
TransferData *PaymentIntentTransferDataParams `form:"transfer_data"`
TransferGroup *string `form:"transfer_group"`
}

// PaymentIntentListParams is the set of parameters that can be used when listing payment intents.
// For more details see https://stripe.com/docs/api#list_payouts.
type PaymentIntentListParams struct {
ListParams `form:"*"`
}

type PaymentIntentSourceActionAuthorizeWithURL struct {
URL string `json:"url"`
}

// PaymentIntentSourceActionValue describes the `value` property in `next_source_action`
// The `type` in the parent should indicate which object is fleshed out.
type PaymentIntentSourceActionValue struct {
AuthorizeWithURL *PaymentIntentSourceActionAuthorizeWithURL `json:"-"`
}

type PaymentIntentSourceAction struct {
Type PaymentIntentNextActionType `json:"type"`
Value *PaymentIntentSourceActionValue `json:"-"`
}

// UnmarshalJSON handles deserialization of a PaymentIntentSourceAction.
// This custom unmarshaling is needed because the specific
// type of for `value` it refers to is specified in the `type` property
func (s *PaymentIntentSourceAction) UnmarshalJSON(data []byte) error {
type paymentIntentSourceAction PaymentIntentSourceAction
var v paymentIntentSourceAction
if err := json.Unmarshal(data, &v); err != nil {
return err
}

var err error
*s = PaymentIntentSourceAction(v)
s.Value = &PaymentIntentSourceActionValue{}

// Unmarshal data a second time so that we can get the raw bytes for the
// `value` field
var rawObject map[string]*json.RawMessage
if err := json.Unmarshal(data, &rawObject); err != nil {
return err
}

switch s.Type {
case PaymentIntentNextActionAuthorizeWithURL:
err = json.Unmarshal(*rawObject["value"], &s.Value.AuthorizeWithURL)
}

return err
}

type PaymentIntentTransferData struct {
Amount int64 `json:"amount"`
}

// Payout is the resource representing a Stripe payout.
// For more details see https://stripe.com/docs/api#payouts.
type PaymentIntent struct {
AllowedSourceTypes []string `json:"allowed_source_types"`
Amount int64 `json:"amount"`
AmountCapturable int64 `json:"amount_capturable"`
AmountReceived int64 `json:"amount_received"`
Application *Application `json:"application"`
ApplicationFee int64 `json:"application_fee"`
CanceledAt int64 `json:"canceled_at"`
CaptureMethod PaymentIntentCaptureMethod `json:"capture_method"`
Charges *ChargeList `json:"charges"`
ClientSecret string `json:"client_secret"`
ConfirmationMethod PaymentIntentConfirmationMethod `json:"confirmation_method"`
Created int64 `json:"created"`
Currency string `json:"currency"`
Customer *Customer `json:"customer"`
Description string `json:"description"`
Livemode bool `json:"livemode"`
ID string `json:"id"`
Metadata map[string]string `json:"metadata"`
NextSourceAction *PaymentIntentSourceAction `json:"next_source_action"`
OnBehalfOf *Account `json:"on_behalf_of"`
ReceiptEmail string `json:"receipt_email"`
ReturnURL string `json:"return_url"`
Shipping ShippingDetails `json:"shipping"`
Source *PaymentSource `json:"source"`
StatementDescriptor string `json:"statement_descriptor"`
Status PaymentIntentStatus `json:"status"`
TransferData *PaymentIntentTransferData `json:"transfer_data"`
TransferGroup string `json:"transfer_group"`
}

// PayoutList is a list of payouts as retrieved from a list endpoint.
type PaymentIntentList struct {
ListMeta
Data []*PaymentIntent `json:"data"`
}

// UnmarshalJSON handles deserialization of a Payment Intent.
// This custom unmarshaling is needed because the resulting
// property may be an id or the full struct if it was expanded.
func (p *PaymentIntent) UnmarshalJSON(data []byte) error {
if id, ok := ParseID(data); ok {
p.ID = id
return nil
}

type paymentintent PaymentIntent
var v paymentintent
if err := json.Unmarshal(data, &v); err != nil {
return err
}

*p = PaymentIntent(v)
return nil
}
131 changes: 131 additions & 0 deletions paymentintent/client.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
// Package paymentintent provides API functions related to payment intents.
//
// For more details, see: https://stripe.com/docs/api/go#payment_intents.
package paymentintent

import (
"net/http"

stripe "github.com/stripe/stripe-go"
"github.com/stripe/stripe-go/form"
)

// Client is used to invoke /payment_intents APIs.
type Client struct {
B stripe.Backend
Key string
}

// New creates a payment intent.
func New(params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
return getC().New(params)
}

// New creates a payment intent.
func (c Client) New(params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
intent := &stripe.PaymentIntent{}
err := c.B.Call(http.MethodPost, "/payment_intents", c.Key, params, intent)
return intent, err
}

// Get retrieves a payment intent.
func Get(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
return getC().Get(id, params)
}

// Get retrieves a payment intent.
func (c Client) Get(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
path := stripe.FormatURLPath("/payment_intents/%s", id)
intent := &stripe.PaymentIntent{}
err := c.B.Call(http.MethodGet, path, c.Key, params, intent)
return intent, err
}

// Update updates a payment intent.
func Update(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
return getC().Update(id, params)
}

// Update updates a payment intent.
func (c Client) Update(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
path := stripe.FormatURLPath("/payment_intents/%s", id)
intent := &stripe.PaymentIntent{}
err := c.B.Call(http.MethodPost, path, c.Key, params, intent)
return intent, err
}

// Cancel cancels a payment intent.
func Cancel(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
return getC().Cancel(id, params)
}

// Cancel cancels a payment intent.
func (c Client) Cancel(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
path := stripe.FormatURLPath("/payment_intents/%s/cancel", id)
intent := &stripe.PaymentIntent{}
err := c.B.Call(http.MethodPost, path, c.Key, params, intent)
return intent, err
}

// Capture captures a payment intent.
func Capture(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
return getC().Capture(id, params)
}

// Capture captures a payment intent.
func (c Client) Capture(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
path := stripe.FormatURLPath("/payment_intents/%s/capture", id)
intent := &stripe.PaymentIntent{}
err := c.B.Call(http.MethodPost, path, c.Key, params, intent)
return intent, err
}

// Confirm confirms a payment intent.
func Confirm(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
return getC().Confirm(id, params)
}

// Confirm confirms a payment intent.
func (c Client) Confirm(id string, params *stripe.PaymentIntentParams) (*stripe.PaymentIntent, error) {
path := stripe.FormatURLPath("/payment_intents/%s/confirm", id)
intent := &stripe.PaymentIntent{}
err := c.B.Call(http.MethodPost, path, c.Key, params, intent)
return intent, err
}

// List returns a list of payment intents.
func List(params *stripe.PaymentIntentListParams) *Iter {
return getC().List(params)
}

// List returns a list of payment intents.
func (c Client) List(listParams *stripe.PaymentIntentListParams) *Iter {
return &Iter{stripe.GetIter(listParams, func(p *stripe.Params, b *form.Values) ([]interface{}, stripe.ListMeta, error) {
list := &stripe.PaymentIntentList{}
err := c.B.CallRaw(http.MethodGet, "/payment_intents", c.Key, b, p, list)

ret := make([]interface{}, len(list.Data))
for i, v := range list.Data {
ret[i] = v
}

return ret, list.ListMeta, err
})}
}

// Iter is an iterator for lists of PaymentIntents.
// The embedded Iter carries methods with it;
// see its documentation for details.
type Iter struct {
*stripe.Iter
}

// PaymentIntent returns the most recent PaymentIntent
// visited by a call to Next.
func (i *Iter) PaymentIntent() *stripe.PaymentIntent {
return i.Current().(*stripe.PaymentIntent)
}

func getC() Client {
return Client{stripe.GetBackend(stripe.APIBackend), stripe.Key}
}
Loading

0 comments on commit d7cc37d

Please sign in to comment.