Payments Module Changes Proposal

66 views
Skip to first unread message

Jeremy Shipman

unread,
Dec 21, 2010, 2:09:50 AM12/21/10
to SilverStripe Core Development
I've been putting some serious thought into how the Payment module can
be improved. Whilst the module has been separated from eCommerce, I
think some more work can be done to further decouple it, and make it
more flexible to use, and easier to extend (eg submitting more payment
types).

Your thoughts on any aspect of what I'm proposing are appreciated.

Here's a summary of what I've detailed below:

* I think we firstly need to clearly define what is required of
the Payment module.
* I've also more clearly defined the types of payment gateways
there are, in hopes that common functionality can be abstracted.
* The redirect linking needs to be abstracted, and flexible.
Ie..where the customer is linked back to after paying on the external
gateway.
* Finally I've listed a bunch of feature ideas.

There's also some tickets in trac for Payments that I think really
need to be merged in.

Core Requirements of Payment Module
=============================
* Must not be tied to any particular module – many payment types
are still heavily tied to eCommerce.
* Ability to pay for different objects. Eg: product, event,
subscription …all within one site.
* An integration guide is needed for developers to know how to
incorporate the Payments module into their application / website.
* Provide methods for common functionality
* Provide appropriate hooks for customisation

Payment Type Categories
===================
These could possibly become sub-payment classes to provide common
functionality where appropriate.
View UML sequence diagrams here:
https://code.google.com/p/silverstripe-ecommerce/downloads/detail?name=PaymentsSequenceDiagram.pdf

* Internal Payment – payments made within the store, staff
interaction required to approve, meaning payment is usually slow to
process.
eg: cheque, cash, bank deposit
* External Payment – customer is redirected to an external
gateway site for entering and processing credit card details. External
gateway then redirects the customer back to the merchant website, so a
controller is always needed somewhere to handle the incoming redirect.
eg: Paypal, Paymate, Paystation
* Merchant Hosted Payment – credit card details etc are filled
out in a form on the merchant site. No other site is ever visited by
the customer’s browser. Will require SSL certificate to secure
communications.
eg: DPS?

Final/Success Page Linking
====================
I'm referring to the 'final page' as the URL that is redirected to
after a payment has been completed successfully or unsuccessfully.
Open up the final page redirect options to allow for better
customisation:
* $payment->PaidObject()->Link(‘someaction’);
* $payment->PaidObject()->{someRelation}->Link(‘someaction’);
* Per payment, session stored link?
* Mysite/predefined-page/$PaymentID/$PaidObjectID
* PreDefinedController/someaction/$PaymentID/$PaidObjectID
* Default – home, or PaymentController??
…this link would be retrieved automatically via $payment-
>RedirectURL() based on Payment module configuration settings. Perhaps
this could be customisable based on payment status also, or
overridable via decorator or sub-classing.

Additional Feature Ideas
=================
* Validation – making sure required fields are filled out, and
fields are filled out correctly. This could just be user_errors.
* Allow for a single payment type – ie provide relevant form
fields when there is only one allowed type, instead of radio buttons
all the time.
* Provide a decorator to make something ‘Payable’. This would add
has_many Payments to the parent object. It would also include useful
functions like TotalPaid, createPayment.
* Allow external payments to be filled out within an IFrame. This
simply looks a bit nicer than being redirected to an entirely
different website.
* Allow cross-checking against ip, session id, transaction id etc…
perhaps make it customisable.
* Provide factory methods for quickly creating new payments.

dalesaurus

unread,
Jan 5, 2011, 6:40:15 PM1/5/11
to silverst...@googlegroups.com
All of your points sound good.  With the lack of replies I'm guessing nobody is against decoupling, simplifying, and semantic class structures :)

What about 'strap-on' cart systems like FoxyCart?  It uses JS you add to your header to progressively enhance a page with an AJAXy cart they host, and handles the checkout process on their site/then boots back like PayPal.  Would that be more of its own module in your mind or something that belongs in this discussion?

For the Final/Success Page Linking I can say that is quite overwhelming.  There will always be many needs but I would think something simple would be best in the base class and allow Payment system implementations handle it.  I recently did a Presta Shop gateway and their model can be paraphrased as:

Payment::Submit Payment -> pre-payment-attempt-hook -> Payment::Process Payment -> post-payment-attempt-hook
Where Payment is the base class and the hooks are the implemetation's responsibility.  That way each driver has to deal with Success/Fail in the post-payment-attempt-hook with redirection or destination shuffling.


Some further thoughts on this:

-It would be handy to be able to 'stack' Multiple payment methods to a single payment form (similar to the Member Login form with its Auth drivers).  It is very common to have multiple processors to handle different payment types (and each of those having custom form requirements/processing methods/etc).  This way Factory methods are not really necessary as they would all be part of the base Payment Form.

-Security basics should be baked in to the base (record IP, ProxyIP, useragent, etc) but allow hook/extension for the cross checking you mention.

-I'm not sure I see a real use case for a Payable decorator, as payments are not always 1:1 with a DataObject.  This seems like functionality that is much more at home in the Ecommerce module which deals with invoices/orders/etc.  Although it does raise the question of what one would/should be able to do with Payment and without Ecommerce.

Barry Swaisland

unread,
Jan 6, 2011, 11:34:57 AM1/6/11
to SilverStripe Core Development
I second not extending as in my systems it is a has_many payments
Just to note as well that the name of the data objects should be maybe
SSPayments as suprisinginly I had a payment class and had to do a
bunch of renaming and database admin to just dev/build payments
module

The structure of my payments is currently
PaymentManager
-SagePayManager
-IridiumManager
-PayapalManager (*taken from payments module)

the abstraction is a great idea and that is what I've done myself so
that I could change from one payment provider to another easily. Then
when an old payment needs refunding that is SagePay, but the System
uses Iridium now by default it still executes the refund process
matching that payment.

Iridium is a fairly simple process with security keys...
1)Direct to Irdium (with post vars + verification key)
2)Verify and process post message from iridum

SagePay very annoying with more steps
1)Request a URL from the server (need to store transaction and key
references)
2)Redirect to supplied URL
3)have a page that handle the return URL process, SagePay requests the
"noticifaction" URL to return to from a fixed url on the site, this is
with post data and security keys
4)SagePay redirects to the "notification" URL and the completion of
the order is handled

I'd be happy to help get these to systems into the code and help get
the interface right.

Other points to note about each system is the sending of the any
customer details to the site for a)auto populating the fields (e.g.
address) and b) displaying cart information as just a string to allow
for anything to be paid (if in fact the system requires any knowledge
of the cart info).

Also branding of the site could be helped with, I can see some stuff
for paypal, but for the systems I use there is documentation and
examples that would be useful to be bundled into the system. I would
disagree about using an iframe as the browser should be totally
secure, rather that report some things on this page are secure and
some are not right?

Dan Rye

unread,
Jan 6, 2011, 12:00:39 PM1/6/11
to silverst...@googlegroups.com
webbower is also working on authorize.net support.


I plan to help with his contribution by testing with 2.4.  He has written it for 2.3.


--
You received this message because you are subscribed to the Google Groups "SilverStripe Core Development" group.
To post to this group, send email to silverst...@googlegroups.com.
To unsubscribe from this group, send email to silverstripe-d...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/silverstripe-dev?hl=en.


dalesaurus

unread,
Jan 7, 2011, 10:32:51 AM1/7/11
to SilverStripe Core Development
@Barry; I agree that returns are a super pain. That is another reason
in my mind to not create an Object level decorator for Payable. I
think they belong to the Payment module as a PaymentTransaction object
and let the implementation in Ecommerce or whatever deal with the
details.

Also Branding is very important to many of the processors/gateways.
Some have very specific requirements on embedding logos, size, copy,
etc. Chase PaymentTech has a wonky system that requires you to
authorize your secure site URL and embed a JS callback to verifiy it
is your site calling that will then embed the logo. You can have your
account suspended or denied approval for production if not in 100%
compliance (at least, this was the case ~1 year ago).

I have fully working api wrappers for Authorize.net and Chase
PaymentTech (including recurring payments and refunds). I'd be happy
to contribute or help testing. Get at me via email if there is
interest in adding these. Is anyone in charge here? :)
> > "SilverStripe Core Development" group.> To post to this group, send email tosilvers...@googlegroups.com.
> > To unsubscribe from this group, send email to>silverstripe-d...@googlegroups.com<silverstripe-dev%2Bunsu...@googlegroups.com>
> > .

Nicolaas Thiemen Francken - Sunny Side Up

unread,
Jan 8, 2011, 10:56:17 PM1/8/11
to silverst...@googlegroups.com
Hi Dale

It would be super useful to "make available" any of the payment.  If you have one then please contact me and I will add you with commit rights to an e-commerce payment module.

Also - anyone - who would like to contribute to e-commerce please contact Jeremy or me and we will get you on board.

Cheers

Nicolaas

Barry Swaisland

unread,
Jan 10, 2011, 4:45:31 AM1/10/11
to SilverStripe Core Development
Hi Nicolass,

I'm very interested in helping move this forward and can make
available the SagePay and Iridium stuff - there is another guy on the
list emailing me to ask for this to go in - I'd like to more the
payments forward to decouple them more from the ecommerce as Jeremy
has indicated and use that. I'll send you a mail now and also forward
your email to inCharge.

Barry


On Jan 9, 3:56 am, Nicolaas Thiemen Francken - Sunny Side Up

Barry Swaisland

unread,
Jan 10, 2011, 10:13:28 AM1/10/11
to SilverStripe Core Development
I've created another group to discuss this and even uploaded my code
to get the ball rolling...
http://groups.google.com/group/silverstripe-payments-module

Dan Rye

unread,
Jan 10, 2011, 10:36:55 AM1/10/11
to silverstripe-dev, silverstrip...@googlegroups.com
Do we need a new group, or should it be done within the silverstripe-ecommerce group?

--
You received this message because you are subscribed to the Google Groups "SilverStripe Core Development" group.
To post to this group, send email to silverst...@googlegroups.com.
To unsubscribe from this group, send email to silverstripe-d...@googlegroups.com.

Barry Swaisland

unread,
Jan 10, 2011, 11:16:37 AM1/10/11
to SilverStripe Core Development
Well I am not bothered if no one uses it. You can got there an get
SagePay and Iridium code if you like.

Personally I'd say it is the only way to decouple payments - to treat
it as a different module. I am interested in eCommerce but not that
much because I have a completely different system - I am EXTREMELY
interested in a nice payments module.
> > silverstripe-d...@googlegroups.com<silverstripe-dev%2Bunsubscrib e...@googlegroups.com>
> > .

Dan Rye

unread,
Jan 10, 2011, 11:58:00 AM1/10/11
to silverst...@googlegroups.com
I don't disagree, however the guys working on eCommerce is working on payments also right now.  They are making a push for a lot of updates in the coming weeks.  Just wanted to make sure everyone was in the loop, and on the same page.

To unsubscribe from this group, send email to silverstripe-d...@googlegroups.com.

Jeremy Shipman

unread,
Jan 10, 2011, 5:07:56 PM1/10/11
to SilverStripe Core Development
@Dale, I think Foxy cart would be in it's own module, as you suggest.
Unless somehow it can be used as a payment gateway/type/method (which
is what I believe the Payment module is all about).

@Dale, yes the Final/Success linking list there is a bit
extensive...but I think it was useful to make such a list. I do
however like your idea of having pre/post callback hooks...which would
allow for great flexibility. How would you go about adding
these?...keeping in mind that we need to allow payments for multiple
modules at once.

@Barry & Dale: the Payable decorator would be an optional thing, that
I thought might help for the cases where people want to allow to use
another payment method when another fails. Eg bank, when credit card
fails. It could even be named something else, if it causes confusion.
It was not my intention that Payable handle the return linking. I
think this should be done by Payment_Controller, or
ExternalPayment_Controller ...depending on if/how Payments are
subclassed.

@Barry As per my diagrams: Iridium sounds like a "Merchant Hosted
Payment" and SagePay sounds like an "External Gateway Payment".
Something important that you brought up, and I haven't really thought
about is the ability to refund payments.

@Dan & Barry: I think it would be a good idea to have the Payment
module entirely moved to a place where more developers can contribute
easier. Before starting this thread I have been in touch with Norman,
who is the current developer. I think he's keen for such community
involvement, so I'm guessing he'll be open to it.

Other ideas that has come to mind:

* It might also be useful to standardize/abstract all the shipping /
contact info fields. In other words we define a big list of
standardized field names: name, phone, street name & number, city,
suburb, country etc. This would serve as a middle point between module
and payment so you're not having to always customize your module to
use the right field names for each payment type. Payment type
developers could then draw from this standardized list of fields to
connect in to the gateway they are developing for.
I'm sure this won't work in all cases, and we would allow for still
using custom fields if desired.
...unless anyone sees a better way to do this?

* Make the list of payment types customisable when introducing into a
form.

* Move payment name into the payment type itself, rather than being in
the Payment::$supported_methods array.

* Payment types could be stored in individual module folders. We're
already doing this in the eCommerce module, serving as a temporary
place for our additional payment types. Each payment would be stored
as payment_paymenttype. This way you don't get all the unecessary
gateways being included in your site, and it also means logos etc can
be referenced as payment_paymenttype/images/logo.jpg. SilverStripe LTD
have apparently already done something like this with their internal
version of Payments.

* Along with a set of guidelines/instructions, it would be good to
provide a template for developing new gateways.



I think the best way to move forward from here is to collaboratively
come up with a new Payment.php class (and possibly sub-classes), along
with template(s) for creating a new payment type. I might give this a
shot when I get time, but I'm open to anyone else having a go also.

Barry Swaisland

unread,
Jan 13, 2011, 4:28:32 AM1/13/11
to SilverStripe Core Development
Jeremy,

> @Barry & Dale: the Payable decorator would be an optional thing, that
> I thought might help for the cases where people want to allow to use
> another payment method when another fails. Eg bank, when credit card
> fails. It could even be named something else, if it causes confusion.
> It was not my intention that Payable handle the return linking. I
> think this should be done by Payment_Controller, or
> ExternalPayment_Controller ...depending on if/how Payments are
> subclassed.


> @Barry As per my diagrams: Iridium sounds like a "Merchant Hosted
> Payment" and SagePay sounds like an "External Gateway Payment".
> Something important that you brought up, and I haven't really thought
> about is the ability to refund payments.

I totally missed the diagram - you have really thought this through
and it is indeed very comprehensive.

> @Dan & Barry: I think it would be a good idea to have the Payment
> module entirely moved to a place where more developers can contribute
> easier. Before starting this thread I have been in touch with Norman,
> who is the current developer. I think he's keen for such community
> involvement, so I'm guessing he'll be open to it.

With the group setup and discussion starting - anyone can join - of
course I have invited you specifically

> Other ideas that has come to mind:
>
> * It might also be useful to standardize/abstract all the shipping /
> contact info fields. In other words we define a big list of
> standardized field names: name, phone, street name & number, city,
> suburb, country etc. This would serve as a middle point between module
> and payment so you're not having to always customize your module to
> use the right field names for each payment type. Payment type
> developers could then draw from this standardized list of fields to
> connect in to the gateway they are developing for.
> I'm sure this won't work in all cases, and we would allow for still
> using custom fields if desired.
> ...unless anyone sees a better way to do this?

Yes I agree we could have the standard fields that are required when
redirecting to these payment gateways - for example sagepay and iridum
both accept the address posted to them, but other than that just the
currency and amount (no basket info). There are things like
transaction ids and security ID's to take into consideration that are
needed during the process.

> * Make the list of payment types customisable when introducing into a
> form.
>
> * Move payment name into the payment type itself, rather than being in
> the Payment::$supported_methods array.

The Payments could be indicated by a property of the class or that it
is a subclass of Payment - (e.g. $classes =
ClassInfo::subclassesFor("Payment");)

> * Payment types could be stored in individual module folders. We're
> already doing this in the eCommerce module, serving as a temporary
> place for our additional payment types. Each payment would be stored
> as payment_paymenttype. This way you don't get all the unecessary
> gateways being included in your site, and it also means logos etc can
> be referenced as payment_paymenttype/images/logo.jpg. SilverStripe LTD
> have apparently already done something like this with their internal
> version of Payments.
>
> * Along with a set of guidelines/instructions, it would be good to
> provide a template for developing new gateways.
>
> I think the best way to move forward from here is to collaboratively
> come up with a new Payment.php class (and possibly sub-classes), along
> with template(s) for creating a new payment type. I might give this a
> shot when I get time, but I'm open to anyone else having a go also.

Based on your PDF?
Reply all
Reply to author
Forward
0 new messages