diff --git a/.travis.yml b/.travis.yml
index 3a8da30999..56f22e0a71 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -70,6 +70,7 @@ script:
- cd ../SettingsBundle; ../../../../bin/phpspec run -fpretty --verbose
- cd ../PromotionsBundle; ../../../../bin/phpspec run -fpretty --verbose
- cd ../PaymentsBundle; ../../../../bin/phpspec run -fpretty --verbose
+ - cd ../PayumBundle; ../../../../bin/phpspec run -fpretty --verbose
notifications:
email: "travis-ci@sylius.org"
diff --git a/app/AppKernel.php b/app/AppKernel.php
index aa81c8ac94..e50c8a966f 100644
--- a/app/AppKernel.php
+++ b/app/AppKernel.php
@@ -39,6 +39,7 @@ class AppKernel extends Kernel
new Sylius\Bundle\TaxationBundle\SyliusTaxationBundle(),
new Sylius\Bundle\ShippingBundle\SyliusShippingBundle(),
new Sylius\Bundle\PaymentsBundle\SyliusPaymentsBundle(),
+ new Sylius\Bundle\PayumBundle\SyliusPayumBundle(),
new Sylius\Bundle\PromotionsBundle\SyliusPromotionsBundle(),
new Sylius\Bundle\AddressingBundle\SyliusAddressingBundle(),
new Sylius\Bundle\InventoryBundle\SyliusInventoryBundle(),
@@ -71,6 +72,7 @@ class AppKernel extends Kernel
new Stof\DoctrineExtensionsBundle\StofDoctrineExtensionsBundle(),
new JMS\TranslationBundle\JMSTranslationBundle(),
new Knp\Bundle\SnappyBundle\KnpSnappyBundle(),
+ new Payum\Bundle\PayumBundle\PayumBundle(),
);
if (in_array($this->getEnvironment(), array('dev'))) {
diff --git a/app/config/config.yml b/app/config/config.yml
index 4c8942aeab..3aa43e125a 100644
--- a/app/config/config.yml
+++ b/app/config/config.yml
@@ -2,6 +2,7 @@ imports:
- { resource: parameters.yml }
- { resource: security.yml }
- { resource: sylius.yml }
+ - { resource: payum.yml }
framework:
translator: { fallback: %sylius.locale% }
@@ -129,4 +130,4 @@ knp_snappy:
image:
enabled: true
binary: /usr/bin/wkhtmltoimage
- options: []
+ options: []
\ No newline at end of file
diff --git a/app/config/parameters.yml.dist b/app/config/parameters.yml.dist
index 908745347d..6fc6b6f203 100644
--- a/app/config/parameters.yml.dist
+++ b/app/config/parameters.yml.dist
@@ -17,3 +17,11 @@ parameters:
sylius.currency: EUR
sylius.cache: file_system
+
+ paypal.express_checkout.username: EDITME
+ paypal.express_checkout.password: EDITME
+ paypal.express_checkout.signature: EDITME
+ paypal.express_checkout.sandbox: true
+
+ stripe.secret_key: EDITME
+ stripe.test_mode: true
\ No newline at end of file
diff --git a/app/config/payum.yml b/app/config/payum.yml
new file mode 100644
index 0000000000..3bd2e77f03
--- /dev/null
+++ b/app/config/payum.yml
@@ -0,0 +1,60 @@
+payum:
+ security:
+ token_storage:
+ Sylius\Bundle\PayumBundle\Model\PaymentSecurityToken:
+ doctrine:
+ driver: orm
+
+ contexts:
+ paypal_express_checkout:
+ paypal_express_checkout_nvp:
+ api:
+ options:
+ username: %paypal.express_checkout.username%
+ password: %paypal.express_checkout.password%
+ signature: %paypal.express_checkout.signature%
+ sandbox: %paypal.express_checkout.sandbox%
+ actions:
+ - sylius.payum.action.capture_order_with_paypal
+ - sylius.payum.action.order_status
+
+ storages:
+ Sylius\Bundle\CoreBundle\Model\Order:
+ doctrine:
+ driver: orm
+ Sylius\Bundle\PaymentsBundle\Model\Payment:
+ doctrine:
+ driver: orm
+
+ stripe:
+ omnipay:
+ type: Stripe
+ options:
+ apiKey: %stripe.secret_key%
+ testMode: %stripe.test_mode%
+ actions:
+ - sylius.payum.action.capture_order_with_stripe
+ - sylius.payum.action.obtain_credit_card
+ - sylius.payum.action.order_status
+
+ storages:
+ Sylius\Bundle\CoreBundle\Model\Order:
+ doctrine:
+ driver: orm
+ Sylius\Bundle\PaymentsBundle\Model\Payment:
+ doctrine:
+ driver: orm
+
+ dummy:
+ custom:
+ actions:
+ - sylius.payum.action.capture_order_with_dummy
+ - sylius.payum.action.dummy_order_status
+
+ storages:
+ Sylius\Bundle\CoreBundle\Model\Order:
+ doctrine:
+ driver: orm
+ Sylius\Bundle\PaymentsBundle\Model\Payment:
+ doctrine:
+ driver: orm
\ No newline at end of file
diff --git a/app/config/routing.yml b/app/config/routing.yml
index ff28e08a03..e0bf074933 100644
--- a/app/config/routing.yml
+++ b/app/config/routing.yml
@@ -4,6 +4,9 @@ sylius_installer:
sylius_web:
resource: @SyliusWebBundle/Resources/config/routing/main.yml
+payum_capture:
+ resource: "@PayumBundle/Resources/config/routing/capture.xml"
+
fos_user_security:
resource: "@FOSUserBundle/Resources/config/routing/security.xml"
diff --git a/app/config/sylius.yml b/app/config/sylius.yml
index ceb6b5c7f8..d46e56167c 100644
--- a/app/config/sylius.yml
+++ b/app/config/sylius.yml
@@ -72,6 +72,9 @@ sylius_payments:
dummy: Test
stripe: Stripe
+sylius_payum:
+ driver: doctrine/orm
+
sylius_addressing:
classes:
address:
diff --git a/composer.json b/composer.json
index edf7e70e6d..e1917c56d0 100644
--- a/composer.json
+++ b/composer.json
@@ -1,3 +1,4 @@
+
{
"name": "sylius/sylius",
"type": "project",
@@ -38,7 +39,6 @@
"liip/doctrine-cache-bundle": "*",
"liip/imagine-bundle": "~0.9",
"mathiasverraes/money": "*@dev",
- "omnipay/omnipay": "*@dev",
"sensio/distribution-bundle": "2.3.*",
"stof/doctrine-extensions-bundle": "1.1.*",
"symfony/assetic-bundle": "2.3.*",
@@ -47,7 +47,12 @@
"symfony/swiftmailer-bundle": "2.3.*",
"symfony/symfony": "~2.3",
"twig/extensions": "1.0.*",
- "white-october/pagerfanta-bundle": "1.0.*@dev"
+ "white-october/pagerfanta-bundle": "1.0.*@dev",
+ "omnipay/omnipay": "1.0.*",
+ "payum/payum": "0.6.*@dev",
+ "payum/payum-bundle": "0.6.*@dev",
+ "payum/paypal-express-checkout-nvp": "0.6.*@dev",
+ "payum/omnipay-bridge": "0.6.*@dev"
},
"require-dev": {
"behat/behat": "2.4.*@stable",
diff --git a/composer.lock b/composer.lock
index c85adf4d55..2453f972ee 100644
--- a/composer.lock
+++ b/composer.lock
@@ -3,7 +3,7 @@
"This file locks the dependencies of your project to a known state",
"Read more about it at http://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file"
],
- "hash": "44206bb63f0af4d9594c308f6dcbb0cc",
+ "hash": "275dc038a243748ecf2b11bfb9340c59",
"packages": [
{
"name": "athari/yalinqo",
@@ -53,12 +53,12 @@
"source": {
"type": "git",
"url": "https://github.com/doctrine/annotations.git",
- "reference": "40db0c96985aab2822edbc4848b3bd2429e02670"
+ "reference": "v1.1.2"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/doctrine/annotations/zipball/40db0c96985aab2822edbc4848b3bd2429e02670",
- "reference": "40db0c96985aab2822edbc4848b3bd2429e02670",
+ "url": "https://api.github.com/repos/doctrine/annotations/zipball/v1.1.2",
+ "reference": "v1.1.2",
"shasum": ""
},
"require": {
@@ -773,17 +773,17 @@
"source": {
"type": "git",
"url": "https://github.com/FriendsOfSymfony/FOSRest.git",
- "reference": "9a84df8220553e2ae3163b8325a3c4c2e9792426"
+ "reference": "0.8.0"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/FriendsOfSymfony/FOSRest/zipball/9a84df8220553e2ae3163b8325a3c4c2e9792426",
- "reference": "9a84df8220553e2ae3163b8325a3c4c2e9792426",
+ "url": "https://api.github.com/repos/FriendsOfSymfony/FOSRest/zipball/0.8.0",
+ "reference": "0.8.0",
"shasum": ""
},
"require": {
"php": ">=5.3.2",
- "symfony/http-foundation": "~2.0"
+ "symfony/http-foundation": ">=2.0,<3.0"
},
"type": "library",
"extra": {
@@ -1644,7 +1644,7 @@
],
"authors": [
{
- "name": "Johannes M. Schmitt",
+ "name": "Johannes Schmitt",
"email": "schmittjoh@gmail.com",
"homepage": "http://jmsyst.com",
"role": "Developer of wrapped JMSSerializerBundle"
@@ -2159,6 +2159,54 @@
],
"time": "2013-07-19 00:03:27"
},
+ {
+ "name": "kriswallsmith/buzz",
+ "version": "v0.10",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/kriswallsmith/Buzz.git",
+ "reference": "759432d66387e3433d3b06cb6f773b97225b9b17"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/kriswallsmith/Buzz/zipball/759432d66387e3433d3b06cb6f773b97225b9b17",
+ "reference": "759432d66387e3433d3b06cb6f773b97225b9b17",
+ "shasum": ""
+ },
+ "require": {
+ "php": ">=5.3.0"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "3.7.*"
+ },
+ "suggest": {
+ "ext-curl": "*"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-0": {
+ "Buzz": "lib/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Kris Wallsmith",
+ "email": "kris.wallsmith@gmail.com",
+ "homepage": "http://kriswallsmith.net/"
+ }
+ ],
+ "description": "Lightweight HTTP client",
+ "homepage": "https://github.com/kriswallsmith/Buzz",
+ "keywords": [
+ "curl",
+ "http client"
+ ],
+ "time": "2013-05-19 03:41:15"
+ },
{
"name": "liip/doctrine-cache-bundle",
"version": "1.0.3",
@@ -2231,7 +2279,7 @@
"symfony/options-resolver": ">=2.0.16,~2.0"
},
"require-dev": {
- "symfony/yaml": ">=2.0.16,~2.0",
+ "symfony/yaml": ">=2.0.16.0,>=2.0,<3.0",
"twig/twig": ">=1.0,<2.0-dev"
},
"suggest": {
@@ -2383,13 +2431,13 @@
"version": "v0.9.1",
"source": {
"type": "git",
- "url": "https://github.com/nikic/PHP-Parser.git",
- "reference": "b1cc9ce676b4350b23d0fafc8244d08eee2fe287"
+ "url": "https://github.com/nikic/PHP-Parser",
+ "reference": "v0.9.1"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/nikic/PHP-Parser/zipball/b1cc9ce676b4350b23d0fafc8244d08eee2fe287",
- "reference": "b1cc9ce676b4350b23d0fafc8244d08eee2fe287",
+ "url": "https://github.com/nikic/PHP-Parser/archive/v0.9.1.zip",
+ "reference": "v0.9.1",
"shasum": ""
},
"require": {
@@ -2415,20 +2463,20 @@
"parser",
"php"
],
- "time": "2012-04-23 22:52:11"
+ "time": "2012-04-23 15:52:11"
},
{
"name": "omnipay/omnipay",
- "version": "dev-master",
+ "version": "v1.0.4",
"source": {
"type": "git",
"url": "https://github.com/adrianmacneil/omnipay.git",
- "reference": "4de6c429661af33ce6323d9a58f60b4e82fcf35d"
+ "reference": "4f5e82232161939c0b14f5921c092ed77980d450"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/adrianmacneil/omnipay/zipball/4de6c429661af33ce6323d9a58f60b4e82fcf35d",
- "reference": "4de6c429661af33ce6323d9a58f60b4e82fcf35d",
+ "url": "https://api.github.com/repos/adrianmacneil/omnipay/zipball/4f5e82232161939c0b14f5921c092ed77980d450",
+ "reference": "4f5e82232161939c0b14f5921c092ed77980d450",
"shasum": ""
},
"require": {
@@ -2445,11 +2493,6 @@
"twig/twig": "~1.12"
},
"type": "library",
- "extra": {
- "branch-alias": {
- "dev-master": "1.0.x-dev"
- }
- },
"autoload": {
"psr-0": {
"Omnipay": "src/"
@@ -2486,7 +2529,6 @@
"merchant",
"migs",
"mollie",
- "multisafepay",
"netaxept",
"netbanx",
"pay",
@@ -2503,11 +2545,10 @@
"stripe",
"tala",
"tala-payments",
- "targetpay",
"twocheckout",
"worldpay"
],
- "time": "2013-10-10 23:03:59"
+ "time": "2013-09-20 23:40:41"
},
{
"name": "pagerfanta/pagerfanta",
@@ -2571,6 +2612,267 @@
],
"time": "2013-09-23 08:06:55"
},
+ {
+ "name": "payum/omnipay-bridge",
+ "version": "dev-master",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Payum/OmnipayBridge.git",
+ "reference": "da2a1c061efe27ecc8006bc8c7e7e7ba7a17e763"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Payum/OmnipayBridge/zipball/da2a1c061efe27ecc8006bc8c7e7e7ba7a17e763",
+ "reference": "da2a1c061efe27ecc8006bc8c7e7e7ba7a17e763",
+ "shasum": ""
+ },
+ "require": {
+ "omnipay/omnipay": "1.0.*",
+ "payum/payum": "0.6.x-dev",
+ "php": ">=5.3.2"
+ },
+ "require-dev": {
+ "phpunit/phpunit": "3.7.*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "0.6-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Payum\\Bridge\\Omnipay": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Kotlyar Maksim",
+ "email": "kotlyar.maksim@gmail.com"
+ }
+ ],
+ "description": "This bridge allows you to use omnipay gateways but in payum like way.",
+ "homepage": "https://github.com/Payum/OmnipayBridge",
+ "keywords": [
+ "omnipay",
+ "payment"
+ ],
+ "time": "2013-07-31 10:48:07"
+ },
+ {
+ "name": "payum/paypal-express-checkout-nvp",
+ "version": "dev-master",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Payum/PaypalExpressCheckoutNvp.git",
+ "reference": "7aaaf140b5348a9676feb87881df5893b84b06f9"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Payum/PaypalExpressCheckoutNvp/zipball/7aaaf140b5348a9676feb87881df5893b84b06f9",
+ "reference": "7aaaf140b5348a9676feb87881df5893b84b06f9",
+ "shasum": ""
+ },
+ "require": {
+ "kriswallsmith/buzz": "*",
+ "payum/payum": "0.6.x-dev",
+ "php": ">=5.3.2"
+ },
+ "require-dev": {
+ "doctrine/mongodb-odm": "~1.0@dev",
+ "doctrine/orm": ">=2.3,<2.4-dev",
+ "ext-curl": "*",
+ "ext-pdo_sqlite": "*",
+ "fp/testo": "dev-master",
+ "phpunit/phpunit": "3.7.*"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "0.6-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Payum\\Paypal\\ExpressCheckout\\Nvp": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Kotlyar Maksim",
+ "email": "kotlyar.maksim@gmail.com"
+ }
+ ],
+ "description": "Paypal express checkout",
+ "keywords": [
+ "digital goods",
+ "express checkout",
+ "payment",
+ "paypal",
+ "recurring payment"
+ ],
+ "time": "2013-10-10 20:10:49"
+ },
+ {
+ "name": "payum/payum",
+ "version": "dev-master",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Payum/Payum.git",
+ "reference": "57b553f6dac1e4a2499f3f79797447476f9d9542"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Payum/Payum/zipball/57b553f6dac1e4a2499f3f79797447476f9d9542",
+ "reference": "57b553f6dac1e4a2499f3f79797447476f9d9542",
+ "shasum": ""
+ },
+ "require": {
+ "kriswallsmith/buzz": "*",
+ "php": ">=5.3.2"
+ },
+ "require-dev": {
+ "doctrine/mongodb": "1.0.*@dev",
+ "doctrine/mongodb-odm": "1.0.*@dev",
+ "doctrine/orm": "2.*",
+ "ext-curl": "*",
+ "ext-pdo_sqlite": "*",
+ "fp/testo": "dev-master",
+ "phpunit/phpunit": "3.7.*",
+ "psr/log": "~1.0"
+ },
+ "suggest": {
+ "doctrine/mongodb-odm": "If you want to store models to mongo doctrin2 ODM",
+ "doctrine/orm": "If you want to store models to database using doctrin2 ORM",
+ "monolog/monolog": "In case you want to use logger",
+ "payum/authorize-net-aim": "If you want to use Authorize.Net AIM payment gateway",
+ "payum/be2bill": "If you want to use be2bill payment gateway",
+ "payum/omnipay-bridge": "If you want to use omnipay's gateways",
+ "payum/paypal-express-checkout-nvp": "If you want to use paypal express checkout, digital goods or recurring payments",
+ "payum/paypal-ipn": "If you want to use paypal instant payment notifications(Paypal IPN)",
+ "payum/paypal-pro-checkout-nvp": "If you want to use paypal pro checkout"
+ },
+ "type": "library",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "0.6-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Payum": "src/"
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Kotlyar Maksim",
+ "email": "kotlyar.maksim@gmail.com"
+ }
+ ],
+ "description": "Payment lib",
+ "keywords": [
+ "authorize.net",
+ "be2bill",
+ "omnipay gateways",
+ "payment",
+ "paypal",
+ "paypal digital goods",
+ "paypal ipn",
+ "paypal recurring payments"
+ ],
+ "time": "2013-10-14 18:47:40"
+ },
+ {
+ "name": "payum/payum-bundle",
+ "version": "dev-master",
+ "target-dir": "Payum/Bundle/PayumBundle",
+ "source": {
+ "type": "git",
+ "url": "https://github.com/Payum/PayumBundle.git",
+ "reference": "7f4708009c256b2dcc5dea378e8c003e61c3c09c"
+ },
+ "dist": {
+ "type": "zip",
+ "url": "https://api.github.com/repos/Payum/PayumBundle/zipball/7f4708009c256b2dcc5dea378e8c003e61c3c09c",
+ "reference": "7f4708009c256b2dcc5dea378e8c003e61c3c09c",
+ "shasum": ""
+ },
+ "require": {
+ "payum/payum": "0.6.x-dev",
+ "php": ">=5.3.2",
+ "symfony/framework-bundle": "2.*"
+ },
+ "require-dev": {
+ "doctrine/orm": "*",
+ "fp/testo": "@dev",
+ "payum/authorize-net-aim": "0.6.x-dev",
+ "payum/be2bill": "0.6.x-dev",
+ "payum/omnipay-bridge": "0.6.x-dev",
+ "payum/payex": "0.6.x-dev",
+ "payum/paypal-express-checkout-nvp": "0.6.x-dev",
+ "payum/paypal-pro-checkout-nvp": "0.6.x-dev",
+ "phpunit/phpunit": "*"
+ },
+ "suggest": {
+ "payum/authorize-net-aim": "If you want to use authorize.net gateway",
+ "payum/be2bill": "If you want to use be2bill gateway",
+ "payum/omnipay-bridge": "If you want to use omnipay provided gateways",
+ "payum/payex": "If you want to use payex gateway",
+ "payum/paypal-express-checkout-nvp": "If you want to use paypal express checkout nvp gateway",
+ "payum/paypal-pro-checkout-nvp": "If you want to use paypal pro checkout nvp gateway"
+ },
+ "type": "symfony-bundle",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "0.6-dev"
+ }
+ },
+ "autoload": {
+ "psr-0": {
+ "Payum\\Bundle\\PayumBundle": ""
+ }
+ },
+ "notification-url": "https://packagist.org/downloads/",
+ "license": [
+ "MIT"
+ ],
+ "authors": [
+ {
+ "name": "Kotlyar Maksim",
+ "email": "kotlyar.maksim@gmail.com"
+ },
+ {
+ "name": "Community",
+ "homepage": "https://github.com/Payum/PayumBundle/graphs/contributors"
+ }
+ ],
+ "description": "The payment bundle integrates payum libs into symfony2 framework",
+ "homepage": "https://github.com/Payum/PayumBundle",
+ "keywords": [
+ "authorize.net",
+ "be2bill",
+ "omnipay",
+ "payex",
+ "payment",
+ "paypal",
+ "paypal express checkout",
+ "paypal pro checkout",
+ "paypal recurring payment"
+ ],
+ "time": "2013-09-30 20:51:39"
+ },
{
"name": "phpcollection/phpcollection",
"version": "0.2.0",
@@ -2675,13 +2977,13 @@
"version": "1.0.0",
"source": {
"type": "git",
- "url": "https://github.com/php-fig/log.git",
- "reference": "fe0936ee26643249e916849d48e3a51d5f5e278b"
+ "url": "https://github.com/php-fig/log",
+ "reference": "1.0.0"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/php-fig/log/zipball/fe0936ee26643249e916849d48e3a51d5f5e278b",
- "reference": "fe0936ee26643249e916849d48e3a51d5f5e278b",
+ "url": "https://github.com/php-fig/log/archive/1.0.0.zip",
+ "reference": "1.0.0",
"shasum": ""
},
"type": "library",
@@ -3864,12 +4166,12 @@
"source": {
"type": "git",
"url": "https://github.com/phpspec/php-diff.git",
- "reference": "8d82ac415225fac373a4073ba14b1fe286aa2312"
+ "reference": "v1.0.1"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/phpspec/php-diff/zipball/8d82ac415225fac373a4073ba14b1fe286aa2312",
- "reference": "8d82ac415225fac373a4073ba14b1fe286aa2312",
+ "url": "https://api.github.com/repos/phpspec/php-diff/zipball/v1.0.1",
+ "reference": "v1.0.1",
"shasum": ""
},
"type": "library",
@@ -4028,8 +4330,11 @@
"knplabs/knp-gaufrette-bundle": 20,
"knplabs/knp-snappy-bundle": 20,
"mathiasverraes/money": 20,
- "omnipay/omnipay": 20,
"white-october/pagerfanta-bundle": 20,
+ "payum/payum": 20,
+ "payum/payum-bundle": 20,
+ "payum/paypal-express-checkout-nvp": 20,
+ "payum/omnipay-bridge": 20,
"behat/behat": 0,
"phpspec/phpspec": 20
},
diff --git a/features/frontend/checkout_finalize.feature b/features/frontend/checkout_finalize.feature
index a350ecceb3..bbfcef9302 100644
--- a/features/frontend/checkout_finalize.feature
+++ b/features/frontend/checkout_finalize.feature
@@ -20,8 +20,8 @@ Feature: Checkout finalization
| zone | name |
| UK | DHL Express |
And the following payment methods exist:
- | name | gateway | enabled |
- | Credit Card | stripe | yes |
+ | name | gateway | enabled |
+ | Dummy | dummy | yes |
Scenario: Placing the order
Given I am logged in user
@@ -31,7 +31,7 @@ Feature: Checkout finalization
And I press "Continue"
And I select the "DHL Express" radio button
And I press "Continue"
- And I select the "Credit Card" radio button
+ And I select the "Dummy" radio button
And I press "Continue"
When I click "Place order"
Then I should be on the store homepage
diff --git a/features/frontend/checkout_security.feature b/features/frontend/checkout_security.feature
index 2d9f72ada7..3669a95bd1 100644
--- a/features/frontend/checkout_security.feature
+++ b/features/frontend/checkout_security.feature
@@ -24,8 +24,8 @@ Feature: Checkout security
| zone | name |
| UK | DHL Express |
And the following payment methods exist:
- | name | gateway | enabled |
- | Credit Card | stripe | yes |
+ | name | gateway | enabled |
+ | Dummy | dummy | yes |
And I added product "PHP Top" to cart
And I go to the checkout start page
@@ -62,7 +62,7 @@ Feature: Checkout security
And I press "Continue"
And I select the "DHL Express" radio button
And I press "Continue"
- And I select the "Credit Card" radio button
+ And I select the "Dummy" radio button
And I press "Continue"
And I click "Place order"
Then I should be on the store homepage
diff --git a/features/frontend/checkout_taxation.feature b/features/frontend/checkout_taxation.feature
index df01df1c9b..931bfe9046 100644
--- a/features/frontend/checkout_taxation.feature
+++ b/features/frontend/checkout_taxation.feature
@@ -26,8 +26,8 @@ Feature: Checkout taxation
| zone | name |
| UK | DHL Express |
And the following payment methods exist:
- | name | gateway | enabled |
- | Credit Card | stripe | yes |
+ | name | gateway | enabled |
+ | Dummy | dummy | yes |
And I am logged in user
And I added product "PHP Top" to cart
And I go to the checkout start page
@@ -37,7 +37,7 @@ Feature: Checkout taxation
And I press "Continue"
And I select the "DHL Express" radio button
And I press "Continue"
- And I select the "Credit Card" radio button
+ And I select the "Dummy" radio button
When I press "Continue"
Then I should be on the checkout finalize step
And "Tax total: €37.50" should appear on the page
diff --git a/src/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenario.php b/src/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenario.php
index 505c48bbe6..6b88f0d5e5 100644
--- a/src/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenario.php
+++ b/src/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenario.php
@@ -52,6 +52,7 @@ class CheckoutProcessScenario implements ProcessScenarioInterface
->add('shipping', 'sylius_checkout_shipping')
->add('payment', 'sylius_checkout_payment')
->add('finalize', 'sylius_checkout_finalize')
+ ->add('purchase', 'sylius_checkout_purchase')
;
$builder
diff --git a/src/Sylius/Bundle/CoreBundle/Checkout/Step/FinalizeStep.php b/src/Sylius/Bundle/CoreBundle/Checkout/Step/FinalizeStep.php
index 278f7994b7..a33b6f32d8 100644
--- a/src/Sylius/Bundle/CoreBundle/Checkout/Step/FinalizeStep.php
+++ b/src/Sylius/Bundle/CoreBundle/Checkout/Step/FinalizeStep.php
@@ -13,6 +13,7 @@ namespace Sylius\Bundle\CoreBundle\Checkout\Step;
use Sylius\Bundle\CoreBundle\Checkout\SyliusCheckoutEvents;
use Sylius\Bundle\CoreBundle\Model\OrderInterface;
+use Sylius\Bundle\CoreBundle\Model\Order;
use Sylius\Bundle\FlowBundle\Process\Context\ProcessContextInterface;
use Sylius\Bundle\SalesBundle\SyliusOrderEvents;
@@ -45,10 +46,6 @@ class FinalizeStep extends CheckoutStep
$order->setUser($this->getUser());
$this->completeOrder($order);
- $this->getCartProvider()->abandonCart();
-
- $translator = $this->get('translator');
- $this->get('session')->getFlashBag()->add('success', $translator->trans('sylius.checkout.success', array(), 'flashes'));
return $this->complete();
}
diff --git a/src/Sylius/Bundle/CoreBundle/DataFixtures/ORM/LoadPaymentMethodsData.php b/src/Sylius/Bundle/CoreBundle/DataFixtures/ORM/LoadPaymentMethodsData.php
index f3fa4a6d6e..f821c71bdc 100644
--- a/src/Sylius/Bundle/CoreBundle/DataFixtures/ORM/LoadPaymentMethodsData.php
+++ b/src/Sylius/Bundle/CoreBundle/DataFixtures/ORM/LoadPaymentMethodsData.php
@@ -25,9 +25,9 @@ class LoadPaymentMethodsData extends DataFixture
*/
public function load(ObjectManager $manager)
{
- $manager->persist($this->createPaymentMethod('Test Credit Card', 'dummy'));
- $manager->persist($this->createPaymentMethod('Stripe', 'dummy'));
- $manager->persist($this->createPaymentMethod('Disabled Payment method', 'dummy'), false);
+ $manager->persist($this->createPaymentMethod('Dummy', 'dummy'));
+ $manager->persist($this->createPaymentMethod('Paypal Express Checkout', 'paypal_express_checkout'));
+ $manager->persist($this->createPaymentMethod('Stripe', 'stripe'));
$manager->flush();
}
diff --git a/src/Sylius/Bundle/CoreBundle/spec/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenarioSpec.php b/src/Sylius/Bundle/CoreBundle/spec/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenarioSpec.php
index ba13d52f87..0d38c7272d 100644
--- a/src/Sylius/Bundle/CoreBundle/spec/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenarioSpec.php
+++ b/src/Sylius/Bundle/CoreBundle/spec/Sylius/Bundle/CoreBundle/Checkout/CheckoutProcessScenarioSpec.php
@@ -50,6 +50,7 @@ class CheckoutProcessScenarioSpec extends ObjectBehavior
$builder->add('shipping', 'sylius_checkout_shipping')->willReturn($builder)->shouldBeCalled();
$builder->add('payment', 'sylius_checkout_payment')->willReturn($builder)->shouldBeCalled();
$builder->add('finalize', 'sylius_checkout_finalize')->willReturn($builder)->shouldBeCalled();
+ $builder->add("purchase", "sylius_checkout_purchase")->willReturn($builder)->shouldBeCalled();
$builder->setDisplayRoute('sylius_checkout_display')->willReturn($builder)->shouldBeCalled();
$builder->setForwardRoute('sylius_checkout_forward')->willReturn($builder)->shouldBeCalled();
diff --git a/src/Sylius/Bundle/PaymentsBundle/Model/Payment.php b/src/Sylius/Bundle/PaymentsBundle/Model/Payment.php
index 67fd01303e..03d4e73a85 100644
--- a/src/Sylius/Bundle/PaymentsBundle/Model/Payment.php
+++ b/src/Sylius/Bundle/PaymentsBundle/Model/Payment.php
@@ -83,15 +83,21 @@ class Payment implements PaymentInterface
*/
protected $updatedAt;
+ /**
+ * @var array
+ */
+ protected $details;
+
/**
* Constructor.
*/
public function __construct()
{
$this->amount = 0;
- $this->state = PaymentInterface::STATE_PENDING;
+ $this->state = PaymentInterface::STATE_NEW;
$this->logs = new ArrayCollection();
$this->createdAt = new \DateTime('now');
+ $this->details = array();
}
/**
@@ -275,4 +281,20 @@ class Payment implements PaymentInterface
return $this;
}
+
+ /**
+ * @param array $details
+ */
+ public function setDetails(array $details)
+ {
+ $this->details = $details;
+ }
+
+ /**
+ * @return array
+ */
+ public function getDetails()
+ {
+ return $this->details;
+ }
}
diff --git a/src/Sylius/Bundle/PaymentsBundle/Model/PaymentInterface.php b/src/Sylius/Bundle/PaymentsBundle/Model/PaymentInterface.php
index 12a4c163c3..1deb36ad87 100644
--- a/src/Sylius/Bundle/PaymentsBundle/Model/PaymentInterface.php
+++ b/src/Sylius/Bundle/PaymentsBundle/Model/PaymentInterface.php
@@ -27,6 +27,8 @@ interface PaymentInterface extends TimestampableInterface
const STATE_FAILED = 'failed';
const STATE_VOID = 'void';
const STATE_COMPLETED = 'completed';
+ const STATE_NEW = 'new';
+ const STATE_UNKNOWN = 'unknown';
/**
* Get payment method associated with this payment.
@@ -127,4 +129,14 @@ interface PaymentInterface extends TimestampableInterface
* @param PaymentLogInterface $log
*/
public function removeLog(PaymentLogInterface $log);
+
+ /**
+ * @param array $details
+ */
+ public function setDetails(array $details);
+
+ /**
+ * @return array
+ */
+ public function getDetails();
}
diff --git a/src/Sylius/Bundle/PaymentsBundle/Resources/config/doctrine/model/Payment.orm.xml b/src/Sylius/Bundle/PaymentsBundle/Resources/config/doctrine/model/Payment.orm.xml
index a8a179bff1..5ac2ab103b 100644
--- a/src/Sylius/Bundle/PaymentsBundle/Resources/config/doctrine/model/Payment.orm.xml
+++ b/src/Sylius/Bundle/PaymentsBundle/Resources/config/doctrine/model/Payment.orm.xml
@@ -26,6 +26,7 @@
+
diff --git a/src/Sylius/Bundle/PaymentsBundle/spec/Sylius/Bundle/PaymentsBundle/Model/PaymentSpec.php b/src/Sylius/Bundle/PaymentsBundle/spec/Sylius/Bundle/PaymentsBundle/Model/PaymentSpec.php
index b8b3923ff6..a767b99494 100644
--- a/src/Sylius/Bundle/PaymentsBundle/spec/Sylius/Bundle/PaymentsBundle/Model/PaymentSpec.php
+++ b/src/Sylius/Bundle/PaymentsBundle/spec/Sylius/Bundle/PaymentsBundle/Model/PaymentSpec.php
@@ -94,9 +94,9 @@ class PaymentSpec extends ObjectBehavior
$this->getAmount()->shouldReturn(4999);
}
- function it_has_pending_state_by_default()
+ function it_has_new_state_by_default()
{
- $this->getState()->shouldReturn(PaymentInterface::STATE_PENDING);
+ $this->getState()->shouldReturn(PaymentInterface::STATE_NEW);
}
function its_state_is_mutable()
diff --git a/src/Sylius/Bundle/PayumBundle/.gitignore b/src/Sylius/Bundle/PayumBundle/.gitignore
new file mode 100644
index 0000000000..46aed33710
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/.gitignore
@@ -0,0 +1,5 @@
+vendor/
+bin/
+
+composer.phar
+composer.lock
diff --git a/src/Sylius/Bundle/PayumBundle/Checkout/Step/PurchaseStep.php b/src/Sylius/Bundle/PayumBundle/Checkout/Step/PurchaseStep.php
new file mode 100644
index 0000000000..46de8c44be
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Checkout/Step/PurchaseStep.php
@@ -0,0 +1,120 @@
+getCurrentCart();
+
+ $captureToken = $this->getTokenFactory()->createCaptureToken(
+ $order->getPayment()->getMethod()->getGateway(),
+ $order,
+ 'sylius_checkout_forward',
+ array('stepName' => $this->getName())
+ );
+
+ return new RedirectResponse($captureToken->getTargetUrl());
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function forwardAction(ProcessContextInterface $context)
+ {
+ $token = $this->getHttpRequestVerifier()->verify($this->getRequest());
+ $this->getHttpRequestVerifier()->invalidate($token);
+ $this->getCartProvider()->abandonCart();
+
+ $payment = $this->getPayum()->getPayment($token->getPaymentName());
+
+ $status = new StatusRequest($token);
+ $payment->execute($status);
+
+ /** @var OrderInterface $order */
+ $order = $status->getModel();
+
+ if (!$order instanceof OrderInterface) {
+ throw new \RuntimeException(sprintf('Expected order to be set as model but it is %s', get_class($order)));
+ }
+
+ $order->getPayment()->setState($status->getStatus());
+
+ if ($status->isSuccess()) {
+ $type = 'success';
+ $msg = 'sylius.checkout.success';
+ } elseif ($status->isPending()) {
+ $type = 'notice';
+ $msg = 'sylius.checkout.pending';
+ } elseif ($status->isCanceled()) {
+ $type = 'notice';
+ $msg = 'sylius.checkout.canceled';
+ } elseif ($status->isExpired()) {
+ $type = 'notice';
+ $msg = 'sylius.checkout.expired';
+ } elseif ($status->isSuspended()) {
+ $type = 'notice';
+ $msg = 'sylius.checkout.suspended';
+ } elseif ($status->isFailed()) {
+ $type = 'error';
+ $msg = 'sylius.checkout.failed';
+ } else {
+ $type = 'error';
+ $msg = 'sylius.checkout.unknown';
+ }
+
+ //TODO: an event here
+
+ $this->getDoctrine()->getManager()->flush();
+
+ $this->get('session')->getFlashBag()->add($type, $this->get('translator')->trans($msg, array(), 'flashes'));
+
+ return $this->complete();
+ }
+
+ /**
+ * @return RegistryInterface
+ */
+ protected function getPayum()
+ {
+ return $this->get('payum');
+ }
+
+ /**
+ * @return TokenFactory
+ */
+ protected function getTokenFactory()
+ {
+ return $this->get('payum.security.token_factory');
+ }
+
+ /**
+ * @return HttpRequestVerifierInterface
+ */
+ protected function getHttpRequestVerifier()
+ {
+ return $this->get('payum.security.http_request_verifier');
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/DependencyInjection/Configuration.php b/src/Sylius/Bundle/PayumBundle/DependencyInjection/Configuration.php
new file mode 100644
index 0000000000..5e103aa3b9
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/DependencyInjection/Configuration.php
@@ -0,0 +1,60 @@
+root('sylius_payum');
+
+ $rootNode
+ ->addDefaultsIfNotSet()
+ ->children()
+ ->scalarNode('driver')->cannotBeOverwritten()->isRequired()->cannotBeEmpty()->end()
+ ->end()
+ ;
+
+ $this->addClassesSection($rootNode);
+
+ return $treeBuilder;
+ }
+
+ /**
+ * Adds `classes` section.
+ *
+ * @param ArrayNodeDefinition $node
+ */
+ private function addClassesSection(ArrayNodeDefinition $node)
+ {
+ $node
+ ->children()
+ ->arrayNode('classes')
+ ->addDefaultsIfNotSet()
+ ->children()
+ ->arrayNode('payment_security_token')
+ ->addDefaultsIfNotSet()
+ ->children()
+ ->scalarNode('model')->defaultValue('Sylius\\Bundle\\PayumBundle\\Model\\PaymentSecurityToken')->end()
+ ->end()
+ ->end()
+ ->end()
+ ->end()
+ ->end()
+ ;
+ }
+}
diff --git a/src/Sylius/Bundle/PayumBundle/DependencyInjection/SyliusPayumExtension.php b/src/Sylius/Bundle/PayumBundle/DependencyInjection/SyliusPayumExtension.php
new file mode 100644
index 0000000000..e5437c9c63
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/DependencyInjection/SyliusPayumExtension.php
@@ -0,0 +1,73 @@
+processConfiguration($configuration, $config);
+ $loader = new XmlFileLoader($container, new FileLocator(__DIR__.'/../Resources/config'));
+
+ $driver = $config['driver'];
+
+ if (!in_array($driver, SyliusPayumBundle::getSupportedDrivers())) {
+ throw new \InvalidArgumentException(sprintf('Driver "%s" is unsupported for SyliusPayumBundle', $driver));
+ }
+
+ $loader->load(sprintf('driver/%s.xml', $driver));
+
+ $container->setParameter('sylius_payum.driver', $driver);
+ $container->setParameter('sylius_payum.driver.'.$driver, true);
+
+ $loader->load('services.xml');
+
+ $classes = $config['classes'];
+
+ $this->mapClassParameters($classes, $container);
+
+ if ($container->hasParameter('sylius.config.classes')) {
+ $classes = array_merge($classes, $container->getParameter('sylius.config.classes'));
+ }
+
+ $container->setParameter('sylius.config.classes', $classes);
+ }
+
+ /**
+ * Remap class parameters.
+ *
+ * @param array $classes
+ * @param ContainerBuilder $container
+ */
+ protected function mapClassParameters(array $classes, ContainerBuilder $container)
+ {
+ foreach ($classes as $model => $serviceClasses) {
+ foreach ($serviceClasses as $service => $class) {
+ $service = $service === 'form' ? 'form.type' : $service;
+ $container->setParameter(sprintf('sylius.%s.%s.class', $service, $model), $class);
+ }
+ }
+ }
+}
diff --git a/src/Sylius/Bundle/PayumBundle/Model/PaymentSecurityToken.php b/src/Sylius/Bundle/PayumBundle/Model/PaymentSecurityToken.php
new file mode 100644
index 0000000000..6079b7aedb
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Model/PaymentSecurityToken.php
@@ -0,0 +1,18 @@
+supports($request)) {
+ throw RequestNotSupportedException::createActionNotSupported($this, $request);
+ }
+
+ /** @var OrderInterface $order */
+ $order = $request->getModel();
+
+ $paymentDetails = $order->getPayment()->getDetails();
+ if (empty($paymentDetails)) {
+ $order->getPayment()->setDetails(array(
+ 'captured' => true,
+ ));
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function supports($request)
+ {
+ return
+ $request instanceof CaptureRequest &&
+ $request->getModel() instanceof OrderInterface
+ ;
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Payum/Action/CaptureOrderWithPaypalAction.php b/src/Sylius/Bundle/PayumBundle/Payum/Action/CaptureOrderWithPaypalAction.php
new file mode 100644
index 0000000000..f0343d0b08
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Payum/Action/CaptureOrderWithPaypalAction.php
@@ -0,0 +1,81 @@
+supports($request)) {
+ throw RequestNotSupportedException::createActionNotSupported($this, $request);
+ }
+
+ /** @var OrderInterface $order */
+ $order = $request->getModel();
+
+ $paymentDetails = $order->getPayment()->getDetails();
+ if (empty($paymentDetails)) {
+ $paymentDetails['RETURNURL'] = $request->getToken()->getTargetUrl();
+ $paymentDetails['CANCELURL'] = $request->getToken()->getTargetUrl();
+ $paymentDetails['INVNUM'] = $order->getNumber();
+
+ $paymentDetails['PAYMENTREQUEST_0_CURRENCYCODE'] = $order->getCurrency();
+ $paymentDetails['PAYMENTREQUEST_0_AMT'] = number_format(($order->getTotal() + $order->getShippingTotal()) / 100, 2);
+ $paymentDetails['PAYMENTREQUEST_0_ITEMAMT'] = number_format($order->getItemsTotal() / 100, 2);
+ $paymentDetails['PAYMENTREQUEST_0_TAXAMT'] = number_format($order->getTaxTotal() / 100, 2);
+ $paymentDetails['PAYMENTREQUEST_0_SHIPPINGAMT'] = number_format($order->getShippingTotal() / 100, 2);
+
+ $m = 0;
+ foreach ($order->getItems() as $item) {
+ $paymentDetails['L_PAYMENTREQUEST_0_AMT'.$m] = number_format($item->getTotal() / 100, 2);
+ $paymentDetails['L_PAYMENTREQUEST_0_QTY'.$m] = $item->getQuantity();
+
+ $m++;
+ }
+ }
+
+ // TODO: find a way to simply the next logic
+
+ $paymentDetails = ArrayObject::ensureArrayObject($paymentDetails);
+
+ try {
+ $this->payment->execute(new CaptureRequest($paymentDetails));
+ $order->getPayment()->setDetails((array) $paymentDetails);
+ } catch (\Exception $e) {
+ $order->getPayment()->setDetails((array) $paymentDetails);
+
+ throw $e;
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function supports($request)
+ {
+ return
+ $request instanceof SecuredCaptureRequest &&
+ $request->getModel() instanceof OrderInterface
+ ;
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Payum/Action/CaptureOrderWithStripeAction.php b/src/Sylius/Bundle/PayumBundle/Payum/Action/CaptureOrderWithStripeAction.php
new file mode 100644
index 0000000000..104e465183
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Payum/Action/CaptureOrderWithStripeAction.php
@@ -0,0 +1,80 @@
+supports($request)) {
+ throw RequestNotSupportedException::createActionNotSupported($this, $request);
+ }
+
+ /** @var OrderInterface $order */
+ $order = $request->getModel();
+
+ $paymentDetails = $order->getPayment()->getDetails();
+ if (empty($paymentDetails)) {
+ $this->payment->execute($obtainCreditCardRequest = new ObtainCreditCardRequest($order));
+
+ $paymentDetails = array(
+ 'card' => array(
+ 'number' => $obtainCreditCardRequest->getCreditCard()->getNumber(),
+ 'expiryMonth' => $obtainCreditCardRequest->getCreditCard()->getExpiryMonth(),
+ 'expiryYear' => $obtainCreditCardRequest->getCreditCard()->getExpiryYear(),
+ 'cvv' => $obtainCreditCardRequest->getCreditCard()->getSecurityCode()
+ ),
+ 'amount' => number_format($order->getTotal() / 100, 2),
+ 'currency' => $order->getCurrency(),
+ );
+ }
+
+ // TODO: find a way to simply the next logic
+
+ $paymentDetails = ArrayObject::ensureArrayObject($paymentDetails);
+
+ try {
+ $this->payment->execute(new CaptureRequest($paymentDetails));
+
+ unset($paymentDetails['card']);
+ $order->getPayment()->setDetails((array) $paymentDetails);
+ } catch (\Exception $e) {
+ unset($paymentDetails['card']);
+ $order->getPayment()->setDetails((array) $paymentDetails);
+
+ throw $e;
+ }
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function supports($request)
+ {
+ return
+ $request instanceof SecuredCaptureRequest &&
+ $request->getModel() instanceof OrderInterface
+ ;
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Payum/Action/DummyOrderStatusAction.php b/src/Sylius/Bundle/PayumBundle/Payum/Action/DummyOrderStatusAction.php
new file mode 100644
index 0000000000..75a51d5ea9
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Payum/Action/DummyOrderStatusAction.php
@@ -0,0 +1,60 @@
+supports($request)) {
+ throw RequestNotSupportedException::createActionNotSupported($this, $request);
+ }
+
+ /** @var Order $order */
+ $order = $request->getModel();
+
+ $paymentDetails = $order->getPayment()->getDetails();
+ if (empty($paymentDetails)) {
+ $request->markNew();
+
+ return;
+ }
+
+ if (isset($paymentDetails['captured'])) {
+ $request->markSuccess();
+
+ return;
+ }
+
+ $request->markUnknown();
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function supports($request)
+ {
+ return
+ $request instanceof StatusRequestInterface &&
+ $request->getModel() instanceof Order
+ ;
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Payum/Action/ObtainCreditCardAction.php b/src/Sylius/Bundle/PayumBundle/Payum/Action/ObtainCreditCardAction.php
new file mode 100644
index 0000000000..e08e66cb57
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Payum/Action/ObtainCreditCardAction.php
@@ -0,0 +1,102 @@
+formFactory = $formFactory;
+ $this->templating = $templating;
+ }
+
+ /**
+ * @param Request $request
+ */
+ public function setRequest(Request $request = null)
+ {
+ $this->httpRequest = $request;
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function execute($request)
+ {
+ /** @var $request ObtainCreditCardRequest */
+ if (!$this->supports($request)) {
+ throw RequestNotSupportedException::createActionNotSupported($this, $request);
+ }
+ if (!$this->httpRequest) {
+ throw new LogicException('The action can be run only when http request is set.');
+ }
+
+ $form = $this->createCreditCardForm();
+ $form->handleRequest($this->httpRequest);
+ if ($form->isValid()) {
+ $request->setCreditCard($form->getData());
+
+ return;
+ }
+
+ throw new ResponseInteractiveRequest(new Response(
+ $this->templating->render('SyliusPayumBundle::Payum\Action\obtainCreditCard.html.twig', array(
+ 'form' => $form->createView()
+ ))
+ ));
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function supports($request)
+ {
+ return $request instanceof ObtainCreditCardRequest;
+ }
+
+ /**
+ * @return \Symfony\Component\Form\Form
+ */
+ protected function createCreditCardForm()
+ {
+ return $this->formFactory->create('sylius_credit_card');
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Payum/Action/OrderStatusAction.php b/src/Sylius/Bundle/PayumBundle/Payum/Action/OrderStatusAction.php
new file mode 100644
index 0000000000..02c518e824
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Payum/Action/OrderStatusAction.php
@@ -0,0 +1,55 @@
+supports($request)) {
+ throw RequestNotSupportedException::createActionNotSupported($this, $request);
+ }
+
+ /** @var OrderInterface $order */
+ $order = $request->getModel();
+
+ if ($order->getPayment()->getDetails()) {
+ $request->setModel($order->getPayment()->getDetails());
+
+ $this->payment->execute($request);
+
+ $request->setModel($order);
+ } else {
+ $request->markNew();
+ }
+ }
+
+ /**
+ * {@inheritDoc}
+ */
+ public function supports($request)
+ {
+ return
+ $request instanceof StatusRequestInterface &&
+ $request->getModel() instanceof OrderInterface
+ ;
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Payum/Request/ObtainCreditCardRequest.php b/src/Sylius/Bundle/PayumBundle/Payum/Request/ObtainCreditCardRequest.php
new file mode 100644
index 0000000000..a5e0ab9a6e
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Payum/Request/ObtainCreditCardRequest.php
@@ -0,0 +1,60 @@
+order = $order;
+ }
+
+ /**
+ * @return OrderInterface
+ */
+ public function getOrder()
+ {
+ return $this->order;
+ }
+
+ /**
+ * @param CreditCardInterface $creditCard
+ */
+ public function setCreditCard(CreditCardInterface $creditCard)
+ {
+ $this->creditCard = $creditCard;
+ }
+
+ /**
+ * @return CreditCardInterface
+ */
+ public function getCreditCard()
+ {
+ return $this->creditCard;
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Payum/Request/StatusRequest.php b/src/Sylius/Bundle/PayumBundle/Payum/Request/StatusRequest.php
new file mode 100644
index 0000000000..d822638759
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Payum/Request/StatusRequest.php
@@ -0,0 +1,146 @@
+status = PaymentInterface::STATE_NEW;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isNew()
+ {
+ return $this->status === PaymentInterface::STATE_NEW;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function markSuccess()
+ {
+ $this->status = PaymentInterface::STATE_COMPLETED;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isSuccess()
+ {
+ return $this->status === PaymentInterface::STATE_COMPLETED;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function markSuspended()
+ {
+ $this->status = PaymentInterface::STATE_VOID;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isSuspended()
+ {
+ return $this->status === PaymentInterface::STATE_VOID;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function markExpired()
+ {
+ $this->status = PaymentInterface::STATE_FAILED;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isExpired()
+ {
+ return $this->status === PaymentInterface::STATE_FAILED;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function markCanceled()
+ {
+ $this->status = PaymentInterface::STATE_VOID;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isCanceled()
+ {
+ return $this->status === PaymentInterface::STATE_VOID;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function markPending()
+ {
+ $this->status = PaymentInterface::STATE_PENDING;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isPending()
+ {
+ return $this->status === PaymentInterface::STATE_PENDING;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function markFailed()
+ {
+ $this->status = PaymentInterface::STATE_FAILED;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isFailed()
+ {
+ return $this->status === PaymentInterface::STATE_FAILED;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function markUnknown()
+ {
+ $this->status = PaymentInterface::STATE_UNKNOWN;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function isUnknown()
+ {
+ return $this->status === PaymentInterface::STATE_UNKNOWN;
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/README.md b/src/Sylius/Bundle/PayumBundle/README.md
new file mode 100644
index 0000000000..4e4459eb0d
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/README.md
@@ -0,0 +1,4 @@
+SyliusPayumBundle
+=================
+
+Provide payum integration for sylius.
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Resources/config/doctrine/model/PaymentSecurityToken.orm.xml b/src/Sylius/Bundle/PayumBundle/Resources/config/doctrine/model/PaymentSecurityToken.orm.xml
new file mode 100644
index 0000000000..536d30c67b
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Resources/config/doctrine/model/PaymentSecurityToken.orm.xml
@@ -0,0 +1,20 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/Resources/config/driver/doctrine/orm.xml b/src/Sylius/Bundle/PayumBundle/Resources/config/driver/doctrine/orm.xml
new file mode 100644
index 0000000000..5bea6f9aea
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Resources/config/driver/doctrine/orm.xml
@@ -0,0 +1,39 @@
+
+
+
+
+
+
+
+ Sylius\Bundle\ResourceBundle\Doctrine\ORM\EntityRepository
+
+
+
+
+
+
+
+
+ %sylius.model.payment_security_token.class%
+
+
+
+
+
+
diff --git a/src/Sylius/Bundle/PayumBundle/Resources/config/services.xml b/src/Sylius/Bundle/PayumBundle/Resources/config/services.xml
new file mode 100644
index 0000000000..421f202eba
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Resources/config/services.xml
@@ -0,0 +1,52 @@
+
+
+
+
+
+
+
+ Sylius\Bundle\PayumBundle\Checkout\Step\PurchaseStep
+ Sylius\Bundle\PayumBundle\Payum\Action\CaptureOrderWithPaypalAction
+ Sylius\Bundle\PayumBundle\Payum\Action\CaptureOrderWithDummyAction
+ Sylius\Bundle\PayumBundle\Payum\Action\CaptureOrderWithStripeAction
+ Sylius\Bundle\PayumBundle\Payum\Action\OrderStatusAction
+ Sylius\Bundle\PayumBundle\Payum\Action\DummyOrderStatusAction
+ Sylius\Bundle\PayumBundle\Payum\Action\ObtainCreditCardAction
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/src/Sylius/Bundle/PayumBundle/Resources/meta/LICENSE b/src/Sylius/Bundle/PayumBundle/Resources/meta/LICENSE
new file mode 100644
index 0000000000..653d37087d
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Resources/meta/LICENSE
@@ -0,0 +1,19 @@
+Copyright (c) 2011-2013 Paweł Jędrzejewski
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is furnished
+to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in all
+copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
diff --git a/src/Sylius/Bundle/PayumBundle/Resources/views/Payum/Action/obtainCreditCard.html.twig b/src/Sylius/Bundle/PayumBundle/Resources/views/Payum/Action/obtainCreditCard.html.twig
new file mode 100644
index 0000000000..1e55f6c0f5
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/Resources/views/Payum/Action/obtainCreditCard.html.twig
@@ -0,0 +1,24 @@
+{% extends 'SyliusWebBundle:Frontend:layout.html.twig' %}
+
+{% block content %}
+
+
+
+{% endblock %}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/SyliusPayumBundle.php b/src/Sylius/Bundle/PayumBundle/SyliusPayumBundle.php
new file mode 100644
index 0000000000..287e62862a
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/SyliusPayumBundle.php
@@ -0,0 +1,51 @@
+ 'sylius.model.payment_security_token.class',
+ );
+
+ $container->addCompilerPass(new ResolveDoctrineTargetEntitiesPass('sylius_payum', $interfaces));
+
+ $mappings = array(
+ realpath(__DIR__ . '/Resources/config/doctrine/model') => 'Sylius\Bundle\PayumBundle\Model',
+ );
+
+ $container->addCompilerPass(DoctrineOrmMappingsPass::createXmlMappingDriver($mappings, array('doctrine.orm.entity_manager'), 'sylius_payum.driver.doctrine/orm'));
+ }
+}
diff --git a/src/Sylius/Bundle/PayumBundle/composer.json b/src/Sylius/Bundle/PayumBundle/composer.json
new file mode 100644
index 0000000000..1785cff00e
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/composer.json
@@ -0,0 +1,40 @@
+{
+ "name": "sylius/payum-bundle",
+ "type": "symfony-bundle",
+ "description": "Payum integration for Symfony2 e-commerce applications.",
+ "keywords": ["payments", "payment", "payum"],
+ "homepage": "http://sylius.com",
+ "license": "MIT",
+ "authors": [
+ {
+ "name": "Kotlyar Maksim",
+ "email": "kotlyar.maksim@gmail.com",
+ },
+ {
+ "name": "Community contributions",
+ "homepage": "https://github.com/Sylius/SyliusPaymentsBundle/contributors"
+ }
+ ],
+ "require": {
+ "php": ">=5.3.3",
+
+ "sylius/sales-bundle": "1.0.*@dev",
+ "sylius/core-bundle": "1.0.*@dev",
+ "sylius/payments-bundle": "1.0.*@dev",
+ "sylius/resource-bundle": "1.0.*@dev",
+ "payum/payum-bundle": "0.6.*@dev",
+ "payum/payum": "0.6.*@dev"
+ },
+ "config": {
+ "bin-dir": "bin"
+ },
+ "autoload": {
+ "psr-0": { "Sylius\\Bundle\\PayumBundle": "" }
+ },
+ "target-dir": "Sylius/Bundle/PayumBundle",
+ "extra": {
+ "branch-alias": {
+ "dev-master": "1.0-dev"
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Model/PaymentSecurityTokenSpec.php b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Model/PaymentSecurityTokenSpec.php
new file mode 100644
index 0000000000..3b63fdfbc7
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Model/PaymentSecurityTokenSpec.php
@@ -0,0 +1,19 @@
+shouldHaveType('Sylius\Bundle\PayumBundle\Model\PaymentSecurityToken');
+ }
+
+ function it_extends_payum_token()
+ {
+ $this->shouldHaveType('Payum\Model\Token');
+ }
+}
diff --git a/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Action/OrderStatusActionSpec.php b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Action/OrderStatusActionSpec.php
new file mode 100644
index 0000000000..050f8ab40a
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Action/OrderStatusActionSpec.php
@@ -0,0 +1,103 @@
+shouldHaveType('Sylius\Bundle\PayumBundle\Payum\Action\OrderStatusAction');
+ }
+
+ function it_extends_payum_payment_aware_action()
+ {
+ $this->shouldHaveType('Payum\Action\PaymentAwareAction');
+ }
+
+ /**
+ * @param Sylius\Bundle\CoreBundle\Model\OrderInterface $order
+ * @param Payum\Request\StatusRequestInterface $statusRequest
+ */
+ function it_should_support_status_request_with_order_model($order, $statusRequest)
+ {
+ $statusRequest->getModel()->willReturn($order);
+
+ $this->supports($statusRequest)->shouldReturn(true);
+ }
+
+ /**
+ * @param Payum\Request\StatusRequestInterface $statusRequest
+ */
+ function it_should_not_support_status_request_with_no_order_model($statusRequest)
+ {
+ $statusRequest->getModel()->willReturn('foo');
+
+ $this->supports($statusRequest)->shouldReturn(false);
+ }
+
+ function it_should_not_support_any_no_status_requests()
+ {
+ $this->supports('foo')->shouldReturn(false);
+ }
+
+ function it_throws_exception_if_executing_not_supported_request()
+ {
+ $notSupportedRequest = 'foo';
+
+ $this
+ ->shouldThrow('Payum\Exception\RequestNotSupportedException')
+ ->duringExecute($notSupportedRequest)
+ ;
+ }
+
+ /**
+ * @param Sylius\Bundle\CoreBundle\Model\OrderInterface $order
+ * @param Sylius\Bundle\PaymentsBundle\Model\PaymentInterface $payment
+ * @param Payum\Request\StatusRequestInterface $statusRequest
+ */
+ function it_should_mark_new_if_order_have_empty_payment_details($order, $payment, $statusRequest)
+ {
+ $statusRequest->getModel()->willReturn($order);
+ $statusRequest->markNew()->shouldBeCalled();
+
+ $order->getPayment()->willReturn($payment);
+ $payment->getDetails()->willReturn(array());
+
+ $this->execute($statusRequest);
+ }
+
+ /**
+ * @param Sylius\Bundle\CoreBundle\Model\OrderInterface $order
+ * @param Sylius\Bundle\PaymentsBundle\Model\PaymentInterface $payment
+ * @param Payum\Request\StatusRequestInterface $statusRequest
+ * @param Payum\PaymentInterface $payment
+ */
+ function it_should_do_status_subrequest_with_payment_details_as_model($order, $payment, $statusRequest, $payment)
+ {
+ $details = array('foo' => 'foo', 'bar' => 'baz');
+
+ $statusRequest->getModel()->willReturn($order);
+ $statusRequest->setModel($details)->shouldBeCalled();
+ $statusRequest->setModel($order)->shouldBeCalled();
+
+ $payment->execute($statusRequest)->shouldBeCalled();
+
+ $order->getPayment()->willReturn($payment);
+ $payment->getDetails()->willReturn($details);
+
+ $this->setPayment($payment);
+ $this->execute($statusRequest);
+ }
+}
diff --git a/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Request/ObtainCreditCardRequestSpec.php b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Request/ObtainCreditCardRequestSpec.php
new file mode 100644
index 0000000000..f291dcc2f3
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Request/ObtainCreditCardRequestSpec.php
@@ -0,0 +1,48 @@
+beConstructedWith($order);
+ }
+
+ function it_is_initializable()
+ {
+ $this->shouldHaveType('Sylius\Bundle\PayumBundle\Payum\Request\ObtainCreditCardRequest');
+ }
+
+ /**
+ * @param Sylius\Bundle\CoreBundle\Model\OrderInterface $order
+ */
+ function it_should_allow_get_order_set_in_constructor($order)
+ {
+ $this->getOrder()->shouldReturn($order);
+ }
+
+ /**
+ * @param Sylius\Bundle\PaymentsBundle\Model\CreditCardInterface $creditCard
+ */
+ function it_should_allow_get_credit_card_set_before($creditCard)
+ {
+ $this->setCreditCard($creditCard);
+
+ $this->getCreditCard()->shouldReturn($creditCard);
+ }
+}
\ No newline at end of file
diff --git a/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Request/StatusRequestSpec.php b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Request/StatusRequestSpec.php
new file mode 100644
index 0000000000..7b5984030a
--- /dev/null
+++ b/src/Sylius/Bundle/PayumBundle/spec/Sylius/Bundle/PayumBundle/Payum/Request/StatusRequestSpec.php
@@ -0,0 +1,146 @@
+beConstructedWith(new \stdClass);
+ }
+
+ function it_is_initializable()
+ {
+ $this->shouldHaveType('Sylius\Bundle\PayumBundle\Payum\Request\StatusRequest');
+ }
+
+ function it_extends_base_status_class()
+ {
+ $this->shouldHaveType('Payum\Request\BaseStatusRequest');
+ }
+
+ function it_is_new_when_marked_as_new()
+ {
+ $this->markNew();
+
+ $this->isNew()->shouldReturn(true);
+ }
+
+ function it_is_return_new_status_when_marked_as_new()
+ {
+ $this->markNew();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_NEW);
+ }
+
+ function it_is_success_when_marked_as_success()
+ {
+ $this->markSuccess();
+
+ $this->isSuccess()->shouldReturn(true);
+ }
+
+ function it_is_return_completed_status_when_marked_as_success()
+ {
+ $this->markSuccess();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_COMPLETED);
+ }
+
+ function it_is_pending_when_marked_as_pending()
+ {
+ $this->markPending();
+
+ $this->isPending()->shouldReturn(true);
+ }
+
+ function it_is_return_pending_status_when_marked_as_pending()
+ {
+ $this->markPending();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_PENDING);
+ }
+
+ function it_is_failed_when_marked_as_failed()
+ {
+ $this->markFailed();
+
+ $this->isFailed()->shouldReturn(true);
+ }
+
+ function it_is_return_failed_status_when_marked_as_failed()
+ {
+ $this->markFailed();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_FAILED);
+ }
+
+ function it_is_canceled_when_marked_as_canceled()
+ {
+ $this->markCanceled();
+
+ $this->isCanceled()->shouldReturn(true);
+ }
+
+ function it_is_return_void_status_when_marked_as_canceled()
+ {
+ $this->markCanceled();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_VOID);
+ }
+
+ function it_is_suspended_when_marked_as_suspended()
+ {
+ $this->markSuspended();
+
+ $this->isSuspended()->shouldReturn(true);
+ }
+
+ function it_is_return_void_status_when_marked_as_suspended()
+ {
+ $this->markSuspended();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_VOID);
+ }
+
+ function it_is_expired_when_marked_as_expired()
+ {
+ $this->markExpired();
+
+ $this->isExpired()->shouldReturn(true);
+ }
+
+ function it_is_return_failed_status_when_marked_as_expired()
+ {
+ $this->markExpired();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_FAILED);
+ }
+
+ function it_is_unknown_when_marked_as_unknown()
+ {
+ $this->markUnknown();
+
+ $this->isUnknown()->shouldReturn(true);
+ }
+
+ function it_is_return_unknown_status_when_marked_as_unknown()
+ {
+ $this->markUnknown();
+
+ $this->getStatus()->shouldReturn(PaymentInterface::STATE_UNKNOWN);
+ }
+}
\ No newline at end of file