From a2e84383731822d6e42a0fbb774787886eac508d Mon Sep 17 00:00:00 2001
From: Michael Furtner
Date: Wed, 25 Jan 2017 17:48:59 +0100
Subject: [PATCH] Initial commit
---
README.md | 49 +
.../Adminhtml/Customer/Edit/Tab/Alias.php | 172 +
.../Customer/Renderer/PaymentMethod.php | 27 +
.../Adminhtml/Customer/Renderer/State.php | 21 +
.../Block/Adminhtml/Kwixo/Shipping/Edit.php | 86 +
.../Adminhtml/Kwixocategory/CategoryTree.php | 106 +
.../Block/Adminhtml/Kwixocategory/Edit.php | 58 +
.../Adminhtml/Kwixocategory/Edit/Form.php | 75 +
.../Creditmemo/ClosedTransaction/Warning.php | 33 +
.../Order/Creditmemo/Totals/Checkbox.php | 33 +
.../Netresearch/OPS/Block/Alias/List.php | 69 +
.../Block/Checkout/DeviceFingerprinting.php | 79 +
.../OPS/Block/Checkout/SubscriptionNotice.php | 202 +
.../community/Netresearch/OPS/Block/Form.php | 363 ++
.../Netresearch/OPS/Block/Form/Alias.php | 55 +
.../OPS/Block/Form/BankTransfer.php | 42 +
.../Netresearch/OPS/Block/Form/Cc.php | 178 +
.../OPS/Block/Form/DirectDebit.php | 47 +
.../OPS/Block/Form/DirectEbanking.php | 42 +
.../Netresearch/OPS/Block/Form/Flex.php | 70 +
.../Netresearch/OPS/Block/Form/Ideal.php | 33 +
.../Netresearch/OPS/Block/Form/InterSolve.php | 52 +
.../OPS/Block/Form/Kwixo/ApresReception.php | 27 +
.../OPS/Block/Form/Kwixo/Comptant.php | 30 +
.../OPS/Block/Form/Kwixo/Credit.php | 28 +
.../OPS/Block/Form/OpenInvoice.php | 63 +
.../Netresearch/OPS/Block/Form/OpsId.php | 17 +
.../Netresearch/OPS/Block/Form/PayPerMail.php | 43 +
.../OPS/Block/Form/RecurringCc.php | 37 +
.../Netresearch/OPS/Block/Frauddetection.php | 74 +
.../Netresearch/OPS/Block/Info/Alias.php | 32 +
.../Netresearch/OPS/Block/Info/Bancontact.php | 54 +
.../Netresearch/OPS/Block/Info/Cc.php | 43 +
.../Netresearch/OPS/Block/Info/Flex.php | 55 +
.../Netresearch/OPS/Block/Info/OpsId.php | 43 +
.../Netresearch/OPS/Block/Info/PayPerMail.php | 44 +
.../OPS/Block/Info/RecurringCc.php | 35 +
.../Netresearch/OPS/Block/Info/Redirect.php | 42 +
.../Netresearch/OPS/Block/Paypage.php | 41 +
.../Netresearch/OPS/Block/Placeform.php | 191 +
.../OPS/Block/Placeform3dsecure.php | 42 +
.../Netresearch/OPS/Block/RetryPayment.php | 103 +
.../OPS/Block/RetryPayment/Methods.php | 80 +
.../Block/System/Config/Form/Field/Brand.php | 53 +
.../Block/System/Config/Form/Field/Image.php | 87 +
.../Block/System/Config/Form/Field/Method.php | 59 +
.../Config/Form/Field/RecurringActive.php | 55 +
.../System/Config/Kwixoconfiguration.php | 35 +
.../OPS/Block/System/Config/Mode.php | 32 +
.../OPS/Block/System/Config/PaymentForm.php | 47 +
.../OPS/Block/System/Config/Support.php | 170 +
.../Netresearch/OPS/Controller/Abstract.php | 181 +
.../Netresearch/OPS/Helper/Address.php | 181 +
.../Netresearch/OPS/Helper/Alias.php | 514 +++
.../community/Netresearch/OPS/Helper/Api.php | 126 +
.../Netresearch/OPS/Helper/Creditcard.php | 79 +
.../community/Netresearch/OPS/Helper/Data.php | 193 +
.../Netresearch/OPS/Helper/Debitcard.php | 21 +
.../Netresearch/OPS/Helper/DirectDebit.php | 150 +
.../Netresearch/OPS/Helper/Directlink.php | 262 ++
.../Netresearch/OPS/Helper/Kwixo.php | 165 +
.../Netresearch/OPS/Helper/MobileDetect.php | 68 +
.../Netresearch/OPS/Helper/Order.php | 170 +
.../Netresearch/OPS/Helper/Order/Abstract.php | 84 +
.../Netresearch/OPS/Helper/Order/Capture.php | 79 +
.../Netresearch/OPS/Helper/Order/Refund.php | 142 +
.../Netresearch/OPS/Helper/Payment.php | 969 +++++
.../OPS/Helper/Payment/DirectLink/Request.php | 333 ++
.../Payment/DirectLink/RequestInterface.php | 115 +
.../OPS/Helper/Payment/Request.php | 738 ++++
.../Netresearch/OPS/Helper/Quote.php | 164 +
.../Netresearch/OPS/Helper/Subscription.php | 148 +
.../OPS/Helper/Validation/Checkout/Step.php | 98 +
.../OPS/Helper/Validation/Result.php | 210 +
.../Netresearch/OPS/Helper/Version.php | 66 +
.../community/Netresearch/OPS/Model/Alias.php | 70 +
.../Netresearch/OPS/Model/Alias/State.php | 34 +
.../Netresearch/OPS/Model/Api/Directlink.php | 218 +
.../Capture/Additional/OpenInvoiceNl.php | 15 +
.../Backend/Operation/Capture/Parameter.php | 51 +
.../OPS/Model/Backend/Operation/Parameter.php | 69 +
.../Backend/Operation/Parameter/Abstract.php | 133 +
.../Parameter/Additional/Interface.php | 11 +
.../Additional/OpenInvoiceNlAbstract.php | 151 +
.../Backend/Operation/Parameter/Interface.php | 17 +
.../Refund/Additional/OpenInvoiceNl.php | 138 +
.../Backend/Operation/Refund/Parameter.php | 70 +
.../Netresearch/OPS/Model/Config.php | 976 +++++
.../Netresearch/OPS/Model/Eci/Values.php | 35 +
.../Netresearch/OPS/Model/File/Download.php | 61 +
.../OPS/Model/Kwixo/Category/Mapping.php | 57 +
.../OPS/Model/Kwixo/Shipping/Setting.php | 24 +
.../Netresearch/OPS/Model/Mysql4/Alias.php | 33 +
.../OPS/Model/Mysql4/Alias/Collection.php | 29 +
.../Model/Mysql4/Kwixo/Category/Mapping.php | 32 +
.../Kwixo/Category/Mapping/Collection.php | 28 +
.../Model/Mysql4/Kwixo/Shipping/Setting.php | 20 +
.../Kwixo/Shipping/Setting/Collection.php | 21 +
.../Netresearch/OPS/Model/Observer.php | 725 ++++
.../OPS/Model/Payment/Abstract.php | 1127 ++++++
.../OPS/Model/Payment/Backend/OpsId.php | 36 +
.../OPS/Model/Payment/Bancontact.php | 102 +
.../OPS/Model/Payment/BankTransfer.php | 49 +
.../OPS/Model/Payment/BelfiusDirectNet.php | 25 +
.../Netresearch/OPS/Model/Payment/CashU.php | 25 +
.../OPS/Model/Payment/CbcOnline.php | 25 +
.../Netresearch/OPS/Model/Payment/Cc.php | 302 ++
.../OPS/Model/Payment/ChinaUnionPay.php | 58 +
.../OPS/Model/Payment/Debitcard.php | 54 +
.../OPS/Model/Payment/DirectDebit.php | 61 +
.../OPS/Model/Payment/DirectEbanking.php | 67 +
.../OPS/Model/Payment/DirectLink.php | 350 ++
.../OPS/Model/Payment/EDankort.php | 26 +
.../Netresearch/OPS/Model/Payment/Eps.php | 24 +
.../Model/Payment/Features/PaymentEmail.php | 198 +
.../Model/Payment/Features/ZeroAmountAuth.php | 41 +
.../Netresearch/OPS/Model/Payment/Flex.php | 41 +
.../OPS/Model/Payment/FortisPayButton.php | 25 +
.../Netresearch/OPS/Model/Payment/GiroPay.php | 26 +
.../Netresearch/OPS/Model/Payment/IDeal.php | 78 +
.../OPS/Model/Payment/IngHomePay.php | 26 +
.../OPS/Model/Payment/InterSolve.php | 51 +
.../OPS/Model/Payment/KbcOnline.php | 26 +
.../OPS/Model/Payment/Kwixo/Abstract.php | 551 +++
.../OPS/Model/Payment/KwixoApresReception.php | 25 +
.../OPS/Model/Payment/KwixoComptant.php | 26 +
.../OPS/Model/Payment/KwixoCredit.php | 27 +
.../OPS/Model/Payment/Masterpass.php | 27 +
.../Model/Payment/OpenInvoice/Abstract.php | 104 +
.../OPS/Model/Payment/OpenInvoiceAt.php | 107 +
.../OPS/Model/Payment/OpenInvoiceDe.php | 95 +
.../OPS/Model/Payment/OpenInvoiceNl.php | 140 +
.../OPS/Model/Payment/PayPerMail.php | 41 +
.../Netresearch/OPS/Model/Payment/Paypal.php | 26 +
.../OPS/Model/Payment/Paysafecard.php | 26 +
.../OPS/Model/Payment/PingPing.php | 26 +
.../OPS/Model/Payment/PostFinanceEFinance.php | 25 +
.../OPS/Model/Payment/Recurring/Cc.php | 391 ++
.../Payment/Recurring/Cc/ParameterBag.php | 533 +++
.../OPS/Model/Response/Handler.php | 77 +
.../OPS/Model/Response/Type/Abstract.php | 373 ++
.../OPS/Model/Response/Type/Authorize.php | 251 ++
.../OPS/Model/Response/Type/Capture.php | 151 +
.../OPS/Model/Response/Type/Refund.php | 193 +
.../OPS/Model/Response/Type/Special.php | 87 +
.../OPS/Model/Response/Type/Void.php | 67 +
.../OPS/Model/Response/TypeInterface.php | 51 +
.../Model/Source/BankTransfer/Countries.php | 70 +
.../Source/Cc/AliasInterfaceEnabledTypes.php | 62 +
.../OPS/Model/Source/Cc/RecurringTypes.php | 50 +
.../Netresearch/OPS/Model/Source/Cc/Types.php | 52 +
.../DebitCard/AliasInterfaceEnabledTypes.php | 61 +
.../OPS/Model/Source/DebitCard/Types.php | 52 +
.../Model/Source/DirectDebit/Countries.php | 65 +
.../Model/Source/DirectEbanking/Brands.php | 67 +
.../Model/Source/Kwixo/ProductCategories.php | 127 +
.../OPS/Model/Source/Kwixo/ShipMethodType.php | 94 +
.../Netresearch/OPS/Model/Source/Mode.php | 31 +
.../OPS/Model/Source/OrderReference.php | 50 +
.../OPS/Model/Source/PaymentAction.php | 50 +
.../Netresearch/OPS/Model/Source/Pmlist.php | 54 +
.../Netresearch/OPS/Model/Source/Template.php | 58 +
.../OPS/Model/Source/TemplateType.php | 23 +
.../Netresearch/OPS/Model/Status.php | 301 ++
.../Netresearch/OPS/Model/Status/Feedback.php | 33 +
.../Netresearch/OPS/Model/Status/Update.php | 314 ++
.../OPS/Model/Subscription/Manager.php | 306 ++
.../Model/System/Config/Backend/Encoding.php | 46 +
.../System/Config/Backend/Flex/Methods.php | 67 +
.../System/Config/Backend/HashMethods.php | 48 +
.../Config/Backend/Intersolve/Brands.php | 60 +
.../System/Config/Backend/PaymentLogo.php | 47 +
.../OPS/Model/System/Config/Mode.php | 40 +
.../OPS/Model/System/Config/Template.php | 63 +
.../Model/Validator/CompositeInterface.php | 12 +
.../Validator/Kwixo/Shipping/Setting.php | 95 +
.../OPS/Model/Validator/Parameter/Factory.php | 63 +
.../OPS/Model/Validator/Parameter/Length.php | 96 +
.../Model/Validator/Parameter/Validator.php | 56 +
.../Adminhtml/Customer/Renderer/StateTest.php | 23 +
.../Adminhtml/Kwixo/Shipping/EditTest.php | 81 +
.../Order/Creditmemo/Totals/CheckboxTest.php | 11 +
.../OPS/Test/Block/Alias/ListTest.php | 77 +
.../Checkout/DeviceFingerprintingTest.php | 75 +
.../fixtures/fingerPrintingDisabled.yaml | 3 +
.../fixtures/fingerPrintingEnabled.yaml | 3 +
.../OPS/Test/Block/Form/CcTest.php | 459 +++
.../Block/Form/CcTest/fixtures/aliases.yaml | 92 +
.../OPS/Test/Block/Form/DirectDebitTest.php | 51 +
.../OPS/Test/Block/Form/Field/MethodTest.php | 42 +
.../OPS/Test/Block/Form/FlexTest.php | 89 +
.../Netresearch/OPS/Test/Block/Form/Ideal.php | 12 +
.../OPS/Test/Block/Form/InterSolveTest.php | 52 +
.../Block/Form/Kwixo/ApresReceptionTest.php | 29 +
.../Test/Block/Form/Kwixo/ComptantTest.php | 30 +
.../OPS/Test/Block/Form/Kwixo/CreditTest.php | 34 +
.../Netresearch/OPS/Test/Block/FormTest.php | 106 +
.../OPS/Test/Block/FormTest/fixtures/.gitkeep | 0
.../Block/FormTest/fixtures/FormTest.yaml | 22 +
.../OPS/Test/Block/FrauddetectionTest.php | 65 +
.../OPS/Test/Block/Info/FlexTest.php | 50 +
.../OPS/Test/Block/PlaceFormShaTest.php | 81 +
.../OPS/Test/Block/PlaceformTest.php | 92 +
.../Test/Block/RetryPayment/MethodsTest.php | 86 +
.../OPS/Test/Block/RetryPaymentTest.php | 94 +
.../System/Config/Form/Field/ImageTest.php | 73 +
.../System/Config/KwixoconfigurationTest.php | 24 +
.../OPS/Test/Block/System/Config/ModeTest.php | 21 +
.../Adminhtml/AdminControllerTest.php | 82 +
.../Adminhtml/KwixocategoryControllerTest.php | 45 +
.../fixtures/category_mapping.yaml | 11 +
.../Adminhtml/KwixoshippingControllerTest.php | 133 +
.../fixtures/shipping_settings.yaml | 7 +
.../Adminhtml/OpsstatusControllerTest.php | 71 +
.../Test/Controller/AliasControllerTest.php | 125 +
.../AliasControllerTest/fixtures/orders.yaml | 595 +++
.../OPS/Test/Controller/ApiControllerTest.php | 165 +
.../Test/Controller/DeviceControllerTest.php | 66 +
.../Test/Controller/PaymentControllerTest.php | 413 ++
.../PaymentControllerTest/fixtures/.gitkeep | 0
.../fixtures/orders.yaml | 26 +
.../OPS/Test/Helper/AddressTest.php | 22 +
.../AddressTest/expectations/splitStreet.yaml | 209 +
.../AddressTest/providers/splitStreet.yaml | 105 +
.../Netresearch/OPS/Test/Helper/AliasTest.php | 763 ++++
.../Test/Helper/AliasTest/fixtures/.gitkeep | 0
.../Netresearch/OPS/Test/Helper/ApiTest.php | 52 +
.../Netresearch/OPS/Test/Helper/DataTest.php | 170 +
.../OPS/Test/Helper/DirectDebitTest.php | 144 +
.../Helper/DirectDebitTest/fixtures/.gitkeep | 0
.../DirectDebitTest/fixtures/orders.yaml | 79 +
.../OPS/Test/Helper/DirectLinkTest.php | 562 +++
.../Helper/DirectLinkTest/fixtures/.gitkeep | 0
.../Netresearch/OPS/Test/Helper/KwixoTest.php | 132 +
.../KwixoTest/fixtures/category_mapping.yaml | 11 +
.../OPS/Test/Helper/MobileDetectTest.php | 77 +
.../OPS/Test/Helper/Order/CaptureTest.php | 82 +
.../Order/CaptureTest/fixtures/.gitkeep | 0
.../OPS/Test/Helper/Order/RefundTest.php | 141 +
.../Helper/Order/RefundTest/fixtures/.gitkeep | 0
.../Netresearch/OPS/Test/Helper/OrderTest.php | 137 +
.../Test/Helper/OrderTest/fixtures/order.yaml | 42 +
.../Helper/Payment/DirectLink/RequestTest.php | 89 +
.../DirectLink/RequestTest/fixtures/.gitkeep | 0
.../OPS/Test/Helper/Payment/RequestTest.php | 323 ++
.../OPS/Test/Helper/PaymentTest.php | 708 ++++
.../Test/Helper/PaymentTest/fixtures/.gitkeep | 0
.../Netresearch/OPS/Test/Helper/QuoteTest.php | 176 +
.../Test/Helper/QuoteTest/fixtures/.gitkeep | 1 +
.../OPS/Test/Helper/SubscriptionTest.php | 116 +
.../SubscriptionTest/fixtures/profile.yaml | 11 +
.../Helper/Validation/Checkout/StepTest.php | 44 +
.../OPS/Test/Helper/Validation/ResultTest.php | 94 +
.../ResultTest/fixtures/quotes.yaml | 42 +
.../OPS/Test/Helper/VersionTest.php | 92 +
.../Test/Model/AliasTest/fixtures/.gitkeep | 0
.../OPS/Test/Model/Api/DirectLinkShaTest.php | 44 +
.../OPS/Test/Model/Api/DirectLinkTest.php | 253 ++
.../Capture/Additional/OpenInvoiceNlTest.php | 291 ++
.../Operation/Capture/ParameterTest.php | 70 +
.../Model/Backend/Operation/ParameterTest.php | 52 +
.../Refund/Additional/OpenInvoiceNlTest.php | 248 ++
.../Operation/Refund/ParameterTest.php | 91 +
.../Netresearch/OPS/Test/Model/ConfigTest.php | 611 +++
.../OPS/Test/Model/File/Download.php | 37 +
.../Test/Model/Kwixo/Category/MappingTest.php | 28 +
.../fixtures/category_mapping.yaml | 11 +
.../OPS/Test/Model/Mysql4/Alias/AliasTest.php | 9 +
.../OPS/Test/Model/Mysql4/AliasTest.php | 11 +
.../OPS/Test/Model/ObserverTest.php | 1111 ++++++
.../Test/Model/ObserverTest/fixtures/.gitkeep | 0
.../Model/Payment/AbstractCaptureTest.php | 276 ++
.../Test/Model/Payment/AbstractRefundTest.php | 214 +
.../OPS/Test/Model/Payment/AbstractTest.php | 890 +++++
.../expectations/paymentMethods.yaml | 279 ++
.../Payment/AbstractTest/fixtures/.gitkeep | 0
.../Payment/AbstractTest/fixtures/orders.yaml | 135 +
.../OPS/Test/Model/Payment/BancontactTest.php | 81 +
.../Payment/BancontactTest/fixtures/.gitkeep | 0
.../OPS/Test/Model/Payment/CcTest.php | 213 +
.../Test/Model/Payment/ChinaUnionPayTest.php | 47 +
.../OPS/Test/Model/Payment/DebitcardTest.php | 53 +
.../Test/Model/Payment/DirectDebitTest.php | 23 +
.../Test/Model/Payment/DirectEbankingTest.php | 19 +
.../OPS/Test/Model/Payment/DirectLinkTest.php | 475 +++
.../Payment/Features/PaymentEmailTest.php | 120 +
.../Payment/Features/ZeroAmountAuthTest.php | 58 +
.../OPS/Test/Model/Payment/FlexTest.php | 77 +
.../OPS/Test/Model/Payment/IDealTest.php | 145 +
.../Payment/IDealTest/fixtures/orders.yaml | 58 +
.../OPS/Test/Model/Payment/InterSolveTest.php | 78 +
.../Test/Model/Payment/Kwixo/AbstractTest.php | 768 ++++
.../expectations/paymentMethods.yaml | 279 ++
.../Kwixo/AbstractTest/fixtures/.gitkeep | 0
.../Kwixo/AbstractTest/fixtures/orders.yaml | 633 +++
.../Model/Payment/KwixoApresReceptionTest.php | 55 +
.../Test/Model/Payment/KwixoComptantTest.php | 56 +
.../Test/Model/Payment/KwixoCreditTest.php | 59 +
.../OPS/Test/Model/Payment/ObjectHandler.php | 14 +
.../Test/Model/Payment/OpenInvoiceAtTest.php | 87 +
.../Test/Model/Payment/OpenInvoiceDeTest.php | 60 +
.../Test/Model/Payment/OpenInvoiceNlTest.php | 94 +
.../OPS/Test/Model/Payment/PayPerMailTest.php | 77 +
.../Payment/Recurring/Cc/ParameterBagTest.php | 396 ++
.../Test/Model/Payment/Recurring/CcTest.php | 582 +++
.../OPS/Test/Model/Payment/objects.xml | 4 +
.../OPS/Test/Model/Response/TestCase.php | 62 +
.../Model/Response/Type/AuthorizeTest.php | 267 ++
.../Type/AuthorizeTest/fixtures/orders.yaml | 239 ++
.../Test/Model/Response/Type/CaptureTest.php | 188 +
.../Type/CaptureTest/fixtures/orders.yaml | 135 +
.../Test/Model/Response/Type/RefundTest.php | 274 ++
.../Type/RefundTest/fixtures/orders.yaml | 157 +
.../Cc/AliasInterfaceEnabledTypesTest.php | 20 +
.../Model/Source/Cc/RecurringTypesTest.php | 41 +
.../Source/DirectEbanking/BrandsTest.php | 19 +
.../Source/Kwixo/ProductCategoriesTest.php | 51 +
.../Model/Source/Kwixo/ShipMethodTypeTest.php | 25 +
.../OPS/Test/Model/Source/ModeTest.php | 21 +
.../Test/Model/Source/OrderReferenceTest.php | 22 +
.../OPS/Test/Model/Status/UpdateTest.php | 311 ++
.../Status/UpdateTest/fixtures/orders.yaml | 135 +
.../Netresearch/OPS/Test/Model/StatusTest.php | 122 +
.../Test/Model/Subscription/ManagerTest.php | 176 +
.../Config/Backend/Design/BrandsTest.php | 53 +
.../System/Config/Backend/EncodingTest.php | 60 +
.../Config/Backend/Flex/MethodsTest.php | 106 +
.../System/Config/Backend/PaymentLogoTest.php | 53 +
.../Validator/Kwixo/Shipping/Setting.php | 124 +
.../Model/Validator/Parameter/FactoryTest.php | 34 +
.../Model/Validator/Parameter/LengthTest.php | 47 +
.../Validator/Parameter/ValidatorTest.php | 36 +
.../OPS/Test/var/fixtures/aliases.yaml | 92 +
.../OPS/Test/var/fixtures/orders.yaml | 703 ++++
.../OPS/Test/var/fixtures/quotes.yaml | 21 +
.../Netresearch/OPS/Trait/AliasController.php | 259 ++
.../Netresearch/OPS/Trait/PaymentHelper.php | 60 +
.../controllers/Adminhtml/AdminController.php | 80 +
.../controllers/Adminhtml/AliasController.php | 42 +
.../Adminhtml/KwixocategoryController.php | 228 ++
.../Adminhtml/KwixoshippingController.php | 93 +
.../Adminhtml/OpsstatusController.php | 31 +
.../OPS/controllers/AliasController.php | 13 +
.../OPS/controllers/ApiController.php | 89 +
.../OPS/controllers/CustomerController.php | 68 +
.../OPS/controllers/DeviceController.php | 83 +
.../OPS/controllers/PaymentController.php | 408 ++
.../data/ops_setup/data-install-14.02.05.php | 12 +
.../data-upgrade-14.02.05-14.06.25.php | 12 +
.../data-upgrade-14.06.25-14.07.16.php | 150 +
.../data-upgrade-15.06.08-15.11.02.php | 44 +
.../data-upgrade-15.11.09-16.03.09.php | 37 +
.../community/Netresearch/OPS/etc/config.xml | 599 +++
.../Netresearch/OPS/etc/jstranslator.xml | 27 +
.../community/Netresearch/OPS/etc/system.xml | 3542 +++++++++++++++++
.../sql/ops_setup/mysql4-install-1.0.1.php | 46 +
.../mysql4-upgrade-1.0.1-12.12.03.php | 24 +
.../mysql4-upgrade-13.04.10-13.04.16.php | 126 +
.../mysql4-upgrade-13.05.30-13.06.07.php | 70 +
.../mysql4-upgrade-13.06.07-13.07.04.php | 17 +
.../mysql4-upgrade-13.07.10-13.07.23.php | 14 +
.../mysql4-upgrade-13.11.04-13.11.05.php | 15 +
.../mysql4-upgrade-14.01.27-14.02.05.php | 52 +
.../mysql4-upgrade-16.05.26-27.06.16.php | 8 +
.../adminhtml/default/default/layout/ops.xml | 89 +
.../default/template/ops/categoriestree.phtml | 632 +++
.../default/template/ops/form/cc.phtml | 177 +
.../template/ops/form/directDebit.phtml | 189 +
.../template/ops/form/kwixo/category.phtml | 21 +
.../template/ops/form/kwixo/shipping.phtml | 102 +
.../default/template/ops/form/opsId.phtml | 37 +
.../template/ops/form/payPerMail.phtml | 31 +
.../default/default/template/ops/info.phtml | 64 +
.../template/ops/info/bancontact.phtml | 81 +
.../default/template/ops/info/cc.phtml | 73 +
.../default/template/ops/info/flex.phtml | 84 +
.../default/template/ops/info/opsId.phtml | 23 +
.../template/ops/info/payPerMail.phtml | 23 +
.../default/template/ops/info/redirect.phtml | 75 +
.../closed-transaction/warning.phtml | 28 +
.../order/creditmemo/totals/checkbox.phtml | 30 +
.../ops/system/config/kwixoconfiglinks.phtml | 44 +
.../template/ops/system/config/support.phtml | 100 +
.../frontend/base/default/layout/ops.xml | 189 +
.../ops/checkout/deviceFingerprinting.phtml | 30 +
.../ops/checkout/subscriptionNotice.phtml | 45 +
.../template/ops/customer/alias/list.phtml | 68 +
.../base/default/template/ops/form.phtml | 38 +
.../default/template/ops/form/alias.phtml | 42 +
.../template/ops/form/bankTransfer.phtml | 51 +
.../base/default/template/ops/form/cc.phtml | 168 +
.../template/ops/form/directDebit.phtml | 145 +
.../template/ops/form/directEbanking.phtml | 51 +
.../base/default/template/ops/form/flex.phtml | 98 +
.../default/template/ops/form/ideal.phtml | 37 +
.../template/ops/form/intersolve.phtml | 56 +
.../ops/form/kwixo/apres_reception.phtml | 11 +
.../template/ops/form/kwixo/comptant.phtml | 11 +
.../template/ops/form/kwixo/credit.phtml | 11 +
.../template/ops/form/openInvoice.phtml | 42 +
.../default/template/ops/form/other.phtml | 26 +
.../default/template/ops/frauddetection.phtml | 48 +
.../base/default/template/ops/info.phtml | 27 +
.../default/template/ops/info/alias.phtml | 23 +
.../template/ops/info/bancontact.phtml | 23 +
.../base/default/template/ops/info/cc.phtml | 23 +
.../base/default/template/ops/info/flex.phtml | 33 +
.../default/template/ops/info/opsId.phtml | 23 +
.../template/ops/info/payPerMail.phtml | 23 +
.../default/template/ops/info/redirect.phtml | 23 +
.../base/default/template/ops/paypage.phtml | 23 +
.../base/default/template/ops/placeform.phtml | 128 +
.../template/ops/placeform3dsecure.phtml | 23 +
.../default/template/ops/retryPayment.phtml | 146 +
.../template/ops/customer/alias/list.phtml | 80 +
app/etc/modules/Netresearch_OPS.xml | 44 +
app/locale/de_DE/Netresearch_OPS.csv | 485 +++
.../ops/ops_email_resend_payment_info.html | 49 +
.../email/ops/ops_pay_per_mail_info.html | 49 +
.../email/ops/suspend_subscription.html | 43 +
app/locale/en_US/Netresearch_OPS.csv | 485 +++
.../ops/ops_email_resend_payment_info.html | 49 +
.../email/ops/ops_pay_per_mail_info.html | 49 +
.../email/ops/suspend_subscription.html | 43 +
app/locale/fr_FR/Netresearch_OPS.csv | 189 +
app/locale/it_IT/Netresearch_OPS.csv | 185 +
app/locale/nl_NL/Netresearch_OPS.csv | 186 +
composer.json | 8 +
js/netresearch/ops/deviceFingerprinting.js | 48 +
js/netresearch/ops/osc_payment.js | 101 +
js/netresearch/ops/payment.js | 198 +
js/netresearch/ops/tokenization.js | 230 ++
lib/MobileDetect/Mobile_Detect.php | 1387 +++++++
modman | 20 +
skin/adminhtml/default/default/ops.css | 46 +
skin/frontend/base/default/css/ops.css | 299 ++
.../ops/alias/brands/AmericanExpress.png | Bin 0 -> 119967 bytes
.../images/ops/alias/brands/DinnerClub.png | Bin 0 -> 40457 bytes
.../images/ops/alias/brands/Maestro.png | Bin 0 -> 29431 bytes
.../images/ops/alias/brands/MasterCard.png | Bin 0 -> 96289 bytes
.../default/images/ops/alias/brands/VISA.png | Bin 0 -> 49753 bytes
.../images/ops/kwixo/apres_reception.jpg | Bin 0 -> 4950 bytes
.../default/images/ops/kwixo/comptant.jpg | Bin 0 -> 4841 bytes
.../base/default/images/ops/kwixo/credit.jpg | Bin 0 -> 4814 bytes
.../default/images/ops/logos/ops_BCMC.png | Bin 0 -> 2306 bytes
.../images/ops/logos/ops_Masterpass.png | Bin 0 -> 1529 bytes
.../images/ops/logos/ops_bankTransfer.png | Bin 0 -> 2037 bytes
.../images/ops/logos/ops_belfiusDirectNet.png | Bin 0 -> 2174 bytes
.../default/images/ops/logos/ops_cashU.png | Bin 0 -> 2218 bytes
.../images/ops/logos/ops_cbcOnline.png | Bin 0 -> 1198 bytes
.../base/default/images/ops/logos/ops_cc.png | Bin 0 -> 2293 bytes
.../images/ops/logos/ops_chinaUnionPay.png | Bin 0 -> 3325 bytes
.../base/default/images/ops/logos/ops_dc.png | Bin 0 -> 2293 bytes
.../images/ops/logos/ops_directDebit.png | Bin 0 -> 1863 bytes
.../images/ops/logos/ops_directEbanking.png | Bin 0 -> 2277 bytes
.../default/images/ops/logos/ops_eDankort.png | Bin 0 -> 1708 bytes
.../base/default/images/ops/logos/ops_eps.png | Bin 0 -> 1848 bytes
.../default/images/ops/logos/ops_flex.png | Bin 0 -> 3490 bytes
.../images/ops/logos/ops_fortisPayButton.png | Bin 0 -> 3488 bytes
.../default/images/ops/logos/ops_giroPay.png | Bin 0 -> 2463 bytes
.../default/images/ops/logos/ops_iDeal.png | Bin 0 -> 2859 bytes
.../images/ops/logos/ops_ingHomePay.png | Bin 0 -> 2187 bytes
.../images/ops/logos/ops_interSolve.jpg | Bin 0 -> 39346 bytes
.../images/ops/logos/ops_interSolve.png | Bin 0 -> 1241 bytes
.../images/ops/logos/ops_kbcOnline.png | Bin 0 -> 1147 bytes
.../ops/logos/ops_kwixoApresReception.png | Bin 0 -> 1822 bytes
.../images/ops/logos/ops_kwixoComptant.png | Bin 0 -> 1822 bytes
.../images/ops/logos/ops_kwixoCredit.png | Bin 0 -> 1822 bytes
.../images/ops/logos/ops_openInvoiceAt.png | Bin 0 -> 1606 bytes
.../images/ops/logos/ops_openInvoiceDe.png | Bin 0 -> 1606 bytes
.../images/ops/logos/ops_openInvoiceNl.png | Bin 0 -> 1606 bytes
.../default/images/ops/logos/ops_opsid.png | Bin 0 -> 2037 bytes
.../default/images/ops/logos/ops_paypal.png | Bin 0 -> 1963 bytes
.../images/ops/logos/ops_paysafecard.png | Bin 0 -> 1860 bytes
.../default/images/ops/logos/ops_pingPing.png | Bin 0 -> 1884 bytes
.../ops/logos/ops_postFinanceEFinance.png | Bin 0 -> 1319 bytes
.../images/ops/logos/ops_recurring_cc.png | Bin 0 -> 2293 bytes
skin/frontend/rwd/default/css/ops.css | 316 ++
478 files changed, 56036 insertions(+)
create mode 100644 README.md
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Edit/Tab/Alias.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/PaymentMethod.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/State.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixo/Shipping/Edit.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/CategoryTree.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit/Form.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/ClosedTransaction/Warning.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/Totals/Checkbox.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Alias/List.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Checkout/DeviceFingerprinting.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Checkout/SubscriptionNotice.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/Alias.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/BankTransfer.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/Cc.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/DirectDebit.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/DirectEbanking.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/Flex.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/Ideal.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/InterSolve.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/Kwixo/ApresReception.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/Kwixo/Comptant.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/Kwixo/Credit.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/OpenInvoice.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/OpsId.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/PayPerMail.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Form/RecurringCc.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Frauddetection.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/Alias.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/Bancontact.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/Cc.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/Flex.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/OpsId.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/PayPerMail.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/RecurringCc.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Info/Redirect.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Paypage.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Placeform.php
create mode 100644 app/code/community/Netresearch/OPS/Block/Placeform3dsecure.php
create mode 100644 app/code/community/Netresearch/OPS/Block/RetryPayment.php
create mode 100644 app/code/community/Netresearch/OPS/Block/RetryPayment/Methods.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Brand.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Image.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Method.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/RecurringActive.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/Kwixoconfiguration.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/Mode.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/PaymentForm.php
create mode 100644 app/code/community/Netresearch/OPS/Block/System/Config/Support.php
create mode 100644 app/code/community/Netresearch/OPS/Controller/Abstract.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Address.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Alias.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Api.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Creditcard.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Data.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Debitcard.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/DirectDebit.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Directlink.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Kwixo.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/MobileDetect.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Order.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Order/Abstract.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Order/Capture.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Order/Refund.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Payment.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/Request.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/RequestInterface.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Payment/Request.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Quote.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Subscription.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Validation/Checkout/Step.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Validation/Result.php
create mode 100644 app/code/community/Netresearch/OPS/Helper/Version.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Alias.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Alias/State.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Api/Directlink.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Additional/OpenInvoiceNl.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Parameter.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Abstract.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/Interface.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/OpenInvoiceNlAbstract.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Interface.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Additional/OpenInvoiceNl.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Parameter.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Config.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Eci/Values.php
create mode 100644 app/code/community/Netresearch/OPS/Model/File/Download.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Kwixo/Category/Mapping.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Kwixo/Shipping/Setting.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Mysql4/Alias.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Mysql4/Alias/Collection.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping/Collection.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting/Collection.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Observer.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Abstract.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Backend/OpsId.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Bancontact.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/BankTransfer.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/BelfiusDirectNet.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/CashU.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/CbcOnline.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Cc.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/ChinaUnionPay.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Debitcard.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/DirectDebit.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/DirectEbanking.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/DirectLink.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/EDankort.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Eps.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Features/PaymentEmail.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Features/ZeroAmountAuth.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Flex.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/FortisPayButton.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/GiroPay.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/IDeal.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/IngHomePay.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/InterSolve.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/KbcOnline.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Kwixo/Abstract.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/KwixoApresReception.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/KwixoComptant.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/KwixoCredit.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Masterpass.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/OpenInvoice/Abstract.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceAt.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceDe.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceNl.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/PayPerMail.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Paypal.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Paysafecard.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/PingPing.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/PostFinanceEFinance.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc/ParameterBag.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/Handler.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/Type/Abstract.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/Type/Authorize.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/Type/Capture.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/Type/Refund.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/Type/Special.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/Type/Void.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Response/TypeInterface.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/BankTransfer/Countries.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Cc/AliasInterfaceEnabledTypes.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Cc/RecurringTypes.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Cc/Types.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/DebitCard/AliasInterfaceEnabledTypes.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/DebitCard/Types.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/DirectDebit/Countries.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/DirectEbanking/Brands.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Kwixo/ProductCategories.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Kwixo/ShipMethodType.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Mode.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/OrderReference.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/PaymentAction.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Pmlist.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/Template.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Source/TemplateType.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Status.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Status/Feedback.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Status/Update.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Subscription/Manager.php
create mode 100644 app/code/community/Netresearch/OPS/Model/System/Config/Backend/Encoding.php
create mode 100644 app/code/community/Netresearch/OPS/Model/System/Config/Backend/Flex/Methods.php
create mode 100644 app/code/community/Netresearch/OPS/Model/System/Config/Backend/HashMethods.php
create mode 100644 app/code/community/Netresearch/OPS/Model/System/Config/Backend/Intersolve/Brands.php
create mode 100644 app/code/community/Netresearch/OPS/Model/System/Config/Backend/PaymentLogo.php
create mode 100644 app/code/community/Netresearch/OPS/Model/System/Config/Mode.php
create mode 100644 app/code/community/Netresearch/OPS/Model/System/Config/Template.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Validator/CompositeInterface.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Validator/Kwixo/Shipping/Setting.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Validator/Parameter/Factory.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Validator/Parameter/Length.php
create mode 100644 app/code/community/Netresearch/OPS/Model/Validator/Parameter/Validator.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Customer/Renderer/StateTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Kwixo/Shipping/EditTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Sales/Order/Creditmemo/Totals/CheckboxTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Alias/ListTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingDisabled.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingEnabled.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/CcTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/CcTest/fixtures/aliases.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/DirectDebitTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/Field/MethodTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/FlexTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/Ideal.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/InterSolveTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ApresReceptionTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ComptantTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/CreditTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/FormTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/FormTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/FormTest/fixtures/FormTest.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/FrauddetectionTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/Info/FlexTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/PlaceFormShaTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/PlaceformTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/RetryPayment/MethodsTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/RetryPaymentTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/System/Config/Form/Field/ImageTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/System/Config/KwixoconfigurationTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Block/System/Config/ModeTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/Adminhtml/AdminControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/Adminhtml/KwixocategoryControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/Adminhtml/KwixocategoryControllerTest/fixtures/category_mapping.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/Adminhtml/KwixoshippingControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/Adminhtml/KwixoshippingControllerTest/fixtures/shipping_settings.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/Adminhtml/OpsstatusControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/AliasControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/AliasControllerTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/ApiControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/DeviceControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/AddressTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/AddressTest/expectations/splitStreet.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/AddressTest/providers/splitStreet.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/AliasTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/AliasTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/ApiTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/DataTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/DirectLinkTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/DirectLinkTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/KwixoTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/KwixoTest/fixtures/category_mapping.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/MobileDetectTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Order/CaptureTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Order/CaptureTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Order/RefundTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Order/RefundTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/OrderTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/OrderTest/fixtures/order.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Payment/DirectLink/RequestTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Payment/DirectLink/RequestTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Payment/RequestTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/PaymentTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/PaymentTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/QuoteTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/QuoteTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest/fixtures/profile.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Validation/Checkout/StepTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest/fixtures/quotes.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Helper/VersionTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/AliasTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkShaTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/Additional/OpenInvoiceNlTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/ParameterTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/ParameterTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/Additional/OpenInvoiceNlTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/ParameterTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/ConfigTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/File/Download.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest/fixtures/category_mapping.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Mysql4/Alias/AliasTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Mysql4/AliasTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/ObserverTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/ObserverTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractCaptureTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractRefundTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/expectations/paymentMethods.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/BancontactTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/BancontactTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/CcTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/ChinaUnionPayTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/DebitcardTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/DirectDebitTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/DirectEbankingTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/DirectLinkTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Features/PaymentEmailTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Features/ZeroAmountAuthTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/FlexTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/InterSolveTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/expectations/paymentMethods.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/fixtures/.gitkeep
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoApresReceptionTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoComptantTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoCreditTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/ObjectHandler.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceAtTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceDeTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceNlTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/PayPerMailTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/Cc/ParameterBagTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/CcTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Payment/objects.xml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Response/TestCase.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Source/Cc/AliasInterfaceEnabledTypesTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Source/Cc/RecurringTypesTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Source/DirectEbanking/BrandsTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ProductCategoriesTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ShipMethodTypeTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Source/ModeTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Source/OrderReferenceTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/StatusTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Subscription/ManagerTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Design/BrandsTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/EncodingTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Flex/MethodsTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/PaymentLogoTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Validator/Kwixo/Shipping/Setting.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/FactoryTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/LengthTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/ValidatorTest.php
create mode 100644 app/code/community/Netresearch/OPS/Test/var/fixtures/aliases.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/var/fixtures/orders.yaml
create mode 100644 app/code/community/Netresearch/OPS/Test/var/fixtures/quotes.yaml
create mode 100644 app/code/community/Netresearch/OPS/Trait/AliasController.php
create mode 100644 app/code/community/Netresearch/OPS/Trait/PaymentHelper.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/Adminhtml/AdminController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/Adminhtml/AliasController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixocategoryController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixoshippingController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/Adminhtml/OpsstatusController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/AliasController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/ApiController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/CustomerController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/DeviceController.php
create mode 100644 app/code/community/Netresearch/OPS/controllers/PaymentController.php
create mode 100644 app/code/community/Netresearch/OPS/data/ops_setup/data-install-14.02.05.php
create mode 100644 app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.02.05-14.06.25.php
create mode 100644 app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.06.25-14.07.16.php
create mode 100644 app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.06.08-15.11.02.php
create mode 100644 app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.11.09-16.03.09.php
create mode 100644 app/code/community/Netresearch/OPS/etc/config.xml
create mode 100644 app/code/community/Netresearch/OPS/etc/jstranslator.xml
create mode 100644 app/code/community/Netresearch/OPS/etc/system.xml
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-install-1.0.1.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-1.0.1-12.12.03.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.04.10-13.04.16.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.05.30-13.06.07.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.06.07-13.07.04.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.07.10-13.07.23.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.11.04-13.11.05.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-14.01.27-14.02.05.php
create mode 100644 app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-16.05.26-27.06.16.php
create mode 100644 app/design/adminhtml/default/default/layout/ops.xml
create mode 100644 app/design/adminhtml/default/default/template/ops/categoriestree.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/form/cc.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/form/directDebit.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/form/kwixo/category.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/form/kwixo/shipping.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/form/opsId.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/form/payPerMail.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/info.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/info/bancontact.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/info/cc.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/info/flex.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/info/opsId.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/info/payPerMail.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/info/redirect.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/sales/order/creditmemo/closed-transaction/warning.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/sales/order/creditmemo/totals/checkbox.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/system/config/kwixoconfiglinks.phtml
create mode 100644 app/design/adminhtml/default/default/template/ops/system/config/support.phtml
create mode 100644 app/design/frontend/base/default/layout/ops.xml
create mode 100644 app/design/frontend/base/default/template/ops/checkout/deviceFingerprinting.phtml
create mode 100644 app/design/frontend/base/default/template/ops/checkout/subscriptionNotice.phtml
create mode 100644 app/design/frontend/base/default/template/ops/customer/alias/list.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/alias.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/bankTransfer.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/cc.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/directDebit.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/directEbanking.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/flex.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/ideal.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/intersolve.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/kwixo/apres_reception.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/kwixo/comptant.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/kwixo/credit.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/openInvoice.phtml
create mode 100644 app/design/frontend/base/default/template/ops/form/other.phtml
create mode 100644 app/design/frontend/base/default/template/ops/frauddetection.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info/alias.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info/bancontact.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info/cc.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info/flex.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info/opsId.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info/payPerMail.phtml
create mode 100644 app/design/frontend/base/default/template/ops/info/redirect.phtml
create mode 100644 app/design/frontend/base/default/template/ops/paypage.phtml
create mode 100644 app/design/frontend/base/default/template/ops/placeform.phtml
create mode 100644 app/design/frontend/base/default/template/ops/placeform3dsecure.phtml
create mode 100644 app/design/frontend/base/default/template/ops/retryPayment.phtml
create mode 100644 app/design/frontend/rwd/default/template/ops/customer/alias/list.phtml
create mode 100644 app/etc/modules/Netresearch_OPS.xml
create mode 100644 app/locale/de_DE/Netresearch_OPS.csv
create mode 100644 app/locale/de_DE/template/email/ops/ops_email_resend_payment_info.html
create mode 100644 app/locale/de_DE/template/email/ops/ops_pay_per_mail_info.html
create mode 100644 app/locale/de_DE/template/email/ops/suspend_subscription.html
create mode 100644 app/locale/en_US/Netresearch_OPS.csv
create mode 100644 app/locale/en_US/template/email/ops/ops_email_resend_payment_info.html
create mode 100644 app/locale/en_US/template/email/ops/ops_pay_per_mail_info.html
create mode 100644 app/locale/en_US/template/email/ops/suspend_subscription.html
create mode 100644 app/locale/fr_FR/Netresearch_OPS.csv
create mode 100644 app/locale/it_IT/Netresearch_OPS.csv
create mode 100644 app/locale/nl_NL/Netresearch_OPS.csv
create mode 100644 composer.json
create mode 100644 js/netresearch/ops/deviceFingerprinting.js
create mode 100644 js/netresearch/ops/osc_payment.js
create mode 100644 js/netresearch/ops/payment.js
create mode 100644 js/netresearch/ops/tokenization.js
create mode 100644 lib/MobileDetect/Mobile_Detect.php
create mode 100644 modman
create mode 100644 skin/adminhtml/default/default/ops.css
create mode 100644 skin/frontend/base/default/css/ops.css
create mode 100644 skin/frontend/base/default/images/ops/alias/brands/AmericanExpress.png
create mode 100644 skin/frontend/base/default/images/ops/alias/brands/DinnerClub.png
create mode 100644 skin/frontend/base/default/images/ops/alias/brands/Maestro.png
create mode 100644 skin/frontend/base/default/images/ops/alias/brands/MasterCard.png
create mode 100644 skin/frontend/base/default/images/ops/alias/brands/VISA.png
create mode 100644 skin/frontend/base/default/images/ops/kwixo/apres_reception.jpg
create mode 100644 skin/frontend/base/default/images/ops/kwixo/comptant.jpg
create mode 100644 skin/frontend/base/default/images/ops/kwixo/credit.jpg
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_BCMC.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_Masterpass.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_bankTransfer.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_belfiusDirectNet.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_cashU.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_cbcOnline.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_cc.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_chinaUnionPay.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_dc.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_directDebit.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_directEbanking.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_eDankort.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_eps.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_flex.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_fortisPayButton.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_giroPay.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_iDeal.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_ingHomePay.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_interSolve.jpg
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_interSolve.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_kbcOnline.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_kwixoApresReception.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_kwixoComptant.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_kwixoCredit.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_openInvoiceAt.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_openInvoiceDe.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_openInvoiceNl.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_opsid.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_paypal.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_paysafecard.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_pingPing.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_postFinanceEFinance.png
create mode 100644 skin/frontend/base/default/images/ops/logos/ops_recurring_cc.png
create mode 100644 skin/frontend/rwd/default/css/ops.css
diff --git a/README.md b/README.md
new file mode 100644
index 0000000..af14cd8
--- /dev/null
+++ b/README.md
@@ -0,0 +1,49 @@
+# Netresearch OPS
+
+**Extension for Magento 1**
+
+Tested for Magento 1.9.3.1
+
+Module version 16.12.14
+
+---
+
+*Please note that we are not the developer of this extension. In this repository, we only added modman and composer support. We will not provide any support for this repository. If you have any problems on integration, please use the official link provided below.*
+
+## Overview
+
+This module is the official Ingenico ePayments extension.
+
+For more information, please visit https://www.magentocommerce.com/magento-connect/official-ingenico-epayments-extension-1.html.
+
+## Installation
+
+Add the `require` and `repositories` sections to your composer.json as shown below and run `composer update`
+
+```
+{
+ ...
+
+ "repositories": [
+
+ ...
+
+ {"type": "git", "url": "https://github.com/kirchbergerknorr/magento1_netresearch_ops"},
+
+ ...
+ ],
+
+ ...
+
+ "require": {
+
+ ...
+
+ "kirchbergerknorr/magento1_netresearch_ops": "^16.12.14",
+
+ ...
+ },
+
+ ...
+}
+```
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Edit/Tab/Alias.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Edit/Tab/Alias.php
new file mode 100644
index 0000000..15f0229
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Edit/Tab/Alias.php
@@ -0,0 +1,172 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Block_Adminhtml_Customer_Edit_Tab_Alias
+ *
+ * @author Thomas Birke
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Block_Adminhtml_Customer_Edit_Tab_Alias
+ extends Mage_Adminhtml_Block_Widget_Grid
+ implements Mage_Adminhtml_Block_Widget_Tab_Interface
+{
+ public function _construct()
+ {
+ parent::_construct();
+ $this->setId('customer_edit_tab_ops_alias');
+ $this->setUseAjax(true);
+ }
+
+ /**
+ * Return Tab label
+ *
+ * @return string
+ */
+ public function getTabLabel()
+ {
+ return $this->__('Payment Information');
+ }
+
+ /**
+ * Return Tab label
+ *
+ * @return string
+ */
+ public function getTabTitle()
+ {
+ return $this->__('Payment Information');
+ }
+
+ /**
+ * Can show tab in tabs
+ *
+ * @return boolean
+ */
+ public function canShowTab()
+ {
+ $customer = Mage::registry('current_customer');
+ return (bool)$customer->getId();
+ }
+
+ /**
+ * Tab is hidden
+ *
+ * @return boolean
+ */
+ public function isHidden()
+ {
+ return false;
+ }
+
+ /**
+ * Defines after which tab, this tab should be rendered
+ *
+ * @return string
+ */
+ public function getAfter()
+ {
+ return 'orders';
+ }
+
+
+ protected function _prepareCollection()
+ {
+ $customer = Mage::registry('current_customer');
+
+ $collection = Mage::getModel('ops/alias')
+ ->getCollection()
+ ->addFieldToFilter('customer_id', $customer->getId());
+
+ $this->setCollection($collection);
+ return parent::_prepareCollection();
+ }
+
+ protected function _prepareColumns()
+ {
+ $this->addColumn(
+ 'alias', array(
+ 'header' => Mage::helper('ops')->__('Alias'),
+ 'align' => 'right',
+ 'index' => 'alias',
+ )
+ );
+
+ $this->addColumn(
+ 'payment_method', array(
+ 'header' => Mage::helper('ops')->__('Payment method'),
+ 'index' => 'payment_method',
+ 'renderer' => 'Netresearch_OPS_Block_Adminhtml_Customer_Renderer_PaymentMethod'
+ )
+ );
+
+ $this->addColumn(
+ 'brand', array(
+ 'header' => Mage::helper('ops')->__('Credit Card Type'),
+ 'index' => 'brand',
+ )
+ );
+
+ $this->addColumn(
+ 'pseudo_account_or_cc_no', array(
+ 'header' => Mage::helper('ops')->__('Card Number/Account Number'),
+ 'index' => 'pseudo_account_or_cc_no',
+ )
+ );
+
+ $this->addColumn(
+ 'expiration_date', array(
+ 'header' => Mage::helper('ops')->__('Expiration Date'),
+ 'index' => 'expiration_date',
+ )
+ );
+
+ $this->addColumn(
+ 'card_holder', array(
+ 'header' => Mage::helper('ops')->__('Card Holder'),
+ 'index' => 'card_holder',
+ )
+ );
+
+ $this->addColumn(
+ 'state', array(
+ 'header' => Mage::helper('ops')->__('State'),
+ 'index' => 'state',
+ 'renderer' => 'Netresearch_OPS_Block_Adminhtml_Customer_Renderer_State',
+ )
+ );
+
+ $this->addColumn(
+ 'action',
+ array(
+ 'header' => Mage::helper('ops')->__('Action'),
+ 'width' => '100',
+ 'type' => 'action',
+ 'getter' => 'getId',
+ 'actions' => array(
+ array(
+ 'caption' => Mage::helper('ops')->__('Delete'),
+ 'url' => array('base' => 'adminhtml/alias/delete'),
+ 'field' => 'id'
+ )
+ ),
+ 'filter' => false,
+ 'sortable' => false,
+ 'index' => 'stores',
+ 'is_system' => true,
+ )
+ );
+
+ return parent::_prepareColumns();
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/PaymentMethod.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/PaymentMethod.php
new file mode 100644
index 0000000..f18da52
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/PaymentMethod.php
@@ -0,0 +1,27 @@
+
+ */
+class Netresearch_OPS_Block_Adminhtml_Customer_Renderer_PaymentMethod
+ extends Mage_Adminhtml_Block_Widget_Grid_Column_Renderer_Abstract
+{
+
+ /**
+ * @param Varien_Object $row
+ * @return string
+ */
+ public function render(Varien_Object $row)
+ {
+ $title = '';
+ $methodCode = $row->getData($this->getColumn()->getIndex());
+ $instance = Mage::helper('payment')->getMethodInstance($methodCode);
+ if ($instance) {
+ $title = $instance->getTitle();
+ }
+
+ return $title;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/State.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/State.php
new file mode 100644
index 0000000..08b8e92
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Customer/Renderer/State.php
@@ -0,0 +1,21 @@
+getData($this->getColumn()->getIndex());
+ return Mage::helper('ops')->__($value);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixo/Shipping/Edit.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixo/Shipping/Edit.php
new file mode 100644
index 0000000..c6e78b3
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixo/Shipping/Edit.php
@@ -0,0 +1,86 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Block_Adminhtml_Kwixo_Shipping_Edit
+ extends Mage_Adminhtml_Block_Widget_Form_Container
+{
+
+
+ protected $kwixoShippingModel = null;
+
+ /**
+ * gets the form action url
+ *
+ * @return string
+ */
+ public function getFormActionUrl()
+ {
+ return $this->getUrl('adminhtml/kwixoshipping/save');
+ }
+
+ /**
+ * gets the shipping types
+ *
+ * @return array
+ */
+ public function getShippingMethods()
+ {
+ $methods = Mage::getSingleton('shipping/config')->getAllCarriers();
+ $options = array();
+
+ foreach ($methods as $carrierCode => $carrier) {
+ if (!$title = Mage::getStoreConfig("carriers/$carrierCode/title")) {
+ $title = $carrierCode;
+ }
+ $values = $this->getValues($carrierCode);
+ $options[] = array('code' => $carrierCode, 'label' => $title, 'values' => $values);
+ }
+
+ return $options;
+ }
+
+ /**
+ * returns the corresponding shipping method types
+ *
+ * @return array - the kwxixo Shipping method types
+ */
+ public function getKwixoShippingTypes()
+ {
+ return Mage::getModel('ops/source_kwixo_shipMethodType')->toOptionArray();
+ }
+
+ public function getKwixoShippingSettingModel()
+ {
+ if (null === $this->kwxioShippingModel) {
+ $this->kwixoShippingModel = Mage::getModel('ops/kwixo_shipping_setting');
+ }
+ return $this->kwixoShippingModel;
+ }
+
+ /**
+ * @param $carrierCode
+ * @return array
+ */
+ protected function getValues($carrierCode)
+ {
+ $values = array(
+ 'kwixo_shipping_type' => '',
+ 'kwixo_shipping_speed' => '',
+ 'kwixo_shipping_details' => ''
+ );
+ if (null != ($this->getData('postData')) && array_key_exists($carrierCode, $this->getData('postData'))) {
+ $errorData = $this->getData('postData');
+ $values = $errorData[$carrierCode];
+ } else {
+ $values = $this->getKwixoShippingSettingModel()->load($carrierCode, 'shipping_code')->getData();
+ }
+ return $values;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/CategoryTree.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/CategoryTree.php
new file mode 100644
index 0000000..b87399b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/CategoryTree.php
@@ -0,0 +1,106 @@
+setTemplate('ops/categoriestree.phtml');
+ $this->setUseAjax(true);
+ $this->_withProductCount = false;
+ }
+
+ public function getSwitchTreeUrl()
+ {
+ return $this->getUrl(
+ "*/*/tree",
+ array(
+ '_current' => true,
+ 'store' => null,
+ '_query' => false,
+ 'id' => null,
+ 'parent' => null
+ )
+ );
+ }
+
+ public function getNodesUrl()
+ {
+ return $this->getUrl('adminhtml/catalog_category/jsonTree');
+ }
+
+ public function getEditUrl()
+ {
+ return $this->getUrl('*/*/edit', array('_current' => true, '_query' => false, 'id' => null, 'parent' => null));
+ }
+
+ protected function _getNodeJson($node, $level = 0)
+ {
+ $item = array();
+ $item['text'] = $this->buildNodeName($node);
+ $item['id'] = $node->getId();
+ $item['cls'] = 'folder ' . ($node->getIsActive() ? 'active-category' : 'no-active-category');
+ $item['store'] = (int) $this->getStore()->getId();
+ $item['path'] = $node->getData('path');
+ $item['allowDrop'] = false;
+ $item['allowDrag'] = false;
+ if ((int) $node->getChildrenCount() > 0) {
+ $item['children'] = array();
+ }
+ $isParent = $this->_isParentSelectedCategory($node);
+ if ($node->hasChildren()) {
+ $item['children'] = array();
+ if (!($this->getUseAjax() && $node->getLevel() > 1 && !$isParent)) {
+ foreach ($node->getChildren() as $child) {
+ $item['children'][] = $this->_getNodeJson($child, $level + 1);
+ }
+ }
+ }
+
+ if ($isParent || $node->getLevel() < 2) {
+ $item['expanded'] = true;
+ }
+ return $item;
+ }
+
+ protected function _getProductTypeLabel($productTypeId)
+ {
+ $res = '';
+ $types = Mage::getModel('ops/source_kwixo_productCategories')->toOptionArray();
+ foreach ($types as $data) {
+ if ($data['value'] == $productTypeId) {
+ $res = $data['label'];
+ break;
+ }
+ }
+ return $res;
+ }
+
+ public function buildNodeName($node)
+ {
+ $result = $this->escapeHtml($node->getName());
+ return $result;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit.php
new file mode 100644
index 0000000..d38d6e6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit.php
@@ -0,0 +1,58 @@
+_objectId = 'id';
+ $this->_controller = 'adminhtml_kwixocategory';
+ $this->_blockGroup = 'ops';
+ $this->_mode = 'edit';
+ $this->_updateButton('save', 'label', $this->__('Save'));
+ $this->_updateButton('save', 'url', $this->getUrl('*/*/save'));
+
+ }
+
+ public function getHeaderText()
+ {
+ $categoryId = (int) $this->getRequest()->getParam('id');
+
+ if ($categoryId <= 0) {
+ return Mage::helper('ops/data')->__('Categories configuration');
+ }
+ $category = Mage::getModel('catalog/category')->load($categoryId);
+ return Mage::helper('ops/data')->__("Categorie's %s configuration", $category->getName());
+ }
+
+ public function getFormActionUrl()
+ {
+ return $this->getUrl('*/*/save');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit/Form.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit/Form.php
new file mode 100644
index 0000000..7bf3e59
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Kwixocategory/Edit/Form.php
@@ -0,0 +1,75 @@
+ 'edit_form',
+ 'action' => $this->getUrl('*/*/save'),
+ 'method' => 'post',
+ 'enctype' => 'multipart/form-data'
+ )
+ );
+
+ $categoryId = (int) $this->getRequest()->getParam('id');
+ if ($categoryId <= 0) {
+ return parent::_prepareForm();
+ }
+ $kwixoCategoryMapping = Mage::getModel('ops/kwixo_category_mapping')->loadByCategoryId($categoryId);
+ $storeId = (int) $this->getRequest()->getParam('store');
+
+ $fieldset = $form->addFieldset(
+ 'ops_form',
+ array(
+ 'legend' => Mage::helper('ops/data')->__('Categories configuration')
+ )
+ );
+
+ $fieldset->addField(
+ 'storeId', 'hidden', array(
+ 'required' => true,
+ 'name' => 'storeId',
+ 'value' => $storeId,
+ )
+ );
+
+ $fieldset->addField(
+ 'id', 'hidden', array(
+ 'required' => false,
+ 'name' => 'id',
+ 'value' => $kwixoCategoryMapping->getId(),
+ )
+ );
+ $fieldset->addField(
+ 'category_id', 'hidden', array(
+ 'required' => true,
+ 'name' => 'category_id',
+ 'value' => $categoryId,
+ )
+ );
+
+ $fieldset->addField(
+ 'kwixoCategory_id', 'select', array(
+ 'label' => Mage::Helper('ops/data')->__('Kwixo category'),
+ 'class' => 'required-entry',
+ 'required' => true,
+ 'name' => 'kwixoCategory_id',
+ 'value' => $kwixoCategoryMapping->getKwixoCategoryId(),
+ 'values' => Mage::getModel('ops/source_kwixo_productCategories')->toOptionArray()
+ )
+ );
+
+ $fieldset->addField(
+ 'applysubcat', 'checkbox', array(
+ 'label' => Mage::Helper('ops/data')->__('Apply to sub-categories'),
+ 'name' => 'applysubcat'
+ )
+ );
+
+ $form->setUseContainer(true);
+ $this->setForm($form);
+ return parent::_prepareForm();
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/ClosedTransaction/Warning.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/ClosedTransaction/Warning.php
new file mode 100644
index 0000000..d3a48be
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/ClosedTransaction/Warning.php
@@ -0,0 +1,33 @@
+
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Block_Adminhtml_Sales_Order_Creditmemo_Create_Adjustments_Checkbox
+ *
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Block_Adminhtml_Sales_Order_Creditmemo_ClosedTransaction_Warning
+ extends Mage_Core_Block_Template
+{
+
+ /**
+ * Internal constructor, that is called from real constructor.
+ *
+ *
+ */
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate('ops/sales/order/creditmemo/closed-transaction/warning.phtml');
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/Totals/Checkbox.php b/app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/Totals/Checkbox.php
new file mode 100644
index 0000000..a070d3a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Adminhtml/Sales/Order/Creditmemo/Totals/Checkbox.php
@@ -0,0 +1,33 @@
+
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Block_Adminhtml_Sales_Order_Creditmemo_Create_Adjustments_Checkbox
+ *
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Block_Adminhtml_Sales_Order_Creditmemo_Totals_Checkbox
+ extends Mage_Core_Block_Template
+{
+
+ /**
+ * Internal constructor, that is called from real constructor.
+ *
+ *
+ */
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate('ops/sales/order/creditmemo/totals/checkbox.phtml');
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Alias/List.php b/app/code/community/Netresearch/OPS/Block/Alias/List.php
new file mode 100644
index 0000000..806cb5b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Alias/List.php
@@ -0,0 +1,69 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Block_Alias_List
+ *
+ * @author Thomas Birke
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Block_Alias_List
+ extends Mage_Core_Block_Template
+{
+ public function getAliases()
+ {
+ $aliases = array();
+ $customer = Mage::helper('customer')->getCustomer();
+ if (0 < $customer->getId()) {
+ $aliasesCollection = Mage::helper('ops/alias')->getAliasesForCustomer($customer->getId());
+ foreach ($aliasesCollection as $alias) {
+ $aliases[] = $alias;
+ }
+ }
+ return $aliases;
+ }
+
+ /**
+ * get human readable name of payment method
+ *
+ * @param string $methodCode Code of payment method
+ * @return string Name of payment method
+ */
+ public function getMethodName($methodCode)
+ {
+ $title = '';
+ $instance = Mage::helper('payment')->getMethodInstance($methodCode);
+ if ($instance) {
+ $title = $instance->getTitle();
+ }
+
+ return $title;
+ }
+
+ /**
+ * retrieves the url for deletion the alias
+ *
+ * @param $aliasId - the id of the alias
+ *
+ * @return string - the url for deleting the alias with the given id
+ */
+ public function getAliasDeleteUrl($aliasId)
+ {
+ return Mage::getUrl(
+ 'ops/customer/deleteAlias/',
+ array(
+ 'id' => $aliasId,
+ '_secure' => Mage::app()->getFrontController()->getRequest()->isSecure()
+ )
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Checkout/DeviceFingerprinting.php b/app/code/community/Netresearch/OPS/Block/Checkout/DeviceFingerprinting.php
new file mode 100644
index 0000000..2c00ce2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Checkout/DeviceFingerprinting.php
@@ -0,0 +1,79 @@
+
+ * @copyright 2016 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+
+/**
+ * Netresearch_OPS_Block_Checkout_DeviceFingerprinting
+ *
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @author Christoph Aßmann
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+class Netresearch_OPS_Block_Checkout_DeviceFingerprinting
+ extends Mage_Core_Block_Template
+{
+ /**
+ * @var string
+ */
+ protected $_template = 'ops/checkout/deviceFingerprinting.phtml';
+
+ /**
+ * @return Mage_Core_Block_Abstract
+ */
+ protected function _prepareLayout()
+ {
+ if (Mage::getModel('ops/config')->getDeviceFingerPrinting()) {
+ /** @var Mage_Page_Block_Html_Head $headBlock */
+ $headBlock = $this->getLayout()->getBlock('head');
+ if ($headBlock) {
+ $headBlock->addJs('netresearch/ops/deviceFingerprinting.js');
+ }
+ }
+
+ return parent::_prepareLayout();
+ }
+
+ /**
+ * @return string
+ */
+ protected function _toHtml()
+ {
+ if (!Mage::getModel('ops/config')->getDeviceFingerPrinting()) {
+ return '';
+ }
+
+ return parent::_toHtml();
+ }
+
+ /**
+ * @return string
+ */
+ public function getConsentUrl()
+ {
+ return $this->getUrl('ops/device');
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Checkout/SubscriptionNotice.php b/app/code/community/Netresearch/OPS/Block/Checkout/SubscriptionNotice.php
new file mode 100644
index 0000000..5820ba1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Checkout/SubscriptionNotice.php
@@ -0,0 +1,202 @@
+
+ *
+ *
+ * @method Netresearch_OPS_Block_Checkout_SubscriptionNotice setProfile(Mage_Catalog_Model_Product $product)
+ *
+ */
+class Netresearch_OPS_Block_Checkout_SubscriptionNotice extends Mage_Core_Block_Template
+{
+
+ /**
+ * Returns the quotes nominal items product
+ *
+ * @return Mage_Sales_Model_Recurring_Profile
+ */
+ public function getProfile()
+ {
+ if (!$this->hasData('profile')) {
+ /** @var Mage_Sales_Model_Quote_Item $item */
+ foreach ($this->getQuote()->getAllItems() as $item) {
+ $product = $item->getProduct();
+ if (is_object($product) && $product->isRecurring()
+ && $profile = Mage::getModel('sales/recurring_profile')->importProduct($product)
+ ) {
+ $profile->importQuote($this->getQuote());
+ $profile->importQuoteItem($item);
+ $this->setProfile($profile);
+ break;
+ }
+ }
+ }
+
+ return $this->getData('profile');
+ }
+
+ /**
+ * Get checkout session quote
+ *
+ * @return Mage_Sales_Model_Quote
+ */
+ public function getQuote()
+ {
+ return Mage::getSingleton('checkout/session')->getQuote();
+ }
+
+ /**
+ * Checks wether the recurring profile has a trial period specified
+ *
+ * @return bool
+ */
+ public function hasTrial()
+ {
+ return (bool)$this->getProfile()->getTrialPeriodUnit();
+ }
+
+ /**
+ * Checks wether the recurring profile has an initial fee specified
+ *
+ * @return bool
+ */
+ public function hasInitialFee()
+ {
+ return $this->getProfile()->getInitAmount() > 0;
+ }
+
+ /**
+ * @return string
+ */
+ public function getInitialFeeText()
+ {
+ return $this->__(
+ 'You will be charged an initial amount of %s.',
+ $this->helper('checkout')->formatPrice($this->getProfile()->getInitAmount())
+ );
+ }
+
+ /**
+ * @return string
+ */
+ public function getTrialSubscriptionText()
+ {
+ $profile = $this->getProfile();
+
+ return $this->__(
+ 'A trial subscription will be created. This will charge you %s every %s %s until %s.',
+ $this->helper('checkout')->formatPrice(
+ $profile->getTrialBillingAmount() + $profile->getShippingAmount()
+ ),
+ $profile->getTrialPeriodFrequency(),
+ $profile->getPeriodUnitLabel($profile->getTrialPeriodUnit()),
+ $this->localizeDate($this->getTrialSubscriptionEndDate())
+ );
+ }
+
+ /**
+ * @return string
+ */
+ public function getRegularSubscriptionText()
+ {
+ $profile = $this->getProfile();
+
+ $message = $this->__(
+ 'A subscription will be created. This will charge you %s every %s %s.',
+ $this->helper('checkout')->formatPrice(
+ $profile->getBillingAmount() + $profile->getTaxAmount() + $profile->getShippingAmount()
+ ),
+ $profile->getPeriodFrequency(),
+ $profile->getPeriodUnitLabel($profile->getPeriodUnit())
+ );
+
+ if ($this->getRegularSubscriptionEndDate()) {
+ $message .= $this->__(
+ ' The subscription will end on %s.',
+ $this->localizeDate($this->getRegularSubscriptionEndDate())
+ );
+ }
+ return $message;
+ }
+
+ public function getCancelInformationText()
+ {
+ return $this->__(
+ 'To cancel the subscription, please send an email to the shop owner' .
+ ' or request this by clicking the suspend button on the subscriptions detail view in your customer account.'
+ . ' A link to that page will be displayed on the checkout success page.'
+ );
+ }
+
+ public function displayNotice()
+ {
+ $result = true;
+ if (!$this->getProfile()
+ || $this->getQuote()->getPayment()->getMethod() != Netresearch_OPS_Model_Payment_Recurring_Cc::CODE
+ ) {
+ $result = false;
+ }
+
+ return $result;
+ }
+
+ protected function getTrialSubscriptionEndDate()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag $parameterModel */
+ $parameterModel = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ $enddate = null;
+ $startDate = new DateTime($this->getProfile()->getStartDatetime());
+ $enddate = $parameterModel->calculateEndDate(
+ $startDate, $this->getProfile()->getTrialPeriodUnit(),
+ $this->getProfile()->getTrialPeriodFrequency(), $this->getProfile()->getTrialPeriodMaxCycles()
+ );
+
+ return $enddate;
+ }
+
+ protected function getRegularSubscriptionEndDate()
+ {
+ $parameterModel = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ $enddate = null;
+ if ($this->hasTrial()) {
+ $startDate = $this->getTrialSubscriptionEndDate();
+ } else {
+ $startDate = new DateTime($this->getProfile()->getStartDatetime());
+ }
+ $enddate = $parameterModel->calculateEndDate(
+ $startDate, $this->getProfile()->getPeriodUnit(),
+ $this->getProfile()->getPeriodFrequency(), $this->getProfile()->getPeriodMaxCycles()
+ );
+
+ return $enddate;
+ }
+
+ protected function localizeDate(DateTime $date)
+ {
+ $date = new Zend_Date($date->getTimestamp());
+ return Mage::helper('core')->formatDate($date);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form.php b/app/code/community/Netresearch/OPS/Block/Form.php
new file mode 100644
index 0000000..7779874
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form.php
@@ -0,0 +1,363 @@
+setTemplate(self::FRONTEND_TEMPLATE);
+ }
+
+ /**
+ * get OPS config
+ *
+ * @return Netresearch_Ops_Model_Config
+ */
+ public function getConfig()
+ {
+ if (null === $this->config) {
+ $this->config = Mage::getSingleton('ops/config');
+ }
+
+ return $this->config;
+ }
+
+ /**
+ * @param Netresearch_OPS_Model_Config $config
+ * @return $this
+ */
+ public function setConfig(Netresearch_OPS_Model_Config $config)
+ {
+ $this->config = $config;
+
+ return $this;
+ }
+
+ /**
+ * @return Mage_Sales_Model_Quote
+ */
+ public function getQuote()
+ {
+ $quote = Mage::getSingleton('checkout/session')->getQuote();
+ if (Mage::app()->getStore()->isAdmin()) {
+ $quote = Mage::getSingleton('adminhtml/sales_order_create')->getQuote();
+ }
+
+ return $quote;
+ }
+
+ /**
+ * @return array
+ */
+ public function getDirectDebitCountryIds()
+ {
+ return explode(',', $this->getConfig()->getDirectDebitCountryIds());
+ }
+
+ public function getBankTransferCountryIds()
+ {
+ return explode(',', $this->getConfig()->getBankTransferCountryIds());
+ }
+
+ /**
+ * @param null $storeId
+ * @return string
+ */
+ public function getPSPID($storeId = null)
+ {
+ return Mage::getModel('ops/config')->getPSPID($storeId);
+ }
+
+ /**
+ * @param null $storeId
+ * @param bool $admin
+ * @return string
+ */
+ public function getGenerateHashUrl($storeId = null, $admin = false)
+ {
+ return Mage::getModel('ops/config')->getGenerateHashUrl($storeId, $admin);
+ }
+
+ /**
+ * @return string
+ */
+ public function getValidationUrl()
+ {
+ return Mage::getModel('ops/config')->getValidationUrl();
+ }
+
+ /**
+ * @return array
+ */
+ public function getDirectEbankingBrands()
+ {
+ return explode(',', $this->getConfig()->getDirectEbankingBrands());
+ }
+
+
+ /**
+ * wrapper for Netresearch_OPS_Helper_Data::checkIfUserRegistering
+ *
+ * @return type bool
+ */
+ public function isUserRegistering()
+ {
+ return Mage::Helper('ops/data')->checkIfUserIsRegistering();
+ }
+
+ /**
+ * wrapper for Netresearch_OPS_Helper_Data::checkIfUserRegistering
+ *
+ * @return type bool
+ */
+ public function isUserNotRegistering()
+ {
+ return Mage::Helper('ops/data')->checkIfUserIsNotRegistering();
+ }
+
+ /**
+ * @return string
+ */
+ public function getPmLogo()
+ {
+ return $this->pmLogo;
+ }
+
+ /**
+ * @return array
+ */
+ protected function getFieldMapping()
+ {
+ return $this->getConfig()->getFrontendFieldMapping();
+ }
+
+ /**
+ * @param $mappedFields
+ * @param $key
+ * @param $value
+ * @param $frontendFields
+ *
+ * @return mixed
+ */
+ public function getFrontendValidationFields($mappedFields, $key, $value, $frontendFields)
+ {
+ if (!is_array($mappedFields[$key])) {
+ $frontendFields[$mappedFields[$key]] = $value;
+ } else {
+ foreach ($mappedFields[$key] as $mKey) {
+ $frontendFields[$mKey] = $value;
+ }
+ }
+
+ return $frontendFields;
+ }
+
+ public function getImageForBrand($brand)
+ {
+ $brandName = str_replace(' ', '', $brand);
+ return $this->getSkinUrl('images/ops/alias/brands/'. $brandName .'.png');
+ }
+
+ /**
+ * Function to add the Payment Logo to the according title
+ *
+ * @return string
+ */
+ public function getMethodLabelAfterHtml()
+ {
+ $paymentCode = $this->getMethod()->getCode();
+ $logoValue = Mage::getStoreConfig('payment/' . $paymentCode . '/image');
+ $logoPosition = Mage::getStoreConfig('payment/' . $paymentCode . '/position');
+
+ if ($logoPosition != 'hidden') {
+ if (!empty($logoValue)) {
+ $url = Mage::getBaseUrl('media') . 'ops/paymentLogo/' . $logoValue;
+ } else {
+ $url = Mage::helper('ops/payment')->getPaymentDefaultLogo($paymentCode);
+ }
+
+ return " ";
+ }
+
+ return '';
+ }
+
+ /**
+ * Obtain redirect message.
+ *
+ * @return string
+ */
+ public function getRedirectMessage()
+ {
+ return $this->__('You will be redirected to finalize your payment.');
+ }
+
+ /**
+ * retrieves the alias data for the logged in customer
+ *
+ * @return array | null - array the alias data or null if the customer
+ * is not logged in
+ */
+ protected function getStoredAliasForCustomer()
+ {
+ if (Mage::helper('customer/data')->isLoggedIn()
+ && Mage::getModel('ops/config')->isAliasManagerEnabled($this->getMethodCode())
+ ) {
+ $quote = $this->getQuote();
+ $aliases = Mage::helper('ops/alias')->getAliasesForAddresses(
+ $quote->getCustomer()->getId(), $quote->getBillingAddress(),
+ $quote->getShippingAddress(), $quote->getStoreId()
+ )
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::ACTIVE)
+ ->addFieldToFilter('payment_method', $this->getMethodCode())
+ ->setOrder('created_at', Varien_Data_Collection::SORT_ORDER_DESC);
+
+
+ foreach ($aliases as $key => $alias) {
+ $this->_aliasDataForCustomer[$key] = $alias;
+ }
+ }
+
+ return $this->_aliasDataForCustomer;
+ }
+
+ /**
+ * @param null $storeId
+ * @param bool $admin
+ *
+ * @return string
+ */
+ public function getAliasAcceptUrl($storeId = null, $admin = false)
+ {
+ return Mage::getModel('ops/config')->getAliasAcceptUrl($storeId, $admin);
+ }
+
+ /**
+ * @param null $storeId
+ * @param bool $admin
+ *
+ * @return string
+ */
+ public function getAliasExceptionUrl($storeId = null, $admin = false)
+ {
+ return Mage::getModel('ops/config')->getAliasExceptionUrl($storeId, $admin);
+ }
+
+
+ /**
+ * @param null $storeId
+ *
+ * @return string
+ */
+ public function getAliasGatewayUrl($storeId = null)
+ {
+ return Mage::getModel('ops/config')->getAliasGatewayUrl($storeId);
+ }
+
+ /**
+ *
+ * @param $aliasId
+ *
+ * @return null|string - the card holder either from alias data or
+ * the name from the the user who is logged in, null otherwise
+ */
+ public function getCardHolderName($aliasId)
+ {
+ $cardHolderName = $this->getStoredAliasDataForCustomer($aliasId, 'card_holder');
+ $customerHelper = Mage::helper('customer/data');
+ if ((null === $cardHolderName || 0 === strlen(trim($cardHolderName)))
+ && $customerHelper->isLoggedIn()
+ && Mage::getModel('ops/config')->isAliasManagerEnabled($this->getMethodCode())
+ ) {
+ $cardHolderName = $customerHelper->getCustomerName();
+ }
+
+ return $cardHolderName;
+ }
+
+ /**
+ * @param $aliasId
+ * @return null|string
+ */
+ public function getAliasCardNumber($aliasId)
+ {
+ $aliasCardNumber = $this->getStoredAliasDataForCustomer($aliasId, 'pseudo_account_or_cc_no');
+ if (0 < strlen(trim($aliasCardNumber))) {
+ $aliasCardNumber = Mage::helper('ops/alias')->formatAliasCardNo(
+ $this->getStoredAliasDataForCustomer($aliasId, 'brand'), $aliasCardNumber
+ );
+ }
+
+ return $aliasCardNumber;
+ }
+
+ /**
+ * retrieves single values to given keys from the alias data
+ *
+ * @param $aliasId
+ * @param $key - string the key for the alias data
+ *
+ * @return null|string - null if key is not set in the alias data, otherwise
+ * the value for the given key from the alias data
+ */
+ protected function getStoredAliasDataForCustomer($aliasId, $key)
+ {
+ $returnValue = null;
+ $aliasData = array();
+
+ if (empty($this->_aliasDataForCustomer)) {
+ $aliasData = $this->getStoredAliasForCustomer();
+ } else {
+ $aliasData = $this->_aliasDataForCustomer;
+ }
+
+ if (array_key_exists($aliasId, $aliasData) && $aliasData[$aliasId]->hasData($key)) {
+ $returnValue = $aliasData[$aliasId]->getData($key);
+ }
+
+ return $returnValue;
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Form/Alias.php b/app/code/community/Netresearch/OPS/Block/Form/Alias.php
new file mode 100644
index 0000000..370e03a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/Alias.php
@@ -0,0 +1,55 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Block_Form_Alias
+ *
+ * @author Thomas Birke
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Block_Form_Alias extends Netresearch_OPS_Block_Form
+{
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate('ops/form/alias.phtml');
+ }
+
+ /**
+ * get available aliases for current customer
+ * will return empty array if there is no current user
+ *
+ * @return array|Netresearch_OPS_Model_Mysql4_Alias_Collection
+ */
+ public function getAvailableAliases()
+ {
+ $customer = Mage::helper('customer')->getCustomer();
+ if (0 < $customer->getId()) {
+ $quote = Mage::helper('ops/payment')->getQuote();
+ return Mage::helper('ops/payment')->getAliasesForCustomer($customer->getId(), $quote);
+ }
+ return array();
+ }
+
+ /**
+ * @param $alias
+ * @return string
+ */
+ protected function getHumanReadableAlias($alias)
+ {
+ $helper = Mage::helper('ops');
+ $aliasString = $helper->__('Credit Card Type') . ' ' . $helper->__($alias->getBrand());
+ $aliasString .= ' ' . $helper->__('AccountNo') . ' ' . $helper->__($alias->getPseudoAccountOrCCNo());
+ $aliasString .= ' ' . $helper->__('Expiration Date') . ' ' . $alias->getExpirationDate();
+ return $aliasString;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Form/BankTransfer.php b/app/code/community/Netresearch/OPS/Block/Form/BankTransfer.php
new file mode 100644
index 0000000..a8adcc0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/BankTransfer.php
@@ -0,0 +1,42 @@
+
+ */
+?>
+setTemplate('ops/form/bankTransfer.phtml');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/Cc.php b/app/code/community/Netresearch/OPS/Block/Form/Cc.php
new file mode 100644
index 0000000..8597605
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/Cc.php
@@ -0,0 +1,178 @@
+
+ * @author Thomas Birke
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Block_Form_Cc extends Netresearch_OPS_Block_Form
+{
+
+ protected $_aliasDataForCustomer = array();
+
+ /**
+ * CC Payment Template
+ */
+ const FRONTEND_TEMPLATE = 'ops/form/cc.phtml';
+
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate(self::FRONTEND_TEMPLATE);
+ }
+
+
+ /**
+ * gets all Alias CC brands
+ *
+ * @return array
+ */
+ public function getAliasBrands()
+ {
+ return Mage::getModel('ops/source_cc_aliasInterfaceEnabledTypes')
+ ->getAliasInterfaceCompatibleTypes();
+ }
+
+ /**
+ * @return string
+ */
+ public function getSaveCcBrandUrl()
+ {
+ return Mage::getModel('ops/config')->getSaveCcBrandUrl();
+ }
+
+ /**
+ * @param null $storeId
+ * @param bool $admin
+ *
+ * @return mixed
+ */
+ public function getCcSaveAliasUrl($storeId = null, $admin = false)
+ {
+ return Mage::getModel('ops/config')->getCcSaveAliasUrl($storeId, $admin);
+ }
+
+ /**
+ * checks if the 'alias' payment method (!) is available
+ * no check for customer has aliases here
+ * just a passthrough of the isAvailable of Netresearch_OPS_Model_Payment_Abstract::isAvailable
+ *
+ * @return boolean
+ */
+ public function isAliasPMEnabled()
+ {
+ return Mage::getModel('ops/config')->isAliasManagerEnabled($this->getMethodCode());
+ }
+
+
+ /**
+ * retrieves the alias data for the logged in customer
+ *
+ * @return array | null - array the alias data or null if the customer
+ * is not logged in
+ */
+ protected function getStoredAliasForCustomer()
+ {
+ if (Mage::helper('customer/data')->isLoggedIn()
+ && Mage::getModel('ops/config')->isAliasManagerEnabled($this->getMethodCode())
+ ) {
+ $quote = $this->getQuote();
+ $aliases = Mage::helper('ops/alias')->getAliasesForAddresses(
+ $quote->getCustomer()->getId(), $quote->getBillingAddress(),
+ $quote->getShippingAddress(), $quote->getStoreId()
+ )
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::ACTIVE)
+ ->addFieldToFilter('payment_method', $this->getMethodCode())
+ ->setOrder('created_at', Varien_Data_Collection::SORT_ORDER_DESC);
+
+
+ foreach ($aliases as $key => $alias) {
+ $this->_aliasDataForCustomer[$key] = $alias;
+ }
+ }
+
+ return $this->_aliasDataForCustomer;
+ }
+
+
+
+
+ /**
+ * @param $aliasId
+ * @param $key
+ * @return null|string
+ */
+ public function getExpirationDatePart($aliasId, $key)
+ {
+ $returnValue = null;
+ $expirationDate = $this->getStoredAliasDataForCustomer($aliasId, 'expiration_date');
+ // set expiration date to actual date if no stored Alias is used
+ if ($expirationDate === null) {
+ $expirationDate = date('my');
+ }
+
+ if (0 < strlen(trim($expirationDate))
+ ) {
+ $expirationDateValues = str_split($expirationDate, 2);
+
+ if ($key == 'month') {
+ $returnValue = $expirationDateValues[0];
+ }
+ if ($key == 'year') {
+ $returnValue = $expirationDateValues[1];
+ }
+
+ if ($key == 'complete') {
+ $returnValue = implode('/', $expirationDateValues);
+ }
+ }
+
+ return $returnValue;
+
+ }
+
+
+ /**
+ * the brand of the stored card data
+ *
+ * @param $aliasId
+ *
+ * @return null|string - string if stored card data were found, null otherwise
+ */
+ public function getStoredAliasBrand($aliasId)
+ {
+ return $this->getStoredAliasDataForCustomer($aliasId, 'brand');
+ }
+
+ /**
+ * determines whether the alias hint is shown to guests or not
+ *
+ * @return bool true if alias feature is enabled and display the hint to
+ * guests is enabled
+ */
+ public function isAliasInfoBlockEnabled()
+ {
+ return ($this->isAliasPMEnabled()
+ && Mage::getModel('ops/config')->isAliasInfoBlockEnabled());
+ }
+
+ /**
+ * @return string[]
+ */
+ public function getCcBrands()
+ {
+ return explode(',', $this->getConfig()->getAcceptedCcTypes($this->getMethodCode()));
+ }
+
+ public function checkIfBrandHasAliasInterfaceSupport($alias)
+ {
+ $brand = $this->getStoredAliasBrand($alias);
+ $allowedBrands = $this->getMethod()->getBrandsForAliasInterface();
+
+ return in_array($brand, $allowedBrands);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Form/DirectDebit.php b/app/code/community/Netresearch/OPS/Block/Form/DirectDebit.php
new file mode 100644
index 0000000..bcaf296
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/DirectDebit.php
@@ -0,0 +1,47 @@
+
+ * @author Thomas Birke
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Block_Form_DirectDebit extends Netresearch_OPS_Block_Form
+{
+
+ /**
+ * Backend Payment Template
+ */
+ const TEMPLATE = 'ops/form/directDebit.phtml';
+
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate(self::TEMPLATE);
+ }
+
+ /**
+ * get ids of supported countries
+ *
+ * @return array
+ */
+ public function getDirectDebitCountryIds()
+ {
+ return explode(',', $this->getConfig()->getDirectDebitCountryIds());
+ }
+
+ /**
+ * @return string
+ */
+ public function getSelectedCountryId()
+ {
+ $countryId = $this->getQuote()->getPayment()->getAdditionalInformation('country_id');
+ if (Mage::app()->getStore()->isAdmin()) {
+ $data = $this->getQuote()->getPayment()->getData('ops_directDebit_data');
+ $countryId = $data && array_key_exists('country_id', $data) ? $data['country_id'] : '';
+ }
+ return $countryId;
+
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Form/DirectEbanking.php b/app/code/community/Netresearch/OPS/Block/Form/DirectEbanking.php
new file mode 100644
index 0000000..c4929f0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/DirectEbanking.php
@@ -0,0 +1,42 @@
+
+ */
+?>
+setTemplate('ops/form/directEbanking.phtml');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/Flex.php b/app/code/community/Netresearch/OPS/Block/Form/Flex.php
new file mode 100644
index 0000000..6a26f05
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/Flex.php
@@ -0,0 +1,70 @@
+
+ */
+?>
+setTemplate('ops/form/flex.phtml');
+ }
+
+ /**
+ * get configurable payment methods
+ *
+ * @return string[][]
+ */
+ public function getFlexMethods()
+ {
+ $methods = $this->getMethod()->getConfigData('methods');
+ if (!is_array($methods)) {
+ $methods = unserialize($methods);
+ }
+
+ return $methods;
+ }
+
+ /**
+ * @return boolean
+ */
+ public function isDefaultOptionActive()
+ {
+ return (bool) $this->getMethod()->getConfigData('default');
+ }
+
+ public function getDefaultOptionTitle()
+ {
+ return $this->getMethod()->getConfigData('default_title');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/Ideal.php b/app/code/community/Netresearch/OPS/Block/Form/Ideal.php
new file mode 100644
index 0000000..5d9ab7c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/Ideal.php
@@ -0,0 +1,33 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Block_Form_Ideal
+ extends Netresearch_OPS_Block_Form
+{
+
+ /**
+ * Init OPS payment form
+ *
+ */
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate('ops/form/ideal.phtml');
+ }
+
+ /**
+ * return the ideal issuers
+ *
+ * @return array
+ */
+ public function getIssuers()
+ {
+ return Mage::getModel('ops/payment_iDeal')->getIDealIssuers();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Form/InterSolve.php b/app/code/community/Netresearch/OPS/Block/Form/InterSolve.php
new file mode 100644
index 0000000..40f483e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/InterSolve.php
@@ -0,0 +1,52 @@
+
+ */
+?>
+setTemplate('ops/form/intersolve.phtml');
+ }
+
+ /**
+ *
+ * @return array empty or intersolve Vouchers
+ */
+ public function getInterSolveBrands()
+ {
+ $brands = Mage::getModel('ops/config')->getIntersolveBrands();
+
+ return $brands;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/Kwixo/ApresReception.php b/app/code/community/Netresearch/OPS/Block/Form/Kwixo/ApresReception.php
new file mode 100644
index 0000000..e93d8dd
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/Kwixo/ApresReception.php
@@ -0,0 +1,27 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Block_Form_Kwixo_ApresReception extends Netresearch_OPS_Block_Form
+{
+ const FRONTEND_TEMPLATE = 'ops/form/kwixo/apres_reception.phtml';
+
+ protected $pmLogo = 'images/ops/kwixo/apres_reception.jpg';
+
+ /**
+ * Init OPS payment form
+ *
+ */
+ protected function _construct()
+ {
+ parent::_construct();
+ /** @noinspection PhpUndefinedMethodInspection */
+ $this->setTemplate(self::FRONTEND_TEMPLATE);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/Kwixo/Comptant.php b/app/code/community/Netresearch/OPS/Block/Form/Kwixo/Comptant.php
new file mode 100644
index 0000000..d35de6e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/Kwixo/Comptant.php
@@ -0,0 +1,30 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+
+class Netresearch_OPS_Block_Form_Kwixo_Comptant extends Netresearch_OPS_Block_Form
+{
+ const FRONTEND_TEMPLATE = 'ops/form/kwixo/comptant.phtml';
+
+ protected $pmLogo = 'images/ops/kwixo/comptant.jpg';
+
+ /**
+ * Init OPS payment form
+ *
+ */
+ protected function _construct()
+ {
+ parent::_construct();
+ /** @noinspection PhpUndefinedMethodInspection */
+ $this->setTemplate(self::FRONTEND_TEMPLATE);
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/Kwixo/Credit.php b/app/code/community/Netresearch/OPS/Block/Form/Kwixo/Credit.php
new file mode 100644
index 0000000..47a6735
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/Kwixo/Credit.php
@@ -0,0 +1,28 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+
+class Netresearch_OPS_Block_Form_Kwixo_Credit extends Netresearch_OPS_Block_Form
+{
+ const FRONTEND_TEMPLATE = 'ops/form/kwixo/credit.phtml';
+
+ protected $pmLogo = 'images/ops/kwixo/credit.jpg';
+
+ /**
+ * Init OPS payment form
+ *
+ */
+ protected function _construct()
+ {
+ parent::_construct();
+ /** @noinspection PhpUndefinedMethodInspection */
+ $this->setTemplate(self::FRONTEND_TEMPLATE);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/OpenInvoice.php b/app/code/community/Netresearch/OPS/Block/Form/OpenInvoice.php
new file mode 100644
index 0000000..09f9c37
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/OpenInvoice.php
@@ -0,0 +1,63 @@
+
+ */
+class Netresearch_OPS_Block_Form_OpenInvoice extends Netresearch_OPS_Block_Form
+{
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate('ops/form/openInvoice.phtml');
+ }
+
+ /**
+ * @return string
+ * @see Netresearch_OPS_Model_Payment_OpenInvoice_Abstract::getInvoiceTermsTitle
+ */
+ public function getInvoiceTermsTitle()
+ {
+ return $this->getMethod()->getInvoiceTermsTitle();
+ }
+
+ /**
+ * @return string
+ * @see Netresearch_OPS_Model_Payment_OpenInvoice_Abstract::getInvoiceTermsUrl
+ */
+ public function getInvoiceTermsUrl()
+ {
+ return $this->getMethod()->getInvoiceTermsUrl();
+ }
+
+ /**
+ * @return bool
+ * @see Netresearch_OPS_Model_Payment_OpenInvoice_Abstract::showInvoiceTermsLink
+ */
+ public function showInvoiceTermsLink()
+ {
+ return $this->getMethod()->showInvoiceTermsLink();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Form/OpsId.php b/app/code/community/Netresearch/OPS/Block/Form/OpsId.php
new file mode 100644
index 0000000..1074da5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/OpsId.php
@@ -0,0 +1,17 @@
+
+ * @author Thomas Birke
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Block_Form_OpsId extends Mage_Payment_Block_Form
+{
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->setTemplate('ops/form/opsId.phtml');
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Form/PayPerMail.php b/app/code/community/Netresearch/OPS/Block/Form/PayPerMail.php
new file mode 100644
index 0000000..41fa881
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/PayPerMail.php
@@ -0,0 +1,43 @@
+
+ */
+?>
+setTemplate('ops/form/payPerMail.phtml');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Form/RecurringCc.php b/app/code/community/Netresearch/OPS/Block/Form/RecurringCc.php
new file mode 100644
index 0000000..99a6c7c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Form/RecurringCc.php
@@ -0,0 +1,37 @@
+
+ */
+
+class Netresearch_OPS_Block_Form_RecurringCc extends Netresearch_OPS_Block_Form_Cc
+{
+
+ public function getCcBrands()
+ {
+ return $this->getConfig()->getAcceptedRecurringCcTypes();
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Frauddetection.php b/app/code/community/Netresearch/OPS/Block/Frauddetection.php
new file mode 100644
index 0000000..e560b92
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Frauddetection.php
@@ -0,0 +1,74 @@
+getStoreId();
+ if (true == Mage::getModel('ops/config')->getDeviceFingerPrinting($storeId)
+ && Mage::getSingleton('customer/session')->getData(Netresearch_OPS_Model_Payment_Abstract::FINGERPRINT_CONSENT_SESSION_KEY)) {
+ $html = parent::_toHtml();
+ }
+
+ return $html;
+ }
+
+ /**
+ * get the tracking code application id from config
+ *
+ * @return string
+ */
+ public function getTrackingCodeAid()
+ {
+ return self::TRACKING_CODE_APPLICATION_ID;
+ }
+
+
+ /**
+ * build md5 hash from customer session ID
+ *
+ * @return string
+ */
+ public function getTrackingSid()
+ {
+ $quote = Mage::getSingleton('checkout/type_onepage')->getQuote();
+
+ return md5(Mage::getModel('ops/config')->getPSPID($quote->getStoreId()) . Mage::helper('ops/order')->getOpsOrderId($quote));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Info/Alias.php b/app/code/community/Netresearch/OPS/Block/Info/Alias.php
new file mode 100644
index 0000000..91500b0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/Alias.php
@@ -0,0 +1,32 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Block_Info_Alias
+ *
+ * @author Thomas Birke
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Block_Info_Alias extends Netresearch_OPS_Block_Info_Redirect
+{
+ /**
+ * Init ops payment information block
+ *
+ */
+ protected function _construct()
+ {
+ parent::_construct();
+ /** @noinspection PhpUndefinedMethodInspection */
+ $this->setTemplate('ops/info/cc.phtml');
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Block/Info/Bancontact.php b/app/code/community/Netresearch/OPS/Block/Info/Bancontact.php
new file mode 100644
index 0000000..ada7f24
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/Bancontact.php
@@ -0,0 +1,54 @@
+setTemplate('ops/info/bancontact.phtml');
+ }
+
+
+ public function getDeviceParameter()
+ {
+ return $this->getInfo()->getAdditionalInformation('DEVICE');
+ }
+
+
+ public function getMobileModeParameter()
+ {
+ return $this->getInfo()->getAdditionalInformation('MOBILEMODE');
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Info/Cc.php b/app/code/community/Netresearch/OPS/Block/Info/Cc.php
new file mode 100644
index 0000000..6527764
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/Cc.php
@@ -0,0 +1,43 @@
+setTemplate('ops/info/cc.phtml');
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Block/Info/Flex.php b/app/code/community/Netresearch/OPS/Block/Info/Flex.php
new file mode 100644
index 0000000..7543ace
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/Flex.php
@@ -0,0 +1,55 @@
+
+ */
+?>
+setTemplate('ops/info/flex.phtml');
+ }
+
+
+ /**
+ * @return string
+ */
+ public function getFlexTitle()
+ {
+ /** @noinspection PhpUndefinedMethodInspection */
+ return $this->getMethod()->getInfoInstance()->getAdditionalInformation(
+ Netresearch_OPS_Model_Payment_Flex::INFO_KEY_TITLE
+ );
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Info/OpsId.php b/app/code/community/Netresearch/OPS/Block/Info/OpsId.php
new file mode 100644
index 0000000..2167e32
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/OpsId.php
@@ -0,0 +1,43 @@
+setTemplate('ops/info/opsId.phtml');
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Block/Info/PayPerMail.php b/app/code/community/Netresearch/OPS/Block/Info/PayPerMail.php
new file mode 100644
index 0000000..002c78e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/PayPerMail.php
@@ -0,0 +1,44 @@
+
+ */
+?>
+setTemplate('ops/info/payPerMail.phtml');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Info/RecurringCc.php b/app/code/community/Netresearch/OPS/Block/Info/RecurringCc.php
new file mode 100644
index 0000000..0406f1e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/RecurringCc.php
@@ -0,0 +1,35 @@
+
+ */
+
+class Netresearch_OPS_Block_Info_RecurringCc extends Netresearch_OPS_Block_Info_Cc
+{
+
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/Info/Redirect.php b/app/code/community/Netresearch/OPS/Block/Info/Redirect.php
new file mode 100644
index 0000000..690e5b9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Info/Redirect.php
@@ -0,0 +1,42 @@
+setTemplate('ops/info/redirect.phtml');
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Paypage.php b/app/code/community/Netresearch/OPS/Block/Paypage.php
new file mode 100644
index 0000000..fa2dafa
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Paypage.php
@@ -0,0 +1,41 @@
+setTemplate('ops/paypage.phtml');
+ return $this;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Placeform.php b/app/code/community/Netresearch/OPS/Block/Placeform.php
new file mode 100644
index 0000000..04cee6a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Placeform.php
@@ -0,0 +1,191 @@
+loadByIncrementId($this->getCheckout()->getLastRealOrderId());
+ if ($order && null != $order->getId()) {
+ $methodInstance = $order->getPayment()->getMethodInstance();
+ }
+
+ return $methodInstance;
+ }
+
+ /**
+ * Return order instance with loaded information by increment id
+ *
+ * @return Mage_Sales_Model_Order
+ */
+ protected function _getOrder()
+ {
+ if ($this->getOrder()) {
+ $order = $this->getOrder();
+ } else if ($this->getCheckout()->getLastRealOrderId()) {
+ $order = Mage::getModel('sales/order')->loadByIncrementId($this->getCheckout()->getLastRealOrderId());
+ } else {
+ return null;
+ }
+ return $order;
+ }
+
+ /**
+ * check if payment method is q kwixo one
+ *
+ * @return boolean
+ */
+ public function isKwixoPaymentMethod()
+ {
+ $isKwixoPayment = false;
+ $methodInstance = $this->_getOrder()->getPayment()->getMethodInstance();
+ if ($methodInstance instanceof Netresearch_OPS_Model_Payment_Kwixo_Abstract) {
+ $isKwixoPayment= true;
+ }
+ return $isKwixoPayment;
+ }
+ /**
+ * Get Form data by using ops payment api
+ *
+ * @return array
+ */
+ public function getFormData()
+ {
+ if (null == $this->formFields && $this->_getOrder()
+ && null != $this->_getOrder()->getId()) {
+ $this->formFields = $this->_getApi()->getFormFields($this->_getOrder(), $this->getRequest()->getParams());
+ }
+ return $this->formFields;
+ }
+
+ /**
+ * Getting gateway url
+ *
+ * @return string
+ */
+ public function getFormAction()
+ {
+ $formAction = '';
+
+ // extract variable to ensure php 5.4 compatibility
+ $question = $this->getQuestion();
+
+ if ($this->getRequest()->isPost() || empty($question)) {
+ /** @var Netresearch_OPS_Model_Payment_Abstract $method */
+ $method = $this->_getOrder()->getPayment()->getMethodInstance();
+ $formAction = $method->getFrontendGateWay();
+ } else {
+ $formAction = Mage::getUrl(
+ '*/*/*', array('_secure' => Mage::app()->getFrontController()->getRequest()->isSecure())
+ );
+ }
+
+ return $formAction;
+ }
+
+ /**
+ * @return bool|null
+ */
+ public function hasMissingParams()
+ {
+ if (null === $this->_getOrder()) {
+ return null;
+ }
+ if (null === $this->hasMissingParams) {
+ $this->hasMissingParams = $this->_getApi()
+ ->hasFormMissingParams(
+ $this->_getOrder(),
+ $this->getRequest()->getParams(),
+ $this->getFormData()
+ );
+ }
+ return $this->hasMissingParams;
+ }
+
+ /**
+ * @return string
+ */
+ public function getQuestion()
+ {
+ if (null === $this->question && $this->_getOrder() && null != $this->_getOrder()->getId()) {
+ $this->question = $this->_getApi()->getQuestion();
+ }
+ return $this->question;
+ }
+
+ /**
+ * @return array
+ */
+ public function getQuestionedFormFields()
+ {
+ if (is_null($this->missingFormFields) && $this->_getOrder() && !is_null($this->_getOrder()->getId())) {
+ $this->missingFormFields = $this->_getApi()
+ ->getQuestionedFormFields($this->_getOrder());
+ }
+
+ return $this->missingFormFields;
+ }
+
+ /**
+ * @return bool
+ */
+ public function isIframeTarget()
+ {
+ return $this->getConfig()->getConfigData('template') === Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_IFRAME;
+ }
+
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/Placeform3dsecure.php b/app/code/community/Netresearch/OPS/Block/Placeform3dsecure.php
new file mode 100644
index 0000000..0f63b12
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/Placeform3dsecure.php
@@ -0,0 +1,42 @@
+_getOrder()) {
+ return base64_decode($this->_getOrder()->getPayment()->getAdditionalInformation('HTML_ANSWER'));
+ }
+ return null;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/RetryPayment.php b/app/code/community/Netresearch/OPS/Block/RetryPayment.php
new file mode 100644
index 0000000..4d73353
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/RetryPayment.php
@@ -0,0 +1,103 @@
+
+ */
+class Netresearch_OPS_Block_RetryPayment extends Netresearch_OPS_Block_Placeform
+{
+
+ protected $_order = null;
+
+ protected function _getApi()
+ {
+ return $this->_getOrder()->getPayment()->getMethodInstance();
+ }
+
+ protected function _getOrder()
+ {
+ if (null === $this->_order) {
+ $opsOrderId = $this->getOrderId();
+ $this->_order = Mage::helper('ops/order')->getOrder($opsOrderId);
+ }
+
+ return $this->_order;
+ }
+
+ /**
+ * Getting placeform url
+ *
+ * @return string
+ */
+ public function getFormAction()
+ {
+ $formAction = Mage::getUrl(
+ '*/*/updatePaymentAndPlaceForm',
+ array('_secure' => Mage::app()->getFrontController()->getRequest()->isSecure())
+ );
+
+ return $formAction;
+ }
+
+ /**
+ * Getting cancel url
+ *
+ * @return string
+ */
+ public function getCancelUrl()
+ {
+ $formAction = Mage::getUrl(
+ '*/*/cancel',
+ array('_secure' => Mage::app()->getFrontController()->getRequest()->isSecure())
+ );
+
+ return $formAction;
+ }
+
+ public function getOrderId()
+ {
+ return $this->getRequest()->getParam('orderID');
+ }
+
+ /**
+ * Returns the orders billing address
+ *
+ * @return Mage_Sales_Model_Order_Address
+ */
+ public function getBillingAddress()
+ {
+ return $this->_getOrder()->getBillingAddress();
+ }
+
+ /**
+ * Returns the orders shipping address or false in case of a virtual order
+ *
+ * @return Mage_Sales_Model_Order_Address|false
+ */
+ public function getShippingAddress()
+ {
+ return $this->_getOrder()->getShippingAddress();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/RetryPayment/Methods.php b/app/code/community/Netresearch/OPS/Block/RetryPayment/Methods.php
new file mode 100644
index 0000000..19d4e80
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/RetryPayment/Methods.php
@@ -0,0 +1,80 @@
+
+ */
+class Netresearch_OPS_Block_RetryPayment_Methods extends Mage_Checkout_Block_Onepage_Payment_Methods
+{
+ protected $quote = null;
+
+ /**
+ * Get Order ID from Url
+ *
+ * @return null
+ * @throws Exception
+ */
+ public function getQuote()
+ {
+ if (null === $this->quote) {
+ $opsOrderId = $this->getRequest()->getParam('orderID');
+ $order = Mage::helper('ops/order')-> getOrder($opsOrderId);
+ $quote = Mage::getModel('sales/quote')->load($order->getQuoteId());
+
+ if ($quote->getId()) {
+ $quote->setIsActive(1)
+ ->save();
+ Mage::getSingleton('checkout/session')
+ ->replaceQuote($quote);
+ }
+
+ $this->quote = $quote;
+ }
+
+ return $this->quote;
+ }
+
+ /**
+ * Retrieve available payment methods - filtered by OPS methods
+ *
+ * @return array
+ */
+ public function getMethods()
+ {
+ $methods = $this->getData('methods');
+ if ($methods === null) {
+ $methods = parent::getMethods();
+ foreach ($methods as $key => $method) {
+ if (!$method instanceof Netresearch_OPS_Model_Payment_Abstract) {
+ $this->_assignMethod($method);
+ unset($methods[$key]);
+ }
+ }
+ $this->setData('methods', $methods);
+ }
+
+ return $methods;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Brand.php b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Brand.php
new file mode 100644
index 0000000..b10ad10
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Brand.php
@@ -0,0 +1,53 @@
+
+ */
+
+class Netresearch_OPS_Block_System_Config_Form_Field_Brand
+ extends Mage_Adminhtml_Block_System_Config_Form_Field_Array_Abstract
+{
+ public function __construct()
+ {
+ $this->addColumn(
+ 'brand', array(
+ 'label' => Mage::helper('ops')->__('Brand'),
+ 'style' => 'width:120px',
+ )
+ );
+ $this->addColumn(
+ 'value', array(
+ 'label' => Mage::helper('ops')->__('Title'),
+ 'style' => 'width:120px',
+ )
+ );
+ $this->_addAfter = false;
+ $this->_addButtonLabel = Mage::helper('ops')->__('Add Brand');
+ parent::__construct();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Image.php b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Image.php
new file mode 100644
index 0000000..cb022a1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Image.php
@@ -0,0 +1,87 @@
+
+ */
+class Netresearch_OPS_Block_System_Config_Form_Field_Image
+ extends Mage_Adminhtml_Block_System_Config_Form_Field_Image
+{
+
+ /**
+ * Return element html code
+ *
+ * @return string
+ */
+ public function getElementHtml()
+ {
+ $html = '';
+ $url = $this->_getUrl();
+
+ if (!empty($url)) {
+ $value = $this->getData('value');
+ $html = ''
+ . ' '
+ . ' ';
+ }
+ $this->setData('class', 'input-file');
+ $html .= Varien_Data_Form_Element_Abstract::getElementHtml();
+ $html .= $this->_getDeleteCheckbox();
+
+ return $html;
+ }
+
+ /**
+ * Get image preview url
+ *
+ * @return string
+ */
+ protected function _getUrl()
+ {
+ $url = $this->getData('value');
+ $config = $this->getData('field_config');
+
+ if (!empty($url)) {
+ /* @var $config Varien_Simplexml_Element */
+ if (!empty($config->base_url)) {
+ $el = $config->descend('base_url');
+ $urlType = empty($el['type']) ? 'link' : (string)$el['type'];
+ $url = Mage::getBaseUrl($urlType) . (string)$config->base_url . '/' . $url;
+ }
+ } else {
+ preg_match("/groups\[([a-zA-Z_]*)/", $this->getData('name'), $imageName);
+
+ if (isset($imageName[1])) {
+ $url = Mage::helper('ops/payment')->getPaymentDefaultLogo($imageName[1]);
+ }
+ }
+
+ return $url;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Method.php b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Method.php
new file mode 100644
index 0000000..30a92f9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/Method.php
@@ -0,0 +1,59 @@
+
+ */
+
+class Netresearch_OPS_Block_System_Config_Form_Field_Method extends Mage_Adminhtml_Block_System_Config_Form_Field_Array_Abstract
+{
+ public function __construct()
+ {
+ $this->addColumn(
+ 'title', array(
+ 'label' => Mage::helper('ops')->__('Title'),
+ 'style' => 'width:80px',
+ 'class' => 'required-entry'
+ )
+ );
+ $this->addColumn(
+ 'pm', array(
+ 'label' => 'PM',
+ 'style' => 'width:80px',
+ 'class' => 'required-entry'
+ )
+ );
+ $this->addColumn(
+ 'brand', array(
+ 'label' => 'BRAND',
+ 'style' => 'width:80px',
+ )
+ );
+
+ $this->_addAfter = false;
+ $this->_addButtonLabel = Mage::helper('ops')->__('Add Method');
+ parent::__construct();
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/RecurringActive.php b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/RecurringActive.php
new file mode 100644
index 0000000..49e1ac7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/Form/Field/RecurringActive.php
@@ -0,0 +1,55 @@
+
+ */
+?>
+
+ element = $('" . $element->getHtmlId() . "');
+ Event.observe(element, 'change', function(){
+ if(element.value == 1){
+ $('ops_recurring_cc_active_comment').style.display = 'block';
+ } else {
+ $('ops_recurring_cc_active_comment').style.display = 'none';
+ }
+ });
+ ";
+
+ return $html . $javascript;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/Kwixoconfiguration.php b/app/code/community/Netresearch/OPS/Block/System/Config/Kwixoconfiguration.php
new file mode 100644
index 0000000..dd67f91
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/Kwixoconfiguration.php
@@ -0,0 +1,35 @@
+addData(
+ array(
+ 'fieldset_label' => $fieldset->getLegend(),
+ )
+ );
+
+ return $this->toHtml();
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/Mode.php b/app/code/community/Netresearch/OPS/Block/System/Config/Mode.php
new file mode 100644
index 0000000..0e8e0d6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/Mode.php
@@ -0,0 +1,32 @@
+
+ element = $('".$element->getHtmlId()."');
+ Event.observe(element, 'change', function(){
+ if(element.selectedOptions[0].value != '".$element->getValue()."'){
+ $('ops_mode_comment').style.display = 'block';
+ } else {
+ $('ops_mode_comment').style.display = 'none';
+ }
+ });
+ ";
+
+ return $html.$javascript;
+ }
+
+
+}
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/PaymentForm.php b/app/code/community/Netresearch/OPS/Block/System/Config/PaymentForm.php
new file mode 100644
index 0000000..7ec6b7d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/PaymentForm.php
@@ -0,0 +1,47 @@
+
+ */
+class Netresearch_Ops_Block_System_Config_PaymentForm
+ extends Mage_Adminhtml_Block_System_Config_Form
+{
+
+ /**
+ * Add Payment Logo Image Renderer to renderer types
+ *
+ * @return array
+ */
+ protected function _getAdditionalElementTypes()
+ {
+ $elementTypes = parent::_getAdditionalElementTypes();
+ $elementTypes['paymentLogo'] = Mage::getConfig()->getBlockClassName('ops/system_config_form_field_image');
+
+ return $elementTypes;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Block/System/Config/Support.php b/app/code/community/Netresearch/OPS/Block/System/Config/Support.php
new file mode 100644
index 0000000..5872d8b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Block/System/Config/Support.php
@@ -0,0 +1,170 @@
+getOriginalData();
+ $this->addData(
+ array(
+ 'fieldset_label' => $fieldset->getLegend(),
+ )
+ );
+ return $this->toHtml();
+ }
+
+ /**
+ * get extension version
+ *
+ * @return string
+ */
+ public function getExtensionVersion()
+ {
+ return (string)Mage::getConfig()->getNode('modules')->children()->Netresearch_OPS->version;
+ }
+
+ /**
+ * get Magento version
+ *
+ * @return string
+ */
+ public function getMageVersion()
+ {
+ $mageVersion = Mage::getVersion();
+ if (is_callable('Mage::getEdition')) {
+ $mageVersion = Mage::getEdition() . ' ' . $mageVersion;
+ }
+ return $mageVersion;
+ }
+
+ /**
+ * get support mail address
+ *
+ * @return string
+ */
+ public function getSupportMail()
+ {
+ $mail = $this->getConfig()->getConfigData('support_mail');
+ if (false !== strpos($mail, '@')) {
+ return $mail;
+ }
+ }
+
+ /**
+ * if we have a link to documentation
+ *
+ * @return int
+ */
+ public function hasDocumentation()
+ {
+ return strlen($this->getDocLinkDe() . $this->getDocLinkEn());
+ }
+
+ /**
+ * get URL of German documentation
+ *
+ * @return string
+ */
+ public function getDocLinkDe()
+ {
+ $link = $this->getConfig()->getConfigData('doc_link_de');
+ if (false !== strpos($link, '://')) {
+ return $link;
+ }
+ }
+
+ /**
+ * get URL of English documentation
+ *
+ * @return string
+ */
+ public function getDocLinkEn()
+ {
+ $link = $this->getConfig()->getConfigData('doc_link_en');
+ if (false !== strpos($link, '://')) {
+ return $link;
+ }
+ }
+
+ /**
+ * if we have link to a FAQ
+ *
+ * @return int
+ */
+ public function hasFaq()
+ {
+ return strlen($this->getFaqLinkDe() . $this->getFaqLinkEn());
+ }
+ /**
+ * get URL of German FAQ
+ *
+ * @return string
+ */
+ public function getFaqLinkDe()
+ {
+ $link = $this->getConfig()->getConfigData('faq_link_de');
+ if (false !== strpos($link, '://')) {
+ return $link;
+ }
+
+ }
+
+ /**
+ * get URL of English FAQ
+ *
+ * @return string
+ */
+ public function getFaqLinkEn()
+ {
+ $link = $this->getConfig()->getConfigData('faq_link_en');
+ if (false !== strpos($link, '://')) {
+ return $link;
+ }
+ }
+
+ /**
+ * if we use a prefix for parameter ORDERID
+ *
+ * @return bool
+ */
+ public function hasDevPrefix()
+ {
+ return 0 < strlen($this->getDevPrefix());
+ }
+
+ /**
+ * get prefix for parameter ORDERID
+ *
+ * @return string
+ */
+ public function getDevPrefix()
+ {
+ return $this->getConfig()->getConfigData('devprefix');
+ }
+
+ /**
+ * get link for ops.log download action
+ *
+ * @return string
+ */
+ public function getLogDownloadLink()
+ {
+ return $this->getUrl($this->_downloadLogPath);
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Controller/Abstract.php b/app/code/community/Netresearch/OPS/Controller/Abstract.php
new file mode 100644
index 0000000..b7e946e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Controller/Abstract.php
@@ -0,0 +1,181 @@
+
+ * @author André Herrn
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Controller_Abstract extends Mage_Core_Controller_Front_Action
+{
+ protected function getQuote()
+ {
+ return $this->_getCheckout()->getQuote();
+ }
+
+ /**
+ * Get checkout session namespace
+ *
+ * @return Mage_Checkout_Model_Session
+ */
+ protected function _getCheckout()
+ {
+ return Mage::getSingleton('checkout/session');
+ }
+
+ protected function getConfig()
+ {
+ return Mage::getModel('ops/config');
+ }
+
+ /**
+ * Return order instance loaded by increment id'
+ *
+ * @return Mage_Sales_Model_Order
+ */
+
+ /**
+ * Return order instance loaded by increment id'
+ *
+ * @param $opsOrderId
+ *
+ * @return Mage_Sales_Model_Order
+ */
+
+ protected function _getOrder($opsOrderId = null)
+ {
+ if (empty($this->_order)) {
+ if (null === $opsOrderId) {
+ $opsOrderId = $this->getRequest()->getParam('orderID');
+ }
+ $this->_order = Mage::helper('ops/order')->getOrder($opsOrderId);
+ }
+
+ return $this->_order;
+ }
+
+ /**
+ * Get singleton with Checkout by OPS Api
+ *
+ * @return Netresearch_OPS_Model_Payment_Abstract
+ */
+ protected function _getApi()
+ {
+ $api = Mage::getSingleton('checkout/session')->getQuote()->getPayment()->getMethodInstance();
+ if (null != $this->getRequest()->getParam('orderID')) {
+ $api = $this->_getOrder()->getPayment()->getMethodInstance();
+ }
+
+ return $api;
+ }
+
+ /**
+ * get payment helper
+ *
+ * @return Netresearch_OPS_Helper_Payment
+ */
+ protected function getPaymentHelper()
+ {
+ return Mage::helper('ops/payment');
+ }
+
+ /**
+ * get direct link helper
+ *
+ * @return Netresearch_OPS_Helper_Directlink
+ */
+ protected function getDirectlinkHelper()
+ {
+ return Mage::helper('ops/directlink');
+ }
+
+ protected function getSubscriptionHelper()
+ {
+ return Mage::helper('ops/subscription');
+ }
+
+ /**
+ * Validation of incoming OPS data
+ *
+ * @param mixed[]|bool $paramOverwrite array of parameters with SHASIGN to validate instead of standard request
+ * parameters
+ *
+ * @return bool
+ */
+ protected function _validateOPSData($paramOverwrite = false)
+ {
+ $helper = Mage::helper('ops');
+
+ $params = $paramOverwrite ? : $this->getRequest()->getParams();
+
+ if ($this->getSubscriptionHelper()->isSubscriptionFeedback($params)) {
+ $profile = $this->getSubscriptionHelper()->getProfileForSubscription($params['orderID']);
+ if (!$profile->getId()) {
+ $this->_getCheckout()->addError($this->__('Subscription is not valid'));
+ $helper->log(
+ $helper->__(
+ "Incoming Ingenico ePayments Feedback\n\nRequest Path: %s\nParams: %s\n\nSubscription not valid\n",
+ $this->getRequest()->getPathInfo(),
+ serialize($this->getRequest()->getParams())
+ )
+ );
+ return false;
+ }
+ $storeId = $profile->getStoreId();
+ } else {
+ $order = $this->_getOrder();
+ if (!$order->getId()) {
+ $helper->log(
+ $helper->__(
+ "Incoming Ingenico ePayments Feedback\n\nRequest Path: %s\nParams: %s\n\nOrder not valid\n",
+ $this->getRequest()->getPathInfo(),
+ serialize($this->getRequest()->getParams())
+ )
+ );
+ $this->_getCheckout()->addError($this->__('Order is not valid'));
+ return false;
+ }
+ $storeId = $order->getStoreId();
+ }
+
+ //remove custom responseparams, because they are not hashed by Ingenico ePayments
+ if ($this->getConfig()->getConfigData('template') == Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_IFRAME
+ && array_key_exists('IFRAME', $params)
+ ) {
+ unset($params['IFRAME']);
+ }
+
+ $secureKey = $this->getConfig()->getShaInCode($storeId);
+ $secureSet = $this->getPaymentHelper()->getSHAInSet($params, $secureKey);
+
+ $helper->log(
+ $helper->__(
+ "Incoming Ingenico ePayments Feedback\n\nRequest Path: %s\nParams: %s\n",
+ $this->getRequest()->getPathInfo(),
+ serialize($this->getRequest()->getParams())
+ )
+ );
+
+ if (Mage::helper('ops/payment')->shaCryptValidation($secureSet, $params['SHASIGN']) !== true) {
+ $this->_getCheckout()->addError($this->__('Hash is not valid'));
+ return false;
+ }
+
+ return true;
+ }
+
+ public function isJsonRequested($params)
+ {
+ if (array_key_exists('RESPONSEFORMAT', $params) && $params['RESPONSEFORMAT'] == 'JSON') {
+ return true;
+ }
+ return false;
+ }
+
+ public function getSubscriptionManager()
+ {
+ return Mage::getModel('ops/subscription_manager');
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Address.php b/app/code/community/Netresearch/OPS/Helper/Address.php
new file mode 100644
index 0000000..7f4c2e0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Address.php
@@ -0,0 +1,181 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Address extends Mage_Core_Helper_Abstract
+{
+
+ const OPTION_A_ADDITION_1 = 'A_Addition_to_address_1';
+ const OPTION_A_STREET_NAME = 'A_Street_name_1';
+ const OPTION_A_HOUSE_NUMBER = 'A_House_number_1';
+ const OPTION_A_ADDITION_2 = 'A_Addition_to_address_2';
+ const OPTION_B_ADDITION_1 = 'B_Addition_to_address_1';
+ const OPTION_B_STREET_NAME = 'B_Street_name';
+ const OPTION_B_HOUSE_NUMBER = 'B_House_number';
+ const OPTION_B_ADDITION_2 = 'B_Addition_to_address_2';
+
+
+ /**
+ * split street into street name, number and additional street information
+ *
+ * @param string $street
+ *
+ * @return array
+ */
+ public function splitStreet($street)
+ {
+ $result = array(
+ 'street_name' => $street,
+ 'street_number' => '',
+ 'supplement' => ''
+ );
+
+ if (preg_match($this->getStreetSplitter(), $street, $matches)) {
+
+ // Pattern A
+ if (isset($matches[self::OPTION_A_STREET_NAME]) && !empty($matches[self::OPTION_A_STREET_NAME])) {
+
+ $result['street_name'] = trim($matches[self::OPTION_A_STREET_NAME]);
+
+ if (isset($matches[self::OPTION_A_HOUSE_NUMBER]) && !empty($matches[self::OPTION_A_HOUSE_NUMBER])) {
+ $result['street_number'] = trim($matches[self::OPTION_A_HOUSE_NUMBER]);
+ }
+
+ if (isset($matches[self::OPTION_A_ADDITION_1]) && isset($matches[self::OPTION_A_ADDITION_2])) {
+ $result['supplement'] = trim($matches[self::OPTION_A_ADDITION_1] . ' '
+ . $matches[self::OPTION_A_ADDITION_2]
+ );
+ }
+
+ return $result ;
+
+ // Pattern B
+ } elseif (isset($matches[self::OPTION_B_STREET_NAME]) && !empty($matches[self::OPTION_B_STREET_NAME])) {
+
+ $result['street_name'] = trim($matches[self::OPTION_B_STREET_NAME]);
+
+ if (isset($matches[self::OPTION_B_HOUSE_NUMBER]) && !empty($matches[self::OPTION_B_HOUSE_NUMBER])) {
+ $result['street_number'] = trim($matches[self::OPTION_B_HOUSE_NUMBER]);
+ }
+
+ if (isset($matches[self::OPTION_B_ADDITION_1]) && isset($matches[self::OPTION_B_ADDITION_2])) {
+ $result['supplement'] = trim($matches[self::OPTION_B_ADDITION_1] . ' '
+ . $matches[self::OPTION_B_ADDITION_2]
+ );
+ }
+
+
+ return $result;
+ }
+ }
+
+ return $result;
+ }
+
+ /**
+ * Regex to analyze addresses and split them into the groups Street Name, House Number and Additional Information
+ * Pattern A is addition number street addition
+ * Pattern B is addition street number addition
+ *
+ * @return string
+ */
+ protected function getStreetSplitter()
+ {
+ return "/\\A\\s*
+ (?:
+ #########################################################################
+ # Option A: [] #
+ # [] #
+ #########################################################################
+ (?:
+ (?P.*?)
+ ,\\s*
+ )?
+ # Addition to address 1
+ (?:No\\.\\s*)?
+ (?P
+ \\pN+[a-zA-Z]?
+ (?:\\s*[-\\/\\pP]\\s*\\pN+[a-zA-Z]?)*
+ )
+ # House number
+ \\s*,?\\s*
+ (?P
+ (?:[a-zA-Z]\\s*|\\pN\\pL{2,}\\s\\pL)
+ \\S[^,#]*?
+ (?
+ (?!\\s)
+ .*?
+ )
+ )?
+ # Addition to address 2
+ |
+ #########################################################################
+ # Option B: [] #
+ # [] #
+ #########################################################################
+ (?:
+ (?P.*?)
+ ,\\s*
+ (?=.*[,\\/])
+ )?
+ # Addition to address 1
+ (?!\\s*No\\.)
+ (?P
+ \\S\\s*\\S
+ (?:
+ [^,#]
+ (?!\\b\\pN+\\s)
+ )*?
+ (?
+ \\pN+\\s*-?[a-zA-Z]?
+ (?:
+ \\s*[-\\/\\pP]?\\s*\\pN+
+ (?:\\s*[\\-a-zA-Z])?
+ )*|
+ [IVXLCDM]+
+ (?!.*\\b\\pN+\\b)
+ )
+ (?
+ (?!\\s)
+ .*?
+ )
+ )?
+ # Addition to address 2
+ )
+ \\s*\\Z/x";
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Alias.php b/app/code/community/Netresearch/OPS/Helper/Alias.php
new file mode 100644
index 0000000..3076451
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Alias.php
@@ -0,0 +1,514 @@
+getAdminSession()->getUser()) {
+ return 0 < $this->getAdminSession()->getUser()->getUserId();
+ }
+ return false;
+ }
+
+ /**
+ * PM value is not used for payments with Alias Manager
+ *
+ * @param Mage_Sales_Model_Quote_Payment|null Payment
+ *
+ * @return null
+ */
+ public function getOpsCode($payment = null)
+ {
+ return $payment;
+ }
+
+ /**
+ * BRAND value is not used for payments with Alias Manager
+ *
+ * @param Mage_Sales_Model_Quote_Payment|null Payment
+ *
+ * @return null
+ */
+ public function getOpsBrand($payment = null)
+ {
+ return $payment;
+ }
+
+ /**
+ * saves the alias if customer is logged in (and want to create an alias)
+ *
+ * @param $params
+ *
+ * @return Netresearch_OPS_Model_Alias | null
+ */
+ public function saveAlias($params)
+ {
+ $quote = null;
+ $aliasModel = null;
+ Mage::helper('ops')->log('aliasData ' . Zend_Json::encode(Mage::helper('ops/data')->clearMsg($params)));
+ if (array_key_exists('Alias_OrderId', $params) && is_numeric($params['Alias_OrderId'])) {
+ $quote = Mage::getModel('sales/quote')->load($params['Alias_OrderId']);
+ }
+
+ if ($quote instanceof Mage_Sales_Model_Quote
+ && $quote->getPayment()
+ && Mage::getSingleton('checkout/type_onepage')->getCheckoutMethod()
+ != Mage_Checkout_Model_Type_Onepage::METHOD_GUEST
+ && (array_key_exists('Alias_StorePermanently', $params) && 'Y' == $params['Alias_StorePermanently'])
+ ) {
+
+ // alias does not exist -> create a new one if requested
+ if (null != $quote && $quote->getPayment()) {
+ // create new alias
+ $aliasModel = $this->saveNewAliasFromQuote($quote, $params);
+ $quote->getPayment()->setAdditionalInformation(
+ 'opsAliasId', $aliasModel->getId()
+ );
+ $quote->getPayment()->save();
+ }
+ } elseif (array_key_exists('orderid', $params)) {
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::helper('ops/order')->getOrder($params['orderid']);
+ $aliasModel = $this->saveNewAliasFromOrder($order, $params);
+ $order->getPayment()->setAdditionalInformation('opsAliasId', $aliasModel->getId());
+ }
+
+ return $aliasModel;
+ }
+
+ /**
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ */
+ protected function deleteAlias(Mage_Sales_Model_Quote $quote)
+ {
+ $customerId = $quote->getCustomer()->getId();
+ $billingAddressHash = $this->generateAddressHash(
+ $quote->getBillingAddress()
+ );
+ $shippingAddressHash = $this->generateAddressHash(
+ $quote->getShippingAddress()
+ );
+ $aliasModel = Mage::getModel('ops/alias');
+ $aliasCollection = $aliasModel->getCollection()
+ ->addFieldToFilter('customer_id', $customerId)
+ ->addFieldToFilter('billing_address_hash', $billingAddressHash)
+ ->addFieldToFilter('shipping_address_hash', $shippingAddressHash)
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::PENDING)
+ ->addFieldToFilter('store_id', array(array('eq' => $quote->getStoreId()), array('null' => true)))
+ ->setOrder('created_at', 'DESC')
+ ->setPageSize(1);
+ $aliasCollection->load();
+ foreach ($aliasCollection as $alias) {
+ $alias->delete();
+ }
+ }
+
+ protected function saveNewAliasFromQuote(Mage_Sales_Model_Quote $quote, $params)
+ {
+ $customerId = $quote->getCustomer()->getId();
+ $billingAddressHash = $this->generateAddressHash(
+ $quote->getBillingAddress()
+ );
+ $shippingAddressHash = $this->generateAddressHash(
+ $quote->getShippingAddress()
+ );
+
+
+ $aliasData = array();
+ $aliasData['customer_id'] = $customerId;
+ $aliasData['alias'] = $params['Alias_AliasId'];
+ $aliasData['expiration_date'] = $params['Card_ExpiryDate'];
+ $aliasData['billing_address_hash'] = $billingAddressHash;
+ $aliasData['shipping_address_hash'] = $shippingAddressHash;
+ $aliasData['brand'] = $params['Card_Brand'];
+ $aliasData['payment_method'] = $quote->getPayment()->getMethod();
+ $aliasData['pseudo_account_or_cc_no'] = $params['Card_CardNumber'];
+ $aliasData['state'] = Netresearch_OPS_Model_Alias_State::PENDING;
+ $aliasData['store_id'] = $quote->getStoreId();
+
+ if (array_key_exists('Card_CardHolderName', $params)) {
+ $aliasData['card_holder'] = $params['Card_CardHolderName'];
+ }
+
+ $aliasModel = $this->persistAlias($aliasData);
+
+ return $aliasModel;
+ }
+
+ public function saveNewAliasFromOrder(Mage_Sales_Model_Order $order, $params)
+ {
+ $customerId = $order->getCustomerId();
+ $billingAddressHash = $this->generateAddressHash(
+ $order->getBillingAddress()
+ );
+ $shippingAddressHash = $this->generateAddressHash(
+ $order->getShippingAddress()
+ );
+
+ $aliasData = array();
+ $aliasData['customer_id'] = $customerId;
+ $aliasData['alias'] = $params['alias'];
+ $aliasData['expiration_date'] = $params['ed'];
+ $aliasData['billing_address_hash'] = $billingAddressHash;
+ $aliasData['shipping_address_hash'] = $shippingAddressHash;
+ $aliasData['brand'] = $params['brand'];
+ $aliasData['payment_method'] = $order->getPayment()->getMethod();
+ $aliasData['pseudo_account_or_cc_no'] = $params['cardno'];
+ $aliasData['state'] = Netresearch_OPS_Model_Alias_State::ACTIVE;
+ $aliasData['store_id'] = $order->getStoreId();
+ $aliasData['card_holder'] = $params['cn'];
+
+ $aliasModel = $this->persistAlias($aliasData);
+
+ return $aliasModel;
+ }
+
+
+ public function persistAlias(array $aliasParams)
+ {
+ /** @var Netresearch_OPS_Model_Alias $aliasModel */
+ $aliasModel = Mage::getModel('ops/alias')->load($aliasParams['alias'], 'alias');
+
+ Mage::helper('ops')->log(
+ 'saving alias' . Zend_Json::encode($aliasModel->getData())
+ );
+
+ $aliasModel->addData($aliasParams);
+ $aliasModel->save();
+
+ return $aliasModel;
+ }
+
+ /**
+ * generates hash from address data
+ *
+ * @param Mage_Customer_Model_Address_Abstract $address the address data to hash
+ *
+ * @returns string hash of address
+ */
+ public function generateAddressHash(Mage_Customer_Model_Address_Abstract $address) {
+ /** @var Netresearch_OPS_Helper_Payment $opsHelper */
+ $opsHelper = Mage::helper('ops/payment');
+ $addressString = $address->getFirstname();
+ $addressString .= $address->getMiddlename();
+ $addressString .= $address->getLastname();
+ $addressString .= $address->getCompany();
+ $street = $address->getStreetFull();
+ if (is_array($street)) {
+ $street = implode('', $street);
+ }
+ $addressString .= $street;
+ $addressString .= $address->getPostcode();
+ $addressString .= $address->getCity();
+ $addressString .= $address->getCountryId();
+
+ return hash($opsHelper->getCryptMethod(), $addressString);
+ }
+
+ /**
+ * retrieves the aliases for a given customer
+ *
+ * @param int $customerId
+ * @param Mage_Sales_Model_Quote
+ *
+ * @return Netresearch_OPS_Model_Mysql4_Alias_Collection - collection
+ * of aliases for the given customer
+ */
+ public function getAliasesForCustomer(
+ $customerId, Mage_Sales_Model_Quote $quote = null
+ )
+ {
+ $billingAddressHash = null;
+ $shippingAddressHash = null;
+ $storeId = null;
+ if (null !=($quote)) {
+ $billingAddressHash = $this->generateAddressHash(
+ $quote->getBillingAddress()
+ );
+ $shippingAddressHash = $this->generateAddressHash(
+ $quote->getShippingAddress()
+ );
+ $storeId = $quote->getStoreId();
+ }
+ return Mage::getModel('ops/alias')
+ ->getAliasesForCustomer(
+ $customerId, $billingAddressHash, $shippingAddressHash, $storeId
+ );
+ }
+
+ /**
+ * if alias is valid for address
+ *
+ * @param int $customerId
+ * @param string $alias
+ * @param Mage_Sales_Model_Quote_Address $billingAddress
+ * @param Mage_Sales_Model_Quote_Address $shippingAddress
+ * @param int $storeId
+ *
+ * @return boolean
+ */
+ public function isAliasValidForAddresses(
+ $customerId, $alias, $billingAddress, $shippingAddress, $storeId = null
+ )
+ {
+ $aliasCollection = $this->getAliasesForAddresses(
+ $customerId, $billingAddress, $shippingAddress, $storeId
+ )
+ ->addFieldToFilter('alias', $alias)
+ ->setPageSize(1);
+ return (1 == $aliasCollection->getSize());
+ }
+
+ /**
+ * get aliases that are allowed for customer with given addresses
+ *
+ * @param int $customerId Id of customer
+ * @param Mage_Sales_Model_Quote_Address $billingAddress billing address
+ * @param Mage_Sales_Model_Quote_Address $shippingAddress shipping address
+ * @param int $storeId
+ *
+ * @return Netresearch_OPS_Model_Mysql4_Alias_Collection
+ */
+ public function getAliasesForAddresses(
+ $customerId, $billingAddress, $shippingAddress, $storeId = null
+ )
+ {
+ $billingAddressHash = $this->generateAddressHash($billingAddress);
+ $shippingAddressHash = $this->generateAddressHash($shippingAddress);
+ return Mage::getModel('ops/alias')->getCollection()
+ ->addFieldToFilter('customer_id', $customerId)
+ ->addFieldToFilter('billing_address_hash', $billingAddressHash)
+ ->addFieldToFilter('shipping_address_hash', $shippingAddressHash)
+ ->addFieldToFilter('store_id', array(array('eq' => $storeId), array('null' => true)));
+ }
+
+ /**
+ * formats the pseudo cc number in a brand specific format
+ * supported brand (so far):
+ * - MasterCard
+ * - Visa
+ * - American Express
+ * - Diners Club
+ *
+ * @param $brand - the cc brand we need to format the pseudo cc number
+ * @param $aliasCcNo - the pseudo cc number itself
+ *
+ * @return string - the formatted pseudo cc number
+ */
+ public function formatAliasCardNo($brand, $aliasCcNo)
+ {
+
+ if (in_array(strtolower($brand), array('visa', 'mastercard'))) {
+ $aliasCcNo = implode(' ', str_split($aliasCcNo, 4));
+ }
+ if (in_array(strtolower($brand), array('american express', 'diners club', 'maestrouk'))) {
+ $aliasCcNo = str_replace('-', ' ', $aliasCcNo);
+ }
+
+ return strtoupper($aliasCcNo);
+ }
+
+ /**
+ * saves the alias and if given the cvc to the payment information
+ *
+ * @param Mage_Payment_Model_Info $payment - the payment which should be updated
+ * @param array $aliasData - the data we will update
+ * @param boolean $userIsRegistering - is registering method in checkout
+ * @param boolean $paymentSave - is it necessary to save the payment afterwards
+ */
+ public function setAliasToPayment(
+ Mage_Payment_Model_Info $payment,
+ array $aliasData,
+ $userIsRegistering = false,
+ $paymentSave = false
+ )
+ {
+ if (array_key_exists('alias_aliasid', $aliasData) && 0 < strlen(trim($aliasData['alias_aliasid']))) {
+ $payment->setAdditionalInformation('alias', trim($aliasData['alias_aliasid']));
+ $payment->setAdditionalInformation('userIsRegistering', $userIsRegistering);
+ if (array_key_exists('card_cvc', $aliasData)) {
+ $payment->setAdditionalInformation('cvc', $aliasData['card_cvc']);
+ $this->setCardHolderToAlias($payment->getQuote(), $aliasData);
+ }
+
+ if ( array_key_exists('method', $aliasData)) {
+ $alias = Mage::getModel('ops/alias')->load($aliasData['alias_aliasid'], 'alias');
+ $alias->setPaymentMethod($aliasData['method']);
+ $alias->save();
+ }
+
+ $payment->setDataChanges(true);
+ if ($paymentSave === true) {
+ $payment->save();
+ }
+ } else {
+ Mage::helper('ops/data')->log('did not save alias due to empty alias');
+ Mage::helper('ops/data')->log(serialize($aliasData));
+ }
+ }
+
+ protected function setCardHolderToAlias($quote, $aliasData)
+ {
+ $customerId = $quote->getCustomerId();
+ $billingAddressHash = $this->generateAddressHash($quote->getBillingAddress());
+ $shippingAddressHash = $this->generateAddressHash($quote->getShippingAddress());
+ $oldAlias = Mage::getModel('ops/alias')->getCollection()
+ ->addFieldToFilter('customer_id', $customerId)
+ ->addFieldToFilter('billing_address_hash', $billingAddressHash)
+ ->addFieldToFilter('shipping_address_hash', $shippingAddressHash)
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::ACTIVE)
+ ->addFieldToFilter('store_id', array(array('eq' => $quote->getStoreId()), array('null' => true)))
+ ->getFirstItem();
+ // and if so update this alias with alias data from alias gateway
+ if (is_numeric($oldAlias->getId()) && null === $oldAlias->getCardHolder()
+ && array_key_exists('Card_CardHolderName', $aliasData)
+ ) {
+ $oldAlias->setCardHolder($aliasData['Card_CardHolderName']);
+ $oldAlias->save();
+ }
+ }
+
+ /**
+ * set the last pending alias to active and remove other aliases for customer based on address
+ *
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param Mage_Sales_Model_Order|null $order
+ * @param bool $saveSalesObjects
+ */
+ public function setAliasActive(
+ Mage_Sales_Model_Quote $quote,
+ Mage_Sales_Model_Order $order = null,
+ $saveSalesObjects = false
+ )
+ {
+ if (null === $quote->getPayment()->getAdditionalInformation('userIsRegistering')
+ || false == $quote->getPayment()->getAdditionalInformation('userIsRegistering')
+ ) {
+ $aliasesToDelete = Mage::helper('ops/alias')->getAliasesForAddresses(
+ $quote->getCustomer()->getId(), $quote->getBillingAddress(), $quote->getShippingAddress()
+ )
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::ACTIVE);
+ $lastPendingAlias = Mage::helper('ops/alias')->getAliasesForAddresses(
+ $quote->getCustomer()->getId(),
+ $quote->getBillingAddress(),
+ $quote->getShippingAddress(),
+ $quote->getStoreId()
+ )
+ ->addFieldToFilter('alias', $quote->getPayment()->getAdditionalInformation('alias'))
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::PENDING)
+ ->setOrder('created_at', Varien_Data_Collection::SORT_ORDER_DESC)
+ ->getFirstItem();
+ if (0 < $lastPendingAlias->getId()) {
+ foreach ($aliasesToDelete as $alias) {
+ $alias->delete();
+ }
+ $lastPendingAlias->setState(Netresearch_OPS_Model_Alias_State::ACTIVE);
+ $lastPendingAlias->setPaymentMethod($order->getPayment()->getMethod());
+ $lastPendingAlias->save();
+ }
+ } else {
+ $this->setAliasToActiveAfterUserRegisters($order, $quote);
+ }
+ $this->cleanUpAdditionalInformation($order->getPayment(), false, $saveSalesObjects);
+ $this->cleanUpAdditionalInformation($quote->getPayment(), false, $saveSalesObjects);
+ }
+
+ public function setAliasToActiveAfterUserRegisters(
+ Mage_Sales_Model_Order $order, Mage_Sales_Model_Quote $quote
+ )
+ {
+ if (true == $quote->getPayment()->getAdditionalInformation('userIsRegistering')
+ ) {
+ $customerId = $order->getCustomerId();
+ $billingAddressHash = $this->generateAddressHash(
+ $quote->getBillingAddress()
+ );
+ $shippingAddressHash = $this->generateAddressHash(
+ $quote->getShippingAddress()
+ );
+ $aliasId = $quote->getPayment()->getAdditionalInformation(
+ 'opsAliasId'
+ );
+ if (is_numeric($aliasId) && 0 < $aliasId) {
+ $alias = Mage::getModel('ops/alias')->getCollection()
+ ->addFieldToFilter(
+ 'alias', $quote->getPayment()->getAdditionalInformation('alias')
+ )
+ ->addFieldToFilter(
+ 'billing_address_hash', $billingAddressHash
+ )
+ ->addFieldToFilter(
+ 'shipping_address_hash', $shippingAddressHash
+ )
+ ->addFieldToFilter('store_id', array('eq' => $quote->getStoreId()))
+ ->getFirstItem();
+
+ $alias->setState(Netresearch_OPS_Model_Alias_State::ACTIVE);
+ $alias->setPaymentMethod($order->getPayment()->getMethod());
+ $alias->setCustomerId($customerId);
+ $alias->save();
+ }
+ }
+ }
+
+ /**
+ * cleans up the stored cvc and storedOPSId
+ *
+ * @param Mage_Sales_Model_Quote_Payment || Mage_Sales_Model_Order_Payment $payment
+ * @param bool $cvcOnly
+ * @param bool $savePayment
+ *
+ */
+ public function cleanUpAdditionalInformation($payment, $cvcOnly = false, $savePayment = false)
+ {
+ if (is_array($payment->getAdditionalInformation())
+ && array_key_exists('cvc', $payment->getAdditionalInformation())
+ ) {
+ $payment->unsAdditionalInformation('cvc');
+ }
+
+ if ($cvcOnly === false && is_array($payment->getAdditionalInformation())
+ && array_key_exists('storedOPSId', $payment->getAdditionalInformation())
+ ) {
+ $payment->unsAdditionalInformation('storedOPSId');
+ }
+
+ /* OGNH-7: seems not to needed anymore since payment and quote is saved after this call,
+ otherwise admin payments will fail */
+ if ($savePayment) {
+ $payment->save();
+ }
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Api.php b/app/code/community/Netresearch/OPS/Helper/Api.php
new file mode 100644
index 0000000..6af1e42
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Api.php
@@ -0,0 +1,126 @@
+
+ * @author Sebastian Ertner
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Api extends Mage_Core_Helper_Abstract
+{
+
+ protected $configModel = null;
+
+
+ /**
+ * @param $status - one of the fedd back status
+ *
+ * @throws Mage_Core_Exception - in case the status is not known
+ * @return string - the route for redirect
+ */
+ public function getRedirectRouteFromStatus($status)
+ {
+ $route = null;
+ $configModel = $this->getConfigModel();
+ if ($this->isAcceptStatus($status)) {
+ $route = $configModel->getAcceptRedirectRoute();
+ }
+ if ($this->isCancelStatus($status)) {
+ $route = $configModel->getCancelRedirectRoute();
+ }
+ if ($this->isDeclineStatus($status)) {
+ $route = $configModel->getDeclineRedirectRoute();
+ }
+ if ($this->isExceptionStatus($status)) {
+ $route = $configModel->getExceptionRedirectRoute();
+ }
+
+ // in case none of the cases above match then the status is not known
+ if (null === $route) {
+ Mage::throwException('invalid status provided');
+ }
+
+ return $route;
+ }
+
+
+ /**
+ * config getter
+ *
+ * @return Netresearch_OPS_Model_Config
+ */
+ protected function getConfigModel()
+ {
+ if (null === $this->configModel) {
+ $this->configModel = Mage::getModel('ops/config');
+ }
+ return $this->configModel;
+ }
+
+ /**
+ * determine if the status is known as accepted status
+ *
+ * @param $status - the status
+ *
+ * @return bool - true if the status is known as accept status, false otherwise
+ */
+ protected function isAcceptStatus($status)
+ {
+ return in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT
+ )
+ );
+ }
+
+ /**
+ * determine if the status is known as canceled status
+ *
+ * @param $status - the status
+ *
+ * @return bool - true if the status is known as canceled status, false otherwise
+ */
+ protected function isCancelStatus($status)
+ {
+ return in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_CANCEL
+ )
+ );
+ }
+
+ /**
+ * determine if the status is known as declined status
+ *
+ * @param $status - the status
+ *
+ * @return bool - true if the status is known as declined status, false otherwise
+ */
+ protected function isDeclineStatus($status)
+ {
+ return in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_DECLINE
+ )
+ );
+ }
+
+ /**
+ * determine if the status is known as exception status
+ *
+ * @param $status - the status
+ *
+ * @return bool - true if the status is known as exception status, false otherwise
+ */
+ protected function isExceptionStatus($status)
+ {
+ return in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_EXCEPTION
+ )
+ );
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Creditcard.php b/app/code/community/Netresearch/OPS/Helper/Creditcard.php
new file mode 100644
index 0000000..e726417
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Creditcard.php
@@ -0,0 +1,79 @@
+
+ * @category Netresearch
+ * @package ${MODULENAME}
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Helper_Creditcard extends Netresearch_OPS_Helper_Payment_DirectLink_Request
+{
+
+ protected $aliasHelper = null;
+
+ /**
+ * @param Netresearch_OPS_Helper_Alias $aliasHelper
+ */
+ public function setAliasHelper($aliasHelper)
+ {
+ $this->aliasHelper = $aliasHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Alias
+ */
+ public function getAliasHelper()
+ {
+ if (null === $this->aliasHelper) {
+ $this->aliasHelper = Mage::helper('ops/alias');
+ }
+ return $this->aliasHelper;
+ }
+
+
+ /**
+ * @param Mage_Sales_Model_Quote $quote
+ * @param array $requestParams
+ * @return $this
+ */
+ public function handleAdminPayment(Mage_Sales_Model_Quote $quote, $requestParams)
+ {
+ return $this;
+ }
+
+ protected function getPaymentSpecificParams(Mage_Sales_Model_Quote $quote)
+ {
+ $alias = $quote->getPayment()->getAdditionalInformation('alias');
+ if (null === $alias && $this->getDataHelper()->isAdminSession()) {
+ $alias = $this->getAliasHelper()->getAlias($quote);
+ }
+ $saveAlias = Mage::getModel('ops/alias')->load($alias, 'alias')->getId();
+ $params = array (
+ 'ALIAS' => $alias,
+ 'ALIASPERSISTEDAFTERUSE' => $saveAlias ? 'Y' : 'N',
+ );
+ if ($this->getConfig()->getCreditDebitSplit($quote->getStoreId())) {
+ $params['CREDITDEBIT'] = 'C';
+ }
+ if (is_numeric($quote->getPayment()->getAdditionalInformation('cvc'))) {
+ $params['CVC'] = $quote->getPayment()->getAdditionalInformation('cvc');
+ }
+ $requestParams3ds = array();
+ if ($this->getConfig()->get3dSecureIsActive() && false == $this->getDataHelper()->isAdminSession()) {
+ $requestParams3ds = array(
+ 'FLAG3D' => 'Y',
+ 'WIN3DS' => Netresearch_OPS_Model_Payment_Abstract::OPS_DIRECTLINK_WIN3DS,
+ 'LANGUAGE' => Mage::app()->getLocale()->getLocaleCode(),
+ 'HTTP_ACCEPT' => '*/*',
+ 'HTTP_USER_AGENT' => 'Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)',
+ 'ACCEPTURL' => $this->getConfig()->getAcceptUrl(),
+ 'DECLINEURL' => $this->getConfig()->getDeclineUrl(),
+ 'EXCEPTIONURL' => $this->getConfig()->getExceptionUrl(),
+ );
+ }
+ $params = array_merge($params, $requestParams3ds);
+ return $params;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Data.php b/app/code/community/Netresearch/OPS/Helper/Data.php
new file mode 100644
index 0000000..cc28c50
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Data.php
@@ -0,0 +1,193 @@
+
+ * @author André Herrn
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Data extends Mage_Core_Helper_Abstract
+{
+ const LOG_FILE_NAME = 'ops.log';
+
+ /**
+ * Returns config model
+ *
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig()
+ {
+ return Mage::getSingleton('ops/config');
+ }
+
+ /**
+ * Replace all dots or any content following and including plus ("+") and minus ("-") signs.
+ * @return string
+ */
+ public function getModuleVersionString()
+ {
+ $version = Mage::getConfig()->getNode('modules/Netresearch_OPS/version');
+ $plainversion = preg_replace('/\.|[+-].+$/', '', $version);
+ return 'IG1X' . $plainversion;
+ }
+
+ /**
+ * Checks if logging is enabled and if yes, logs given message to logfile
+ *
+ * @param string $message
+ * @param int $level
+ */
+ public function log($message, $level = null)
+ {
+ $separator = "\n"."===================================================================";
+ $message = $this->clearMsg($message);
+ if ($this->getConfig()->shouldLogRequests()) {
+ Mage::log($message.$separator, $level, self::LOG_FILE_NAME);
+ }
+ }
+
+ /**
+ * Returns full path to ops.log
+ */
+ public function getLogPath()
+ {
+ return Mage::getBaseDir('log'). DIRECTORY_SEPARATOR . self::LOG_FILE_NAME;
+ }
+
+
+ /**
+ * deletes certain keys from the message which is going to logged
+ *
+ * @param $message - the message
+ *
+ * @return array - the cleared message
+ */
+ public function clearMsg($message)
+ {
+ if (is_array($message)) {
+ $keysToBeDeleted = array('cvc', 'CVC');
+ foreach ($keysToBeDeleted as $keyToDelete) {
+ if (array_key_exists($keyToDelete, $message)) {
+ unset($message[$keyToDelete]);
+ }
+ }
+ }
+ if (is_string($message)) {
+ $message = preg_replace('/"CVC":".*"(,)/i', '', $message);
+ $message = preg_replace('/"CVC":".*"/i', '', $message);
+ $message = preg_replace('/"CVC".*"[A-Z]*";/', '', $message);
+ $message = preg_replace('/"CVC":".*"(})/i', '}', $message);
+ }
+ return $message;
+ }
+
+ public function redirect($url)
+ {
+ Mage::app()->getResponse()->setRedirect($url);
+ Mage::app()->getResponse()->sendResponse();
+ }
+
+ /**
+ * Redirects to the given order and prints some notice output
+ *
+ * @param int $orderId
+ * @param string $message
+ * @return void
+ */
+ public function redirectNoticed($orderId, $message)
+ {
+ Mage::getSingleton('core/session')->addNotice($message);
+ $this->redirect(
+ Mage::getUrl('*/sales_order/view', array('order_id' => $orderId))
+ );
+ }
+
+ public function getStatusText($statusCode)
+ {
+ $translationOrigin = "STATUS_".$statusCode;
+ $translationResult = $this->__($translationOrigin);
+ if ($translationOrigin != $translationResult):
+ return $translationResult. " ($statusCode)";
+ else:
+ return $statusCode;
+ endif;
+ }
+
+ public function getAmount($amount)
+ {
+ return round($amount * 100);
+ }
+
+ public function getAdminSession()
+ {
+ return Mage::getSingleton('admin/session');
+ }
+
+ public function isAdminSession()
+ {
+ if ($this->getAdminSession()->getUser()) {
+ return 0 < $this->getAdminSession()->getUser()->getUserId() || $this->getAdminSession()->isLoggedIn();
+ }
+ return false;
+ }
+
+ /*
+ * check if user is registering or not
+ */
+ public function checkIfUserIsRegistering()
+ {
+ $isRegistering = false;
+ $checkoutMethod = Mage::getSingleton('checkout/session')->getQuote()->getCheckoutMethod();
+ if ($checkoutMethod === Mage_Sales_Model_Quote::CHECKOUT_METHOD_REGISTER
+ || $checkoutMethod === Mage_Sales_Model_Quote::CHECKOUT_METHOD_LOGIN_IN
+ ) {
+ $isRegistering = true;
+ }
+ return $isRegistering;
+
+ }
+
+ /*
+ * check if user is registering or not
+ */
+ public function checkIfUserIsNotRegistering()
+ {
+ $isRegistering = false;
+ $checkoutMethod = Mage::getSingleton('checkout/session')->getQuote()->getCheckoutMethod();
+ if ($checkoutMethod === Mage_Sales_Model_Quote::CHECKOUT_METHOD_REGISTER) {
+ $isRegistering = true;
+ }
+ return $isRegistering;
+
+ }
+
+ /**
+ * Trigger sending order confirmation and invoice emails when Magento does not:
+ * - "authorization" after return from gateway (order emails)
+ * - "authorization+capture" (order or invoice emails)
+ *
+ * @param Mage_Sales_Model_Abstract $document
+ * @return Mage_Sales_Model_Abstract
+ * @throws Exception
+ */
+ public function sendTransactionalEmail(Mage_Sales_Model_Abstract $document)
+ {
+ if ($document instanceof Mage_Sales_Model_Order) {
+
+ if (!$document->getEmailSent() && $document->getCanSendNewEmailFlag()) {
+ $document->sendNewOrderEmail();
+ }
+
+ } elseif ($document instanceof Mage_Sales_Model_Order_Invoice) {
+
+ if (!$document->getEmailSent() && Mage::getModel('ops/config')->getSendInvoice()) {
+ $document->sendEmail();
+ }
+
+ }
+
+ return $document;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Debitcard.php b/app/code/community/Netresearch/OPS/Helper/Debitcard.php
new file mode 100644
index 0000000..1c756ad
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Debitcard.php
@@ -0,0 +1,21 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Helper_Debitcard extends Netresearch_OPS_Helper_Creditcard
+{
+ protected function getPaymentSpecificParams(Mage_Sales_Model_Quote $quote)
+ {
+ $params = parent::getPaymentSpecificParams($quote);
+ if ($this->getConfig()->getCreditDebitSplit($quote->getStoreId())) {
+ $params['CREDITDEBIT'] = 'D';
+ }
+ return $params;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/DirectDebit.php b/app/code/community/Netresearch/OPS/Helper/DirectDebit.php
new file mode 100644
index 0000000..9c85fe7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/DirectDebit.php
@@ -0,0 +1,150 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Helper_DirectDebit extends Netresearch_OPS_Helper_Payment_DirectLink_Request
+{
+
+ protected $dataHelper = null;
+
+ protected $quoteHelper = null;
+
+ protected $orderHelper = null;
+
+ protected $customerHelper = null;
+
+
+ /**
+ * sets the data helper
+ *
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ */
+ public function setDataHelper(Netresearch_OPS_Helper_Data $dataHelper)
+ {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ /**
+ * gets the data helper
+ *
+ * @return Netresearch_OPS_Helper_Data
+ */
+ public function getDataHelper()
+ {
+ if (null === $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+
+ /**
+ * sets the quote helper
+ *
+ * @param Netresearch_OPS_Helper_Quote $quoteHelper
+ */
+ public function setQuoteHelper(Netresearch_OPS_Helper_Quote $quoteHelper)
+ {
+ $this->quoteHelper = $quoteHelper;
+ }
+
+ /**
+ * gets the quote helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getQuoteHelper()
+ {
+ if (null === $this->quoteHelper) {
+ $this->quoteHelper = Mage::helper('ops/quote');
+ }
+
+ return $this->quoteHelper;
+ }
+
+ /**
+ * sets the order helper
+ *
+ * @param Netresearch_OPS_Helper_Order $orderHelper
+ */
+ public function setOrderHelper(Netresearch_OPS_Helper_Order $orderHelper)
+ {
+ $this->orderHelper = $orderHelper;
+ }
+
+ /**
+ * gets the order helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getOrderHelper()
+ {
+ if (null === $this->orderHelper) {
+ $this->orderHelper = Mage::helper('ops/order');
+ }
+
+ return $this->orderHelper;
+ }
+
+ /**
+ * sets the customer helper
+ *
+ * @param Mage_Core_Helper_Abstract $customerHelper
+ */
+ public function setCustomerHelper(Mage_Core_Helper_Abstract $customerHelper)
+ {
+ $this->customerHelper = $customerHelper;
+ }
+
+ /**
+ * gets the customer helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getCustomerHelper()
+ {
+ if (null === $this->customerHelper) {
+ $this->customerHelper = Mage::helper('customer/data');
+ }
+
+ return $this->customerHelper;
+ }
+
+ /**
+ * @param Mage_Sales_Model_Quote $quote
+ * @param array $requestParams
+ * @return Netresearch_OPS_Helper_DirectDebit
+ */
+ public function handleAdminPayment(Mage_Sales_Model_Quote $quote, $requestParams)
+ {
+ return $this;
+ }
+
+
+ /**
+ * @param Mage_Sales_Model_Quote $quote
+ * @return array
+ */
+ protected function getPaymentSpecificParams(Mage_Sales_Model_Quote $quote)
+ {
+ $alias = $quote->getPayment()->getAdditionalInformation('alias');
+ $saveAlias = Mage::getModel('ops/alias')->load($alias, 'alias')->getId();
+
+ $paymentMethod = 'Direct Debits ' . $quote->getPayment()->getAdditionalInformation('country_id');
+ $params = array (
+ 'ALIAS' => $alias,
+ 'ALIASPERSISTEDAFTERUSE' => $saveAlias ? 'Y' : 'N',
+ 'PM' => $paymentMethod,
+ 'BRAND' => $paymentMethod
+ );
+
+ return $params;
+ }
+}
+
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Directlink.php b/app/code/community/Netresearch/OPS/Helper/Directlink.php
new file mode 100644
index 0000000..24886df
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Directlink.php
@@ -0,0 +1,262 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Directlink extends Mage_Core_Helper_Abstract
+{
+ /**
+ * Creates Transactions for directlink activities
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param int $transactionID - persistent transaction id
+ * @param int $subPayID - identifier for each transaction
+ * @param array $arrInformation - add dynamic data
+ * @param string $typename - name for the transaction exp.: refund
+ * @param string $comment - order comment
+ *
+ * @return Netresearch_OPS_Helper_Directlink $this
+ */
+ public function directLinkTransact($order,$transactionID, $subPayID,
+ $arrInformation = array(), $typename, $comment, $closed = 0)
+ {
+ $payment = $order->getPayment();
+ $payment->setTransactionId($transactionID."/".$subPayID);
+ $payment->setParentTransactionId($transactionID);
+ $payment->setIsTransactionClosed($closed);
+ $payment->setTransactionAdditionalInfo($arrInformation, null);
+ return $this;
+ }
+
+ /**
+ * Checks if there is an active transaction for a special order for special
+ * type
+ *
+ * @param string $type - refund, capture etc.
+ * @param int $orderID
+ * @return bol success
+ */
+ public function checkExistingTransact($type, $orderID)
+ {
+ $transaction = Mage::getModel('sales/order_payment_transaction')
+ ->getCollection()
+ ->addAttributeToFilter('order_id', $orderID)
+ ->addAttributeToFilter('txn_type', $type)
+ ->addAttributeToFilter('is_closed', 0)
+ ->getLastItem();
+
+ return ($transaction->getTxnId()) ? true : false;
+ }
+
+ /**
+ * get transaction type for given OPS status
+ *
+ * @param string $status
+ *
+ * @return string
+ */
+ public function getTypeForStatus($status)
+ {
+ switch ($status) {
+ case Netresearch_OPS_Model_Status::REFUNDED :
+ case Netresearch_OPS_Model_Status::REFUND_PENDING:
+ case Netresearch_OPS_Model_Status::REFUND_UNCERTAIN :
+ case Netresearch_OPS_Model_Status::REFUND_REFUSED :
+ case Netresearch_OPS_Model_Status::REFUNDED_OK :
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_TRANSACTION_TYPE;
+ case Netresearch_OPS_Model_Status::PAYMENT_REQUESTED :
+ case Netresearch_OPS_Model_Status::PAYMENT_PROCESSED_BY_MERCHANT :
+ case Netresearch_OPS_Model_Status::PAYMENT_PROCESSING:
+ case Netresearch_OPS_Model_Status::PAYMENT_UNCERTAIN:
+ case Netresearch_OPS_Model_Status::PAYMENT_IN_PROGRESS:
+ case Netresearch_OPS_Model_Status::PAYMENT_REFUSED:
+ case Netresearch_OPS_Model_Status::PAYMENT_DECLINED_BY_ACQUIRER:
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_TRANSACTION_TYPE;
+ case Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED: //Void finished
+ case Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED_OK:
+ case Netresearch_OPS_Model_Status::DELETION_WAITING:
+ case Netresearch_OPS_Model_Status::DELETION_UNCERTAIN:
+ case Netresearch_OPS_Model_Status::DELETION_REFUSED:
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_VOID_TRANSACTION_TYPE;
+ case Netresearch_OPS_Model_Status::PAYMENT_DELETED:
+ case Netresearch_OPS_Model_Status::PAYMENT_DELETION_PENDING:
+ case Netresearch_OPS_Model_Status::PAYMENT_DELETION_UNCERTAIN:
+ case Netresearch_OPS_Model_Status::PAYMENT_DELETION_REFUSED:
+ case Netresearch_OPS_Model_Status::PAYMENT_DELETION_OK:
+ case Netresearch_OPS_Model_Status::DELETION_HANDLED_BY_MERCHANT:
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_DELETE_TRANSACTION_TYPE;
+ }
+ }
+
+ /**
+ * Process Direct Link Feedback to do: Capture, De-Capture and Refund
+ *
+ * @param Mage_Sales_Model_Order $order Order
+ * @param array $params Request params
+ *
+ * @return void
+ */
+ public function processFeedback($order, $params)
+ {
+ Mage::getModel('ops/response_handler')->processResponse($params, $order->getPayment()->getMethodInstance());
+ $order->getPayment()->save();
+ }
+
+ /**
+ * Get the payment transaction by PAYID and Operation
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param int $payId
+ * @param string $operation
+ *
+ * @return Mage_Sales_Model_Order_Payment_Transaction
+ *
+ * @throws Mage_Core_Exception
+ */
+ public function getPaymentTransaction($order, $payId, $operation)
+ {
+ $helper = Mage::helper('ops');
+ $transactionCollection = Mage::getModel('sales/order_payment_transaction')
+ ->getCollection()
+ ->addAttributeToFilter('txn_type', $operation)
+ ->addAttributeToFilter('is_closed', 0)
+ ->addAttributeToFilter('order_id', $order->getId());
+ if ($payId != '') {
+ $transactionCollection->addAttributeToFilter('parent_txn_id', $payId);
+ }
+
+ if ($transactionCollection->getSize()>1 || $transactionCollection->getSize() == 0) {
+ $errorMsq = $helper->__(
+ "Warning, transaction count is %s instead of 1 for the Payid '%s', order '%s' and Operation '%s'.",
+ $transactionCollection->getSize(),
+ $payId,
+ $order->getId(),
+ $operation
+ );
+ $helper->log($errorMsq);
+ Mage::throwException($errorMsq);
+ }
+
+ if ($transactionCollection->getSize() == 1) {
+ $transaction = $transactionCollection->getLastItem();
+ $transaction->setOrderPaymentObject($order->getPayment());
+ return $transaction;
+ }
+ }
+
+
+ /**
+ * Check if there are payment transactions for an order and an operation
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param string $authorization
+ *
+ * @return boolean
+ */
+ public function hasPaymentTransactions($order, $operation)
+ {
+ $transactionCollection = Mage::getModel('sales/order_payment_transaction')
+ ->getCollection()
+ ->addAttributeToFilter('txn_type', $operation)
+ ->addAttributeToFilter('is_closed', 0)
+ ->addAttributeToFilter('order_id', $order->getId());
+
+ return (0 < $transactionCollection->getSize());
+ }
+
+ /**
+ * validate incoming and internal amount value format and convert it to float
+ *
+ * @param string
+ * @return float
+ */
+ public function formatAmount($amount)
+ {
+ // Avoid quotes added somewhere unknown
+ if (preg_match("/^[\"']([0-9-\..,-]+)[\"']$/i", $amount, $matches)) {
+ Mage::helper('ops')->log(
+ "Warning in formatAmount: Found quotes around amount in '" . var_export($amount, true) . "'"
+ );
+ $amount = $matches[1];
+ }
+
+ return number_format($amount, 2);
+ }
+
+ /**
+ * determine if the current OPS request is valid
+ *
+ * @param array $transactions Iteratable of Mage_Sales_Model_Order_Payment_Transaction
+ * @param Mage_Sales_Model_Order $order
+ * @param array $opsRequestParams
+ *
+ * @return boolean
+ */
+ public function isValidOpsRequest(
+ $openTransaction,
+ Mage_Sales_Model_Order $order,
+ $opsRequestParams
+ )
+ {
+ if ($this->getTypeForStatus($opsRequestParams['STATUS']) == Netresearch_OPS_Model_Payment_Abstract::OPS_DELETE_TRANSACTION_TYPE) {
+ return false;
+ }
+
+ $requestedAmount = null;
+ if (array_key_exists('amount', $opsRequestParams)) {
+ $requestedAmount = $this->formatAmount($opsRequestParams['amount']);
+ }
+
+ /* find expected amount */
+ $expectedAmount = null;
+ if (null !== $openTransaction) {
+ $transactionInfo = unserialize($openTransaction->getAdditionalInformation('arrInfo'));
+ if (array_key_exists('amount', $transactionInfo)) {
+ if (null === $expectedAmount || $transactionInfo['amount'] == $requestedAmount) {
+ $expectedAmount = $this->formatAmount($transactionInfo['amount']);
+ }
+ }
+ }
+
+ if ($this->getTypeForStatus($opsRequestParams['STATUS']) == Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_TRANSACTION_TYPE
+ || $this->getTypeForStatus($opsRequestParams['STATUS']) == Netresearch_OPS_Model_Payment_Abstract::OPS_VOID_TRANSACTION_TYPE
+ ) {
+ if (null === $requestedAmount || 0 == count($openTransaction) || $requestedAmount != $expectedAmount) {
+ return false;
+ }
+ }
+
+ if ($this->getTypeForStatus($opsRequestParams['STATUS']) == Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_TRANSACTION_TYPE) {
+ if (null === $requestedAmount) {
+ Mage::helper('ops')->log('Please configure Ingenico ePayments to submit amount');
+ return false;
+ }
+ $grandTotal = $this->formatAmount(Mage::helper('ops/payment')->getBaseGrandTotalFromSalesObject($order));
+ if ($grandTotal != $requestedAmount) {
+ if (null === $openTransaction || $expectedAmount != $requestedAmount) {
+ return false;
+ }
+ }
+ }
+ return true;
+ }
+
+ public function performDirectLinkRequest($quote, $params, $storeId = null)
+ {
+ $url = Mage::getModel('ops/config')->getDirectLinkGatewayOrderPath($storeId);
+ $response = Mage::getSingleton('ops/api_directlink')->performRequest($params, $url, $storeId);
+ /**
+ * allow null as valid state for creating the order with status 'pending'
+ */
+ if (null != $response['STATUS'] && Mage::helper('ops/payment')->isPaymentFailed($response['STATUS'])) {
+ Mage::getSingleton('checkout/type_onepage')->getCheckout()->setGotoSection('payment');
+ Mage::throwException(Mage::helper('ops/data')->__('Ingenico ePayments Payment failed'));
+ }
+
+ return $response;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Kwixo.php b/app/code/community/Netresearch/OPS/Helper/Kwixo.php
new file mode 100644
index 0000000..b8f8e4b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Kwixo.php
@@ -0,0 +1,165 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Kwixo extends Mage_Core_Helper_Abstract
+{
+
+ protected $helper = null;
+
+ protected function getHelper()
+ {
+ if (null === $this->helper) {
+ $this->helper = Mage::helper('ops/data');
+ }
+
+ return $this->helper;
+ }
+
+ /**
+ * validates the kwixoConfiguration data
+ *
+ * @param array $postData the data to validate
+ *
+ * @throws Mage_Core_Exception on errors
+ *
+ */
+ public function validateKwixoconfigurationMapping(array $postData)
+ {
+ $this->validateKwixoConfigurationData($postData);
+ $this->validateKwixoMappingExist($postData);
+ $this->validateCategoryExist($postData);
+ }
+
+ /**
+ * saves the KwixoConfigurationMapping
+ *
+ * @param array $postData
+ */
+ public function saveKwixoconfigurationMapping(array $postData)
+ {
+ $this->validateKwixoconfigurationMapping($postData);
+ $kwixoCatMapModel = Mage::getModel(
+ 'ops/kwixo_category_mapping'
+ )->load($postData['id']);
+ $kwixoCatMapModel->setCategoryId($postData['category_id']);
+ $kwixoCatMapModel->setKwixoCategoryId(
+ $postData['kwixoCategory_id']
+ );
+ $kwixoCatMapModel->save();
+ if (array_key_exists('applysubcat', $postData)) {
+ $category = Mage::getModel('catalog/category')->load(
+ $postData['category_id']
+ );
+ $subcategories = $category->getAllChildren(true);
+ foreach ($subcategories as $subcategory) {
+ $kwixoCatMapModel = Mage::getModel('ops/kwixo_category_mapping')->loadByCategoryId($subcategory);
+ $kwixoCatMapModel->setCategoryId($subcategory);
+ $kwixoCatMapModel->setKwixoCategoryId($postData['kwixoCategory_id']);
+ $kwixoCatMapModel->save();
+ }
+ }
+ Mage::getSingleton('adminhtml/session')->addSuccess(
+ Mage::helper('ops/data')->__(
+ 'Successfully added Kwixo category mapping'
+ )
+ );
+ }
+
+
+ /**
+ * validates if the structure of a given array does match the expected kwixo
+ * setting configuration
+ *
+ * @param array $postData - the array to inspect
+ *
+ * @throws Mage_Core_Exception - if the structure does not match
+ */
+ protected function validateKwixoConfigurationData(array $postData)
+ {
+ $helper = $this->getHelper();
+ $isValid = true;
+ $message = '';
+ if (0 === count($postData)) {
+ $message = $helper->__('Invalid form data provided');
+ $isValid = false;
+ }
+
+ if ($isValid && !array_key_exists('id', $postData)) {
+ $message = $helper->__('Invalid form data provided');
+ $isValid = false;
+ }
+
+ if ($isValid && 0 < strlen($postData['id'])
+ && (!is_numeric($postData['id'])
+ || $postData['id'] < 0)
+ ) {
+ $message = $helper->__('Invalid id provided');
+ $isValid = false;
+ }
+ if (false === $isValid) {
+ Mage::throwException($message);
+ }
+ }
+
+ /**
+ * validates if the given array contains the neccessary information for
+ * a proper kwixo category setting
+ *
+ * @param array $postData - the array to inspect
+ *
+ * @throws Mage_Core_Exception - if the array does not contain the needed
+ * information
+ *
+ */
+ protected function validateKwixoMappingExist(array $postData)
+ {
+ $helper = $this->getHelper();
+ $kwixoCategories = Mage::getModel('ops/source_kwixo_productCategories')
+ ->getValidKwixoCategoryIds();
+ if (!array_key_exists('kwixoCategory_id', $postData)
+ || !in_array(
+ $postData['kwixoCategory_id'], $kwixoCategories
+ )
+ ) {
+ Mage::throwException(
+ $helper->__('Invalid kwixo category provided')
+ );
+ }
+ }
+
+ /**
+ * validates if the given array contains a proper category setting
+ *
+ * @param array $postData - the array to inspect
+ *
+ * @throws Mage_Core_Exception - if an invalid setting is given
+ */
+ protected function validateCategoryExist(array $postData)
+ {
+ $helper = $this->getHelper();
+ $isValid = true;
+ $message = '';
+ if (!array_key_exists('category_id', $postData)) {
+ $isValid = false;
+ $message = $helper->__('Invalid category provided');
+
+ }
+ if ($isValid
+ && (!is_numeric($postData['category_id'])
+ || null === Mage::getModel('catalog/category')->load($postData['category_id'])->getId())
+ ) {
+ $isValid = false;
+ $message = $helper->__('Invalid category provided');
+ }
+ if (false === $isValid) {
+ Mage::throwException($message);
+ }
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/MobileDetect.php b/app/code/community/Netresearch/OPS/Helper/MobileDetect.php
new file mode 100644
index 0000000..bf8ba70
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/MobileDetect.php
@@ -0,0 +1,68 @@
+
+ * @license OSL 3.0
+ */
+require_once Mage::getBaseDir('lib') . DS . 'MobileDetect' .DS. 'Mobile_Detect.php';
+
+class Netresearch_OPS_Helper_MobileDetect extends Mage_Core_Helper_Abstract
+{
+ /**
+ * Computer device type string
+ */
+ const DEVICE_TYPE_COMPUTER = 'Computer';
+ /**
+ * mobile device type string
+ */
+ const DEVICE_TYPE_MOBILE = 'Mobile';
+ /**
+ * tablet device type string
+ */
+ const DEVICE_TYPE_TABLET = 'Tablet';
+
+ /**
+ * @var Mobile_Detect
+ */
+ private $_detector = null;
+
+ /**
+ * create class instance
+ *
+ * Netresearch_OPS_Helper_MobileDetect constructor.
+ * @param null $headers
+ * @param null $userAgent
+ * @param null $detector
+ */
+ public function __construct()
+ {
+ $this->_detector = new Mobile_Detect();
+ }
+
+ public function setDetector($detector)
+ {
+ $this->_detector = $detector;
+ }
+
+ /**
+ * determine device type with help of mobile_detect lib and return it
+ *
+ * @return string
+ */
+ public function getDeviceType()
+ {
+ $deviceType = self::DEVICE_TYPE_COMPUTER;
+ if ($this->_detector->isMobile()) {
+ $deviceType = self::DEVICE_TYPE_MOBILE;
+ }
+
+ if ($this->_detector->isTablet()) {
+ $deviceType = self::DEVICE_TYPE_TABLET;
+ }
+
+ return $deviceType;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Order.php b/app/code/community/Netresearch/OPS/Helper/Order.php
new file mode 100644
index 0000000..eeb7cfd
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Order.php
@@ -0,0 +1,170 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Order extends Mage_Core_Helper_Abstract
+{
+
+ const DELIMITER = '#';
+
+ /** @var $config Netresearch_OPS_Model_Config */
+ protected $config = null;
+
+ protected $statusMappingModel = null;
+
+ /**
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ */
+ public function setDataHelper(Netresearch_OPS_Helper_Data $dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Data
+ */
+ public function getDataHelper()
+ {
+ if (null === $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+
+ protected $dataHelper = null;
+
+
+ /**
+ * return the config model
+ *
+ * @return Netresearch_OPS_Model_Config
+ */
+ protected function getConfig()
+ {
+ if (null === $this->config) {
+ $this->config = Mage::getModel('ops/config');
+ }
+
+ return $this->config;
+ }
+
+ /**
+ * generates the OPS order id in dependency to the config
+ *
+ * @param mixed $salesObject
+ * @param bool $useOrderIdIfPossible if false forces the usage of quoteid (for Kwixo pm etc.)
+ *
+ * @return string
+ */
+ public function getOpsOrderId($salesObject, $useOrderIdIfPossible = true)
+ {
+ $config = $this->getConfig();
+ $devPrefix = $config->getConfigData('devprefix');
+ if ($salesObject instanceof Mage_Sales_Model_Order) {
+ /** @var $salesObject Mage_Sales_Model_Order */
+ $orderRef = $salesObject->getQuoteId();
+ } elseif ($salesObject instanceof Mage_Sales_Model_Quote) {
+ /** @var $salesObject Mage_Sales_Model_Quote */
+ $orderRef = $salesObject->getId();
+ }
+
+ if ($config->getOrderReference($salesObject->getStoreId())
+ == Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID
+ && $useOrderIdIfPossible === true
+ ) {
+ if ($salesObject instanceof Mage_Sales_Model_Quote) {
+ $salesObject->reserveOrderId();
+ $orderRef = self::DELIMITER . $salesObject->getReservedOrderId();
+ } elseif ($salesObject instanceof Mage_Sales_Model_Order) {
+ $orderRef = self::DELIMITER . $salesObject->getIncrementId();
+ }
+
+ }
+
+ return $devPrefix . $orderRef;
+ }
+
+ /**
+ * getting the order from opsOrderId which can either the quote id or the order increment id
+ * in both cases the dev prefix is stripped, if neccessary
+ *
+ * @param $opsOrderId
+ *
+ * @return Mage_Sales_Model_Order
+ */
+ public function getOrder($opsOrderId)
+ {
+ $order = null;
+ $fieldToFilter = 'quote_id';
+ $devPrefix = $this->getConfig()->getConfigData('devprefix');
+ if ($devPrefix == substr($opsOrderId, 0, strlen($devPrefix))) {
+ $opsOrderId = substr($opsOrderId, strlen($devPrefix));
+ }
+ // opsOrderId was created from order increment id, use increment id for filtering
+ if (0 === strpos($opsOrderId, self::DELIMITER)) {
+ $opsOrderId = substr($opsOrderId, strlen(self::DELIMITER));
+ $fieldToFilter = 'increment_id';
+ }
+
+ /* @var $order Mage_Sales_Model_Resource_Order_Collection */
+ $order = Mage::getModel('sales/order')->getCollection()
+ ->addFieldToFilter($fieldToFilter, $opsOrderId)
+ // filter for OPS payment methods
+ ->join(array('payment' => 'sales/order_payment'), 'main_table.entity_id=parent_id', 'method')
+ ->addFieldToFilter('method', array(array('like' => 'ops_%')))
+ // sort by increment_id of order to get only the latest (relevant for quote id search)
+ ->addOrder('main_table.increment_id');
+
+ return $order->getFirstItem();
+ }
+
+ /**
+ * load and return the quote via the quoteId
+ *
+ * @param string $quoteId
+ *
+ * @return Mage_Model_Sales_Quote
+ */
+ public function getQuote($quoteId)
+ {
+ return Mage::getModel('sales/quote')->load($quoteId);
+ }
+
+ /**
+ * check if billing is same as shipping address
+ *
+ * @param Mage_Model_Sales_Order $order
+ *
+ * @return int
+ */
+ public function checkIfAddressesAreSame(Mage_Sales_Model_Order $order)
+ {
+ $addMatch = 0;
+ $billingAddressHash = null;
+ $shippingAddressHash = null;
+ if ($order->getBillingAddress() instanceof Mage_Customer_Model_Address_Abstract) {
+ $billingAddressHash = Mage::helper('ops/alias')->generateAddressHash(
+ $order->getBillingAddress()
+ );
+ }
+ if ($order->getShippingAddress() instanceof Mage_Customer_Model_Address_Abstract) {
+ $shippingAddressHash = Mage::helper('ops/alias')->generateAddressHash(
+ $order->getShippingAddress()
+ );
+ }
+
+ if ($billingAddressHash === $shippingAddressHash) {
+ $addMatch = 1;
+ }
+
+ return $addMatch;
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Order/Abstract.php b/app/code/community/Netresearch/OPS/Helper/Order/Abstract.php
new file mode 100644
index 0000000..6387a82
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Order/Abstract.php
@@ -0,0 +1,84 @@
+getBaseGrandTotalFromSalesObject($payment->getOrder())) * 100,
+ 0
+ );
+ $amount = round(($amount * 100), 0);
+
+ if (abs($orderTotalAmount - $amount) <= 1) {
+ return 'full';
+ } else {
+ return 'partial';
+ }
+ }
+
+
+ /**
+ * checks if the amount captured/refunded is equal to the amount of the full order
+ * and returns the operation code accordingly
+ *
+ * @param Mage_Sales_Order_Payment $payment
+ * @param float $amount
+ * @return string operation code for the requested amount
+ * @see getPartialOperationCode() and getFullOperationCode() *
+ */
+ public function determineOperationCode($payment, $amount)
+ {
+ $orderTotalAmount = round(
+ (Mage::helper('ops/payment')->getBaseGrandTotalFromSalesObject($payment->getOrder())) * 100,
+ 0
+ );
+ $totalProcessedAmount = round((($this->getPreviouslyProcessedAmount($payment) + $amount) * 100), 0);
+
+ if (abs($orderTotalAmount - $totalProcessedAmount) <= 1 ) {
+ return $this->getFullOperationCode();
+ } else {
+ return $this->getPartialOperationCode();
+ }
+
+ }
+
+ /**
+ * Returns the Amount already processed for this kind of operation
+ * eg. getBaseAmountPaidOnline and getRefundedAmount
+ *
+ * @param Mage_Sales_Order_Payment $payment
+ * @return float amount already processed for this kind of operation
+ */
+ protected abstract function getPreviouslyProcessedAmount($payment);
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Order/Capture.php b/app/code/community/Netresearch/OPS/Helper/Order/Capture.php
new file mode 100644
index 0000000..afef199
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Order/Capture.php
@@ -0,0 +1,79 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Order_Capture extends Netresearch_OPS_Helper_Order_Abstract
+{
+ protected function getFullOperationCode()
+ {
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_FULL;
+ }
+
+ protected function getPartialOperationCode()
+ {
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_PARTIAL;
+ }
+
+ protected function getPreviouslyProcessedAmount($payment)
+ {
+ return $payment->getBaseAmountPaidOnline();
+ }
+
+
+ /**
+ * Prepare capture informations
+ *
+ * @param Mage_Sales_Order_Payment $payment
+ * @param float $amount
+ * @return array
+ */
+ public function prepareOperation($payment, $amount)
+ {
+ $params = Mage::app()->getRequest()->getParams();
+ if (array_key_exists('invoice', $params)) {
+ $arrInfo = $params['invoice'];
+ $arrInfo['amount'] = $amount;
+ }
+ $arrInfo['type'] = $this->determineType($payment, $amount);
+ $arrInfo['operation'] = $this->determineOperationCode($payment, $amount);
+
+ return $arrInfo;
+ }
+
+ /**
+ * Prepare shipment
+ *
+ * @param Mage_Sales_Model_Order_Invoice $invoice New invoice
+ * @param array $additionalData Array containing additional transaction data
+ *
+ * @return Mage_Sales_Model_Order_Shipment
+ */
+ protected function _prepareShipment($invoice, $additionalData)
+ {
+ $savedQtys = $additionalData['items'];
+ $shipment = Mage::getModel('sales/service_order', $invoice->getOrder())
+ ->prepareShipment($savedQtys);
+ if (!$shipment->getTotalQty()) {
+ return false;
+ }
+
+ $shipment->register();
+ if (array_key_exists('tracking', $additionalData)
+ && $additionalData['tracking']
+ ) {
+ foreach ($additionalData['tracking'] as $data) {
+ $track = Mage::getModel('sales/order_shipment_track')
+ ->addData($data);
+ $shipment->addTrack($track);
+ }
+ }
+
+ return $shipment;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Order/Refund.php b/app/code/community/Netresearch/OPS/Helper/Order/Refund.php
new file mode 100644
index 0000000..d417358
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Order/Refund.php
@@ -0,0 +1,142 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Order_Refund extends Netresearch_OPS_Helper_Order_Abstract
+{
+ protected $payment;
+ protected $amount;
+ protected $params;
+
+ protected function getFullOperationCode()
+ {
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL;
+ }
+
+ protected function getPartialOperationCode()
+ {
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL;
+ }
+
+ protected function getPreviouslyProcessedAmount($payment)
+ {
+ return $payment->getBaseAmountRefundedOnline();
+ }
+
+
+ /**
+ * @param Varien_Object $payment
+ * @return $this
+ */
+ public function setPayment(Varien_Object $payment)
+ {
+ $this->payment = $payment;
+
+ return $this;
+ }
+
+ /**
+ * @param $amount
+ * @return $this
+ */
+ public function setAmount($amount)
+ {
+ $this->amount = $amount;
+
+ return $this;
+ }
+
+ /**
+ * @param array $params
+ * @return $this
+ */
+ public function setCreditMemoRequestParams($params)
+ {
+ $this->params = $params;
+
+ return $this;
+ }
+
+ /**
+ * @return array params
+ */
+ public function getCreditMemoRequestParams()
+ {
+ if (!is_array($this->params)) {
+ $this->setCreditMemoRequestParams(Mage::app()->getRequest()->getParams());
+ }
+
+ return $this->params;
+ }
+
+ public function getInvoiceFromCreditMemoRequest()
+ {
+ $params = $this->getCreditMemoRequestParams();
+ if (array_key_exists('invoice_id', $params)) {
+ return Mage::getModel('sales/order_invoice')->load($params['invoice_id']);
+ }
+
+ return null;
+ }
+
+ public function getCreditMemoFromRequest()
+ {
+ $params = $this->getCreditMemoRequestParams();
+ if (array_key_exists('creditmemo', $params)) {
+ return $params['creditmemo'];
+ }
+
+ return array();
+ }
+
+ /**
+ * @param $payment
+ * @param $amount
+ * @return mixed
+ */
+ public function prepareOperation($payment, $amount)
+ {
+ $params = $this->getCreditMemoRequestParams();
+
+ if (array_key_exists('creditmemo', $params)) {
+ $arrInfo = $params['creditmemo'];
+ $arrInfo['amount'] = $amount;
+ }
+ $arrInfo['type'] = $this->determineType($payment, $amount);
+ $arrInfo['operation'] = $this->determineOperationCode($payment, $amount);
+
+ if($arrInfo['type'] == 'full'){
+ // hard overwrite operation code for last transaction
+ $arrInfo['operation'] = $this->getFullOperationCode();
+ }
+
+
+ return $arrInfo;
+ }
+
+ /**
+ * Checks for open refund transaction
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ *
+ * @return Mage_Sales_Model_Order_Payment_Transaction|null
+ */
+ public function getOpenRefundTransaction($payment)
+ {
+ /** @var Mage_Sales_Model_Resource_Order_Payment_Transaction_Collection $refundTransactions */
+ $refundTransactions = Mage::getModel('sales/order_payment_transaction')->getCollection();
+ $transaction = $refundTransactions->addPaymentIdFilter($payment->getId())
+ ->addTxnTypeFilter(Mage_Sales_Model_Order_Payment_Transaction::TYPE_REFUND)
+ ->setOrderFilter($payment->getOrder())
+ ->addFieldToFilter('is_closed', 0)
+ ->getFirstItem();
+
+ return $transaction;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Payment.php b/app/code/community/Netresearch/OPS/Helper/Payment.php
new file mode 100644
index 0000000..3d57bce
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Payment.php
@@ -0,0 +1,969 @@
+
+ * @author André Herrn
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Payment extends Mage_Core_Helper_Abstract
+{
+ protected $shaAlgorithm = null;
+
+ /**
+ * Get checkout session namespace
+ *
+ * @return Mage_Checkout_Model_Session
+ */
+ protected function _getCheckout()
+ {
+ return Mage::getSingleton('checkout/session');
+ }
+
+ /**
+ * Get checkout session namespace
+ *
+ * @return Netresearch_OPS_Model_Config
+ */
+ protected function getConfig()
+ {
+ return Mage::getSingleton('ops/config');
+ }
+
+ /**
+ * Get encrypt / decrypt algorithm
+ *
+ * @return string
+ */
+ public function getCryptMethod()
+ {
+ if (null === $this->shaAlgorithm) {
+ $this->shaAlgorithm = $this->getConfig()->getConfigData('secret_key_type');
+ }
+
+ return $this->shaAlgorithm;
+ }
+
+ /**
+ * Crypt Data by SHA1 ctypting algorithm by secret key
+ *
+ * @param array $data
+ * @param string $key
+ *
+ * @return string hash
+ */
+ public function shaCrypt($data, $key = '')
+ {
+ if (is_array($data)) {
+ return hash($this->getCryptMethod(), implode("", $data));
+ }
+ if (is_string($data)) {
+ return hash($this->getCryptMethod(), $data);
+ } else {
+ return "";
+ }
+ }
+
+ /**
+ * Check hash crypted by SHA1 with existing data
+ *
+ * @param array $data
+ * @param string $hashFromOPS
+ * @param string $key
+ *
+ * @return bool
+ */
+ public function shaCryptValidation($data, $hashFromOPS, $key = '')
+ {
+ if (is_array($data)) {
+ $data = implode("", $data);
+ }
+
+ $hashUtf8 = strtoupper(hash($this->getCryptMethod(), $data));
+ $hashNonUtf8 = strtoupper(hash($this->getCryptMethod(), utf8_encode($data)));
+
+ $helper = Mage::helper('ops');
+ $helper->log($helper->__("Module Secureset: %s", $data));
+
+ if ($this->compareHashes($hashFromOPS, $hashUtf8)) {
+ return true;
+ } else {
+ $helper->log($helper->__("Trying again with non-utf8 secureset"));
+
+ return $this->compareHashes($hashFromOPS, $hashNonUtf8);
+ }
+ }
+
+ protected function compareHashes($hashFromOPS, $actual)
+ {
+ $helper = Mage::helper('ops');
+ $helper->log(
+ $helper->__(
+ "Checking hashes\nHashed String by Magento: %s\nHashed String by Ingenico ePayments: %s",
+ $actual,
+ $hashFromOPS
+ )
+ );
+
+ if ($hashFromOPS == $actual) {
+ Mage::helper('ops')->log("Successful validation");
+
+ return true;
+ }
+
+ return false;
+ }
+
+ /**
+ * Return set of data which is ready for SHA crypt
+ *
+ * @param array $params
+ * @param string $SHAkey
+ *
+ * @return string
+ */
+ public function getSHAInSet($params, $SHAkey)
+ {
+ $params = $this->prepareParamsAndSort($params);
+ $plainHashString = "";
+ foreach ($params as $paramSet):
+ if ($paramSet['value'] == '' || $paramSet['key'] == 'SHASIGN' || is_array($paramSet['value'])) {
+ continue;
+ }
+ $plainHashString .= strtoupper($paramSet['key']) . "=" . $paramSet['value'] . $SHAkey;
+ endforeach;
+
+ return $plainHashString;
+ }
+
+ /**
+ * Return prepared and sorted array for SHA Signature Validation
+ *
+ * @param array $params
+ *
+ * @return string
+ */
+ public function prepareParamsAndSort($params)
+ {
+ unset($params['CardNo']);
+ unset($params['Brand']);
+ unset($params['SHASign']);
+
+ $params = array_change_key_case($params, CASE_UPPER);
+
+ //PHP ksort takes care about "_", OPS not
+ $sortedParams = array();
+ foreach ($params as $key => $value):
+ $sortedParams[str_replace("_", "", $key)] = array('key' => $key, 'value' => $value);
+ endforeach;
+ ksort($sortedParams);
+
+ return $sortedParams;
+ }
+
+ /*
+ * Get SHA-1-IN hash for ops-authentification
+ *
+ * All Parameters have to be alphabetically, UPPERCASE
+ * Empty Parameters shouldn't appear in the secure string
+ *
+ * @param array $formFields
+ * @param string $shaCode
+ *
+ * @return string
+ */
+ public function getSHASign($formFields, $shaCode = null, $storeId = null)
+ {
+ if (null === $shaCode) {
+ $shaCode = Mage::getModel('ops/config')->getShaOutCode($storeId);
+ }
+ $formFields = array_change_key_case($formFields, CASE_UPPER);
+ uksort($formFields, 'strnatcasecmp');
+ $plainHashString = '';
+ foreach ($formFields as $formKey => $formVal) {
+ if (null === $formVal || '' === $formVal || $formKey == 'SHASIGN') {
+ continue;
+ }
+ $plainHashString .= strtoupper($formKey) . '=' . $formVal . $shaCode;
+ }
+
+ return $plainHashString;
+ }
+
+ /**
+ * @param int $opsOrderId
+ * @param int $storeId
+ *
+ * @return array
+ */
+ public function validateOrderForReuse($opsOrderId, $storeId)
+ {
+
+ return array(
+ 'orderID' => $opsOrderId,
+ 'SHASIGN' => strtoupper(
+ $this->shaCrypt(
+ $this->getSHAInSet(
+ array('orderId' => $opsOrderId),
+ $this->getConfig()->getShaOutCode($storeId)
+ )
+ )
+ ),
+ );
+ }
+
+ /**
+ * We get some CC info from ops, so we must save it
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param array $ccInfo
+ *
+ * @return $this
+ */
+ public function _prepareCCInfo($order, $ccInfo)
+ {
+ if (isset($ccInfo['CN'])) {
+ $order->getPayment()->setCcOwner($ccInfo['CN']);
+ }
+
+ if (isset($ccInfo['CARDNO'])) {
+ $order->getPayment()->setCcNumberEnc($ccInfo['CARDNO']);
+ $order->getPayment()->setCcLast4(substr($ccInfo['CARDNO'], -4));
+ }
+
+ if (isset($ccInfo['ED'])) {
+ $order->getPayment()->setCcExpMonth(substr($ccInfo['ED'], 0, 2));
+ $order->getPayment()->setCcExpYear(substr($ccInfo['ED'], 2, 2));
+ }
+
+ return $this;
+ }
+
+ public function isPaymentAccepted($status)
+ {
+ return in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status::AUTHORIZED,
+ Netresearch_OPS_Model_Status::AUTHORIZATION_WAITING,
+ Netresearch_OPS_Model_Status::AUTHORIZED_UNKNOWN,
+ Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT,
+ Netresearch_OPS_Model_Status::PAYMENT_REQUESTED,
+ Netresearch_OPS_Model_Status::PAYMENT_PROCESSING,
+ Netresearch_OPS_Model_Status::PAYMENT_UNCERTAIN,
+ Netresearch_OPS_Model_Status::WAITING_FOR_IDENTIFICATION
+ )
+ );
+ }
+
+ public function isPaymentAuthorizeType($status)
+ {
+ return in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status::AUTHORIZED,
+ Netresearch_OPS_Model_Status::AUTHORIZATION_WAITING,
+ Netresearch_OPS_Model_Status::AUTHORIZED_UNKNOWN,
+ Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT
+ )
+ );
+ }
+
+ public function isPaymentCaptureType($status)
+ {
+ return in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status::PAYMENT_REQUESTED,
+ Netresearch_OPS_Model_Status::PAYMENT_PROCESSING,
+ Netresearch_OPS_Model_Status::PAYMENT_UNCERTAIN
+ )
+ );
+ }
+
+ public function isPaymentFailed($status)
+ {
+ return false == $this->isPaymentAccepted($status);
+ }
+
+ /**
+ * apply ops state for order
+ *
+ * @param Mage_Sales_Model_Order $order Order
+ * @param array $params Request params
+ *
+ * @return string
+ */
+ public function applyStateForOrder($order, $params)
+ {
+
+ Mage::getModel('ops/response_handler')->processResponse($params, $order->getPayment()->getMethodInstance());
+ $order->getPayment()->save();
+
+ $feedbackStatus = '';
+
+ switch ($params['STATUS']) {
+ case Netresearch_OPS_Model_Status::WAITING_FOR_IDENTIFICATION : //3D-Secure
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT;
+ break;
+ case Netresearch_OPS_Model_Status::AUTHORIZED:
+ case Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT:
+ case Netresearch_OPS_Model_Status::AUTHORIZATION_WAITING:
+ case Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT:
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT;
+ break;
+ case Netresearch_OPS_Model_Status::PAYMENT_REQUESTED:
+ case Netresearch_OPS_Model_Status::PAYMENT_PROCESSING:
+ case Netresearch_OPS_Model_Status::PAYMENT_PROCESSED_BY_MERCHANT:
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT;
+ break;
+ case Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED:
+ case Netresearch_OPS_Model_Status::PAYMENT_REFUSED:
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_DECLINE;
+ break;
+ case Netresearch_OPS_Model_Status::CANCELED_BY_CUSTOMER:
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_CANCEL;
+ break;
+ default:
+ //all unknown transaction will accept as exceptional
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_EXCEPTION;
+ }
+
+ return $feedbackStatus;
+ }
+
+ /**
+ * Process success action by accept url
+ *
+ *
+ * @param $order
+ * @param $params
+ * @param int $instantCapture
+ * @throws Exception
+ */
+ public function acceptOrder($order, $params, $instantCapture = 0)
+ {
+ $this->_getCheckout()->setLastSuccessQuoteId($order->getQuoteId());
+ $this->_prepareCCInfo($order, $params);
+ $this->setPaymentTransactionInformation($order->getPayment(), $params, 'accept');
+ $this->setFraudDetectionParameters($order->getPayment(), $params);
+
+ if ($transaction = Mage::helper('ops/payment')->getTransactionByTransactionId($order->getQuoteId())) {
+ $transaction->setTxnId($params['PAYID'])->save();
+ }
+
+ try {
+ if (false === $this->forceAuthorize($order)
+ && ($this->getConfig()->getConfigData('payment_action')
+ == Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE
+ || $instantCapture)
+ && $params['STATUS'] != Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT
+ ) {
+ $this->_processDirectSale($order, $params, $instantCapture);
+ } else {
+ $this->_processAuthorize($order, $params);
+ }
+ } catch (Exception $e) {
+ $this->_getCheckout()->addError(Mage::helper('ops')->__('Order can not be saved.'));
+ throw $e;
+ }
+ }
+
+ /**
+ * Set Payment Transaction Information
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment Sales Payment Model
+ * @param array $params Request params
+ * @param string $action Action (accept|cancel|decline|wait|exception)
+ */
+ protected function setPaymentTransactionInformation(Mage_Sales_Model_Order_Payment $payment, $params, $action)
+ {
+ $payment->setTransactionId($params['PAYID']);
+ $code = $payment->getMethodInstance()->getCode();
+
+ $isInline = false;
+
+ /* In authorize mode we still have no authorization transaction for CC and DirectDebit payments,
+ * so capture or cancel won't work. So we need to create a new authorization transaction for them
+ * when a payment was accepted by Ingenico ePayments
+ *
+ * In exception-case we create the authorization-transaction too
+ * because some exception-cases can turn into accepted
+ */
+ if (('accept' === $action || 'exception' === $action)
+ && in_array($code, array('ops_cc', 'ops_directDebit'))
+ ) {
+ $payment->setIsTransactionClosed(false);
+ $isInline = $this->isInlinePayment($payment);
+ /* create authorization transaction for non-inline pms */
+ if (false === $isInline
+ || (array_key_exists('HTML_ANSWER', $params)
+ || 0 < strlen(
+ $payment->getAdditionalInformation('HTML_ANSWER')
+ ))
+ ) {
+ $payment->addTransaction("authorization", null, true, $this->__("Process outgoing transaction"));
+ }
+ $payment->setLastTransId($params['PAYID']);
+ }
+
+ /* Ingenico ePayments sends parameter HTML_ANSWER to trigger 3D secure redirection */
+ if (isset($params['HTML_ANSWER']) && ('ops_cc' == $code)) {
+ $payment->setAdditionalInformation('HTML_ANSWER', $params['HTML_ANSWER']);
+ $payment->setIsTransactionPending(true);
+ }
+
+ $payment->setAdditionalInformation('paymentId', $params['PAYID']);
+ $payment->setAdditionalInformation('status', $params['STATUS']);
+ if (array_key_exists('ACCEPTANCE', $params) && 0 < strlen(trim($params['ACCEPTANCE']))) {
+ $payment->setAdditionalInformation('acceptance', $params['ACCEPTANCE']);
+ }
+ if (array_key_exists('BRAND', $params) && ('ops_cc' == $code) && 0 < strlen(trim($params['BRAND']))) {
+ $payment->setAdditionalInformation('CC_BRAND', $params['BRAND']);
+ }
+ if (false === $isInline || array_key_exists('HTML_ANSWER', $params)) {
+ $payment->setIsTransactionClosed(true);
+ }
+ $payment->setDataChanges(true);
+ $payment->save();
+ }
+
+ /**
+ * add fraud detection of Ingenico ePayments to additional payment data
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param array $params
+ */
+ protected function setFraudDetectionParameters($payment, $params)
+ {
+ $params = array_change_key_case($params, CASE_UPPER);
+ if (array_key_exists('SCORING', $params)) {
+ $payment->setAdditionalInformation('scoring', $params['SCORING']);
+ }
+ if (array_key_exists('SCO_CATEGORY', $params)) {
+ $payment->setAdditionalInformation('scoringCategory', $params['SCO_CATEGORY']);
+ }
+ $additionalScoringData = array();
+ foreach ($this->getConfig()->getAdditionalScoringKeys() as $key) {
+ if (array_key_exists($key, $params)) {
+ if (false === mb_detect_encoding($params[$key], 'UTF-8', true)) {
+ $additionalScoringData[$key] = utf8_encode($params[$key]);
+ } else {
+ $additionalScoringData[$key] = $params[$key];
+ }
+ }
+ }
+ $payment->setAdditionalInformation('additionalScoringData', $additionalScoringData);
+ }
+
+
+
+
+
+ /**
+ * Get Payment Exception Message
+ *
+ * @param $ops_status
+ * @return string
+ */
+ protected function getPaymentExceptionMessage($ops_status)
+ {
+ $exceptionMessage = '';
+ switch ($ops_status) {
+ case Netresearch_OPS_Model_Status::PAYMENT_UNCERTAIN :
+ $exceptionMessage = Mage::helper('ops')->__(
+ 'A technical problem arose during payment process, giving unpredictable result. Ingenico ePayments status: %s.',
+ Mage::helper('ops')->getStatusText($ops_status)
+ );
+ break;
+ default:
+ $exceptionMessage = Mage::helper('ops')->__(
+ 'An unknown exception was thrown in the payment process. Ingenico ePayments status: %s.',
+ Mage::helper('ops')->getStatusText($ops_status)
+ );
+ }
+
+ return $exceptionMessage;
+ }
+
+
+ /**
+ * send invoice to customer if that was configured by the merchant
+ *
+ * @param Mage_Sales_Model_Order_Invoice $invoice Invoice to be sent
+ *
+ * @return void
+ */
+ public function sendInvoiceToCustomer(Mage_Sales_Model_Order_Invoice $invoice)
+ {
+ if (false == $invoice->getEmailSent()
+ && $this->getConfig()->getSendInvoice()
+ ) {
+ $invoice->sendEmail(true);
+ }
+ }
+
+ /**
+ * Process Configured Payment Actions: Authorized, Default operation
+ * just place order
+ *
+ * @param Mage_Sales_Model_Order $order Order
+ * @param array $params Request params
+ */
+ protected function _processAuthorize($order, $params)
+ {
+ $status = $params['STATUS'];
+ if ($status == Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT) {
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_PROCESSING,
+ Mage_Sales_Model_Order::STATE_PENDING_PAYMENT,
+ Mage::helper('ops')->__(
+ 'Waiting for payment. Ingenico ePayments status: %s.', Mage::helper('ops')->getStatusText($status)
+ )
+ );
+
+ // send new order mail for bank transfer, since it is 'successfully' authorized at this point
+ if ($order->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_BankTransfer
+ && $order->getEmailSent() != 1
+ ) {
+ $order->sendNewOrderEmail();
+ }
+ } elseif ($status == Netresearch_OPS_Model_Status::AUTHORIZATION_WAITING) {
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_PROCESSING,
+ Mage_Sales_Model_Order::STATE_PENDING_PAYMENT,
+ Mage::helper('ops')->__(
+ 'Authorization uncertain. Ingenico ePayments status: %s.', Mage::helper('ops')->getStatusText($status)
+ )
+ );
+ } else {
+ // for 3DS payments the order has to be retrieved from the payment review step
+ if ($this->isInlinePayment($order->getPayment())
+ && 0 < strlen(trim($order->getPayment()->getAdditionalInformation('HTML_ANSWER')))
+ && $order->getPayment()->getAdditionalInformation('status') == Netresearch_OPS_Model_Status::AUTHORIZED
+ ) {
+
+ $order->getPayment()->setIsTransactionApproved(true)->registerPaymentReviewAction(
+ Mage_Sales_Model_Order_Payment::REVIEW_ACTION_UPDATE, true
+ )->save();
+ }
+ if ($this->isRedirectPaymentMethod($order) === true
+ && $order->getEmailSent() != 1
+ ) {
+ $order->sendNewOrderEmail();
+ }
+
+ if (!$this->isPaypalSpecialStatus($order->getPayment()->getMethodInstance(), $status)) {
+
+ $payId = $params['PAYID'];
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_PROCESSING,
+ Mage_Sales_Model_Order::STATE_PROCESSING,
+ Mage::helper('ops')->__(
+ 'Processed by Ingenico ePayments. Payment ID: %s. Ingenico ePayments status: %s.', $payId,
+ Mage::helper('ops')->getStatusText($status)
+ )
+ );
+ }
+ }
+ $order->save();
+ }
+
+ /**
+ * Special status handling for Paypal and status 91
+ *
+ * @param $pm
+ * @param $status
+ *
+ * @return bool
+ */
+ protected function isPaypalSpecialStatus($pm, $status)
+ {
+ return $pm instanceof Netresearch_OPS_Model_Payment_Paypal
+ && $status == Netresearch_OPS_Model_Status::PAYMENT_PROCESSING;
+ }
+
+ /**
+ * Fetches transaction with given transaction id
+ *
+ * @param string $transactionId
+ *
+ * @return mixed Mage_Sales_Model_Order_Payment_Transaction | boolean
+ */
+ public function getTransactionByTransactionId($transactionId)
+ {
+ if (!$transactionId) {
+ return false;
+ }
+ $transaction = Mage::getModel('sales/order_payment_transaction')
+ ->getCollection()
+ ->addAttributeToFilter('txn_id', $transactionId)
+ ->getLastItem();
+ if (null === $transaction->getId()) {
+ return false;
+ }
+ $transaction->getOrderPaymentObject();
+
+ return $transaction;
+ }
+
+ /**
+ * refill cart
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return void
+ */
+ public function refillCart($order)
+ {
+ // add items
+ $cart = Mage::getSingleton('checkout/cart');
+
+ if (0 < $cart->getQuote()->getItemsCollection()->getSize()) {
+ //cart is not empty, so refilling it is not required
+ return;
+ }
+ foreach ($order->getItemsCollection() as $item) {
+ try {
+ $cart->addOrderItem($item);
+ } catch (Exception $e) {
+ Mage::logException($e);
+ }
+ }
+ $cart->save();
+
+ // add coupon code
+ $coupon = $order->getCouponCode();
+ $session = Mage::getSingleton('checkout/session');
+ if (null != $coupon) {
+ $session->getQuote()->setCouponCode($coupon)->save();
+ }
+ }
+
+ /**
+ * Save OPS Status to Payment
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param array $params OPS-Response
+ *
+ * @return void
+ */
+ public function saveOpsStatusToPayment(Mage_Sales_Model_Order_Payment $payment, $params)
+ {
+ $payment
+ ->setAdditionalInformation('status', $params['STATUS'])
+ ->save();
+ }
+
+ /**
+ * Check is payment method is a redirect method
+ *
+ * @param $order
+ * @return bool
+ */
+ protected function isRedirectPaymentMethod($order)
+ {
+ $result = false;
+ $method = $order->getPayment()->getMethodInstance();
+ if ($method
+ && $method->getOrderPlaceRedirectUrl() != '' // Magento returns ''
+ && $method->getOrderPlaceRedirectUrl() !== false // Ops returns false
+ ) {
+ $result = true;
+ }
+
+ return $result;
+ }
+
+ public function getQuote()
+ {
+ return $this->_getCheckout()->getQuote();
+ }
+
+ /**
+ * sets the state to pending payment if neccessary (order is in state new)
+ * and adds a comment to status history
+ *
+ * @param $order - the order
+ */
+ public function handleUnknownStatus($order)
+ {
+ if ($order instanceof Mage_Sales_Model_Order) {
+ $message = Mage::helper('ops')->__(
+ 'Unknown Ingenico ePayments state for this order. Please check Ingenico ePayments backend for this order.'
+ );
+ if ($order->getState() == Mage_Sales_Model_Order::STATE_NEW) {
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_PENDING_PAYMENT,
+ Mage_Sales_Model_Order::STATE_PENDING_PAYMENT,
+ $message
+ );
+ } else {
+ $order->addStatusHistoryComment($message);
+ }
+ $order->save();
+ }
+ }
+
+ /**
+ * returns the base grand total from either a quote or an order
+ *
+ * @param $salesObject
+ *
+ * @return double the base amount of the order
+ * @throws Exception if $salesObject is not a quote or an order
+ */
+ public function getBaseGrandTotalFromSalesObject($salesObject)
+ {
+ if (!($salesObject instanceof Mage_Sales_Model_Order || $salesObject instanceof Mage_Sales_Model_Quote)) {
+ Mage::throwException('$salesObject is not a quote or an order instance');
+ }
+
+ return $salesObject->getBaseGrandTotal();
+ }
+
+
+ /**
+ * Save the last used refund operation code to payment
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param string $operationCode
+ *
+ * @return void
+ */
+ public function saveOpsRefundOperationCodeToPayment(Mage_Sales_Model_Order_Payment $payment, $operationCode)
+ {
+ if (in_array(
+ strtoupper(trim($operationCode)),
+ array(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL,
+ Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL
+ )
+ )
+ ) {
+ Mage::helper('ops/data')->log(
+ sprintf(
+ "set last refund operation '%s' code to payment for order '%s'",
+ $operationCode,
+ $payment->getOrder()->getIncrementId()
+ )
+ );
+ $payment
+ ->setAdditionalInformation('lastRefundOperationCode', $operationCode)
+ ->save();
+ }
+ }
+
+ /**
+ * sets the canRefund information depending on the last refund operation code
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ */
+ public function setCanRefundToPayment(Mage_Sales_Model_Order_Payment $payment)
+ {
+ $refundOperationCode = $payment->getAdditionalInformation('lastRefundOperationCode');
+ if (in_array(
+ strtoupper(trim($refundOperationCode)),
+ array(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL,
+ Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL
+ )
+ )
+ ) {
+ /*
+ * a further refund is possible if the transaction remains open, that means either the merchant
+ * did not close the transaction or the refunded amount is less than the orders amount
+ */
+ $canRefund = ($refundOperationCode == Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL);
+ Mage::helper('ops/data')->log(
+ sprintf(
+ "set canRefund to '%s' for payment of order '%s'",
+ var_export($canRefund, true),
+ $payment->getOrder()->getIncrementId()
+ )
+ );
+ $payment
+ ->setAdditionalInformation('canRefund', $canRefund)
+ ->save();
+ }
+ }
+
+ /**
+ * determine whether the payment supports only authorize or not
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return true . if so, false otherwise
+ */
+ protected function forceAuthorize(Mage_Sales_Model_Order $order)
+ {
+ return ($order->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Kwixo_Abstract);
+ }
+
+
+ /**
+ * add ops_cc payment to checkout methods if quote total is zero and zero amount checkout is activated
+ *
+ * @param Mage_Payment_Block_Form_Container $block
+ *
+ * @return $this
+ */
+ public function addCCForZeroAmountCheckout(Mage_Payment_Block_Form_Container $block)
+ {
+ $methods = $block->getMethods();
+ if (false === $this->checkIfCCisInCheckoutMethods($methods)) {
+ $ccPayment = Mage::getModel('ops/payment_cc');
+ if ($ccPayment->getFeatureModel()->isCCAndZeroAmountAuthAllowed($ccPayment, $block->getQuote())) {
+ $ccPayment->setInfoInstance($block->getQuote()->getPayment());
+ $methods[] = $ccPayment;
+ $block->setData('methods', $methods);
+ }
+ }
+
+ return $this;
+ }
+
+
+ /**
+ * check if ops_cc is in payment methods array
+ *
+ * @param $methods
+ *
+ * @return array
+ */
+ protected function checkIfCCisInCheckoutMethods($methods)
+ {
+ $result = false;
+ foreach ($methods as $method) {
+ if ($method->getCode() == 'ops_cc') {
+ $result = true;
+ break;
+ }
+ }
+
+ return $result;
+ }
+
+ /**
+ * checks if the payment method can use order's increment id as merchant's reference
+ *
+ * @param Mage_Payment_Model_Info $payment
+ *
+ * @return bool
+ */
+ public function isInlinePaymentWithOrderId(Mage_Payment_Model_Info $payment)
+ {
+ return $this->isInlinePayment($payment) && $this->getConfig()->getInlineOrderReference() == Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID;
+ }
+
+ /**
+ * checks if the payment method can pbe processed via direct link
+ *
+ * @param Mage_Payment_Model_Info $payment
+ *
+ * @return bool
+ */
+ public function isInlinePayment(Mage_Payment_Model_Info $payment)
+ {
+ $result = false;
+ $methodInstance = $payment->getMethodInstance();
+ if ($methodInstance instanceof Netresearch_OPS_Model_Payment_DirectDebit
+ || ($methodInstance instanceof Netresearch_OPS_Model_Payment_Cc
+ && ($methodInstance->hasBrandAliasInterfaceSupport($payment)
+ || Mage::helper('ops/data')->isAdminSession()))
+ ) {
+ $result = true;
+ }
+
+ return $result;
+ }
+
+ /**
+ * checks if the inline payment can use quote id as merchant's reference
+ *
+ * @param Mage_Payment_Model_Info $payment
+ *
+ * @return bool
+ */
+ public function isInlinePaymentWithQuoteId(Mage_Payment_Model_Info $payment)
+ {
+ return $this->isInlinePayment($payment)
+ && (0 === strlen(
+ trim($payment->getMethodInstance()->getConfigPaymentAction())
+ ));
+ }
+
+ /**
+ * sets the invoices of an order to paid
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return Netresearch_OPS_Helper_Payment
+ */
+ public function setInvoicesToPaid($order)
+ {
+ /** @var $invoice Mage_Sales_Model_Order_Invoice */
+ foreach ($order->getInvoiceCollection() as $invoice) {
+ $invoice->setRequestedCaptureCase(Mage_Sales_Model_Order_Invoice::CAPTURE_ONLINE);
+ $invoice->setState(Mage_Sales_Model_Order_Invoice::STATE_PAID);
+ }
+ $order->getInvoiceCollection()->save();
+
+ return $this;
+ }
+
+ /**
+ * cancel all invoices for a given order
+ *
+ * @param $order
+ *
+ * @return Netresearch_OPS_Helper_Payment
+ * @throws Exception
+ */
+ public function cancelInvoices($order)
+ {
+ /** @var $invoice Mage_Sales_Model_Order_Invoice */
+ foreach ($order->getInvoiceCollection() as $invoice) {
+ $invoice->cancel();
+ $invoice->save();
+ }
+
+ return $this;
+ }
+
+ /**
+ * Returns if the current payment status is an invalid one, namely if it is one of the following:
+ * Netresearch_OPS_Model_Payment_Abstract::INVALID_INCOMPLETE,
+ * Netresearch_OPS_Model_Payment_Abstract::CANCELED_BY_CUSTOMER,
+ * Netresearch_OPS_Model_Payment_Abstract::AUTHORISATION_DECLINED,
+ *
+ * @param $status
+ *
+ * @return bool
+ */
+ public function isPaymentInvalid($status)
+ {
+ return in_array(
+ $status,
+ array(
+ Netresearch_OPS_Model_Status::INVALID_INCOMPLETE,
+ Netresearch_OPS_Model_Status::CANCELED_BY_CUSTOMER,
+ Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED,
+ )
+ );
+ }
+
+ /**
+ * @param $paymentCode
+ *
+ * @return string
+ */
+ public function getPaymentDefaultLogo($paymentCode)
+ {
+ return Mage::getSingleton('core/design_package')->getSkinUrl(
+ 'images/ops/logos/' . $paymentCode . '.png',
+ array('_area' => 'frontend')
+ );
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/Request.php b/app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/Request.php
new file mode 100644
index 0000000..8928186
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/Request.php
@@ -0,0 +1,333 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+
+abstract class Netresearch_OPS_Helper_Payment_DirectLink_Request
+ implements Netresearch_OPS_Helper_Payment_DirectLink_RequestInterface
+{
+
+ protected $dataHelper = null;
+
+ protected $quoteHelper = null;
+
+ protected $orderHelper = null;
+
+ protected $customerHelper = null;
+
+ protected $validator = null;
+
+ protected $requestHelper = null;
+
+ protected $config = null;
+
+ /**
+ * @param null $config
+ */
+ public function setConfig($config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig()
+ {
+ if (null === $this->config) {
+ $this->config = Mage::getModel('ops/config');
+ }
+ return $this->config;
+ }
+
+ public function setRequestHelper(Netresearch_OPS_Helper_Payment_Request $requestHelper)
+ {
+ $this->requestHelper = $requestHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Payment_Request
+ */
+ public function getRequestHelper()
+ {
+ if (null === $this->requestHelper) {
+ $this->requestHelper = Mage::helper('ops/payment_request');
+ $this->requestHelper->setConfig($this->getConfig());
+ }
+
+ return $this->requestHelper;
+ }
+
+ /**
+ * sets the data helper
+ *
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ */
+ public function setDataHelper(Netresearch_OPS_Helper_Data $dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+ }
+
+ /**
+ * gets the data helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getDataHelper()
+ {
+ if (null === $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+
+ /**
+ * sets the quote helper
+ *
+ * @param Netresearch_OPS_Helper_Quote $quoteHelper
+ */
+ public function setQuoteHelper(Netresearch_OPS_Helper_Quote $quoteHelper)
+ {
+ $this->quoteHelper = $quoteHelper;
+ }
+
+ /**
+ * gets the quote helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getQuoteHelper()
+ {
+ if (null === $this->quoteHelper) {
+ $this->quoteHelper = Mage::helper('ops/quote');
+ }
+
+ return $this->quoteHelper;
+ }
+
+ /**
+ * sets the order helper
+ *
+ * @param Netresearch_OPS_Helper_Order $orderHelper
+ */
+ public function setOrderHelper(Netresearch_OPS_Helper_Order $orderHelper)
+ {
+ $this->orderHelper = $orderHelper;
+ }
+
+ /**
+ * gets the order helper
+ *
+ * @return Netresearch_OPS_Helper_Order
+ */
+ public function getOrderHelper()
+ {
+ if (null === $this->orderHelper) {
+ $this->orderHelper = Mage::helper('ops/order');
+ }
+
+ return $this->orderHelper;
+ }
+
+ /**
+ * sets the customer helper
+ *
+ * @param Mage_Customer_Helper_Data $customerHelper
+ */
+ public function setCustomerHelper(Mage_Core_Helper_Abstract $customerHelper)
+ {
+ $this->customerHelper = $customerHelper;
+ }
+
+ /**
+ * gets the customer helper
+ *
+ * @return Mage_Customer_Helper_Data
+ */
+ public function getCustomerHelper()
+ {
+ if (null === $this->customerHelper) {
+ $this->customerHelper = Mage::helper('customer/data');
+ }
+
+ return $this->customerHelper;
+ }
+
+
+ /**
+ * extracts the parameter for the direct link request from the quote,
+ * order and, optionally from existing request params
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param Mage_Sales_Model_Order $order
+ * @param array $requestParams
+ *
+ * @return array - the parameters for the direct link request
+ */
+ public function getDirectLinkRequestParams(
+ Mage_Sales_Model_Quote $quote, Mage_Sales_Model_Order $order, $requestParams = array())
+ {
+ $billingAddress = $order->getBillingAddress();
+ $shippingAddress = $this->getShippingAddress($order, $billingAddress);
+ $requestParams = $this->getBaseRequestParams($quote, $order, $billingAddress);
+ $requestParams = array_merge($requestParams, $this->getPaymentSpecificParams($quote));
+
+ if ($this->getConfig()->canSubmitExtraParameter($quote->getStoreId())) {
+ $shipToParams = $this->getRequestHelper()->extractShipToParameters($shippingAddress, $quote);
+ $shipToParams = $this->decodeParamsForDirectLinkCall($shipToParams);
+ $requestParams = array_merge($requestParams, $shipToParams);
+ }
+
+ $requestParams = $this->addCustomerSpecificParams($requestParams);
+ $requestParams = $this->addParamsForAdminPayments($requestParams);
+
+ return $requestParams;
+ }
+
+ /**
+ * specail handling like validation and so on for admin payments
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param array $requestParams
+ *
+ * @return mixed
+ */
+ abstract public function handleAdminPayment(Mage_Sales_Model_Quote $quote, $requestParams);
+
+ /**
+ * extracts payment specific payment parameters
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return array
+ */
+ abstract protected function getPaymentSpecificParams(Mage_Sales_Model_Quote $quote);
+
+ /**
+ * gets the shipping address if there is one, otherwise the billing address is used as shipping address
+ *
+ * @param $order
+ * @param $billingAddress
+ *
+ * @return mixed
+ */
+ protected function getShippingAddress(Mage_Sales_Model_Order $order, $billingAddress)
+ {
+ $shippingAddress = $order->getShippingAddress();
+ if (null === $shippingAddress || false === $shippingAddress) {
+ $shippingAddress = $billingAddress;
+ }
+ return $shippingAddress;
+ }
+
+ /**
+ * utf8 decode for direct link calls
+ *
+ * @param array $requestParams
+ *
+ * @return array - the decoded array
+ */
+ protected function decodeParamsForDirectLinkCall(array $requestParams)
+ {
+ foreach ($requestParams as $key => $value) {
+ $requestParams[$key] = utf8_decode($value);
+ }
+ return $requestParams;
+ }
+
+ /**
+ * @param $requestParams
+ *
+ * @return mixed
+ */
+ protected function addCustomerSpecificParams($requestParams)
+ {
+ if ($this->getCustomerHelper()->isLoggedIn()) {
+ $requestParams['CUID'] = $this->getCustomerHelper()->getCustomer()->getId();
+ }
+ return $requestParams;
+ }
+
+ /**
+ * @param $requestParams
+ *
+ * @return mixed
+ */
+ protected function addParamsForAdminPayments($requestParams)
+ {
+ if ($this->getDataHelper()->isAdminSession()) {
+ $requestParams['ECI'] = Netresearch_OPS_Model_Eci_Values::MANUALLY_KEYED_FROM_MOTO;
+ $requestParams['REMOTE_ADDR'] = 'NONE';
+ }
+
+ return $requestParams;
+ }
+
+ /**
+ * @param $quote
+ * @param $order
+ * @param $billingAddress
+ *
+ * @return array
+ */
+ protected function getBaseRequestParams($quote, $order, $billingAddress)
+ {
+ $merchantRef = $this->getOrderHelper()->getOpsOrderId($order, $this->canUseOrderId($quote->getPayment()));
+ $requestParams = array(
+ 'AMOUNT' => $this->getDataHelper()->getAmount($quote->getBaseGrandTotal()),
+ 'CURRENCY' => $this->getQuoteHelper()->getQuoteCurrency($quote),
+ 'OPERATION' => $this->getQuoteHelper()->getPaymentAction($quote),
+ 'ORDERID' => $merchantRef,
+ 'ORIG' => $this->getDataHelper()->getModuleVersionString(),
+ 'EMAIL' => $order->getCustomerEmail(),
+ 'REMOTE_ADDR' => $quote->getRemoteIp(),
+ 'RTIMEOUT' => $this->getConfig()->getTransActionTimeout()
+ );
+
+ $ownerParams = $this->getOwnerParams($quote, $billingAddress, $requestParams);
+ $requestParams = array_merge($requestParams, $ownerParams);
+ $requestParams['ADDMATCH'] = $this->getOrderHelper()->checkIfAddressesAreSame($order);
+
+ return $requestParams;
+ }
+
+ /**
+ * @param $quote
+ * @param $billingAddress
+ * @param $requestParams
+ *
+ * @return array
+ */
+ protected function getOwnerParams($quote, $billingAddress, $requestParams)
+ {
+ $ownerParams = $this->getRequestHelper()->getOwnerParams($billingAddress, $quote);
+ if (array_key_exists('OWNERADDRESS', $ownerParams) && array_key_exists('OWNERTOWN', $ownerParams)) {
+ $ownerAddrParams = $this->decodeParamsForDirectLinkCall(
+ array('OWNERADDRESS' => $ownerParams['OWNERADDRESS'], 'OWNERTOWN' => $ownerParams['OWNERTOWN'])
+ );
+ $ownerParams = array_merge($ownerParams, $ownerAddrParams);
+ }
+
+ return $ownerParams;
+ }
+
+ /**
+ * @return bool
+ */
+ public function canUseOrderId(Varien_Object $payment)
+ {
+ $methodInstance = $payment->getMethodInstance();
+ return
+ $this->getConfig()->getInlineOrderReference() == Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID
+ && $methodInstance instanceof Netresearch_OPS_Model_Payment_DirectLink;
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/RequestInterface.php b/app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/RequestInterface.php
new file mode 100644
index 0000000..ab196b7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Payment/DirectLink/RequestInterface.php
@@ -0,0 +1,115 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * @author Michael Lühr
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+interface Netresearch_OPS_Helper_Payment_DirectLink_RequestInterface
+{
+ /**
+ * sets the data helper
+ *
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ */
+ public function setDataHelper(Netresearch_OPS_Helper_Data $dataHelper);
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig();
+
+ /**
+ * sets the quote helper
+ *
+ * @param Netresearch_OPS_Helper_Quote $quoteHelper
+ */
+ public function setQuoteHelper(Netresearch_OPS_Helper_Quote $quoteHelper);
+
+ /**
+ * extracts the parameter for the direct link request from the quote, order and, optionally from existing request params
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param Mage_Sales_Model_Order $order
+ * @param array $requestParams
+ *
+ * @return array - the parameters for the direct link request
+ */
+ public function getDirectLinkRequestParams(
+ Mage_Sales_Model_Quote $quote,
+ Mage_Sales_Model_Order $order,
+ $requestParams = array()
+ );
+
+ /**
+ * @param null $config
+ */
+ public function setConfig($config);
+
+ /**
+ * sets the order helper
+ *
+ * @param Netresearch_OPS_Helper_Order $orderHelper
+ */
+ public function setOrderHelper(Netresearch_OPS_Helper_Order $orderHelper);
+
+ /**
+ * sets the customer helper
+ *
+ * @param Mage_Core_Helper_Abstract $customerHelper
+ */
+ public function setCustomerHelper(Mage_Core_Helper_Abstract $customerHelper);
+
+ public function setRequestHelper(Netresearch_OPS_Helper_Payment_Request $requestHelper);
+
+ /**
+ * gets the customer helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getCustomerHelper();
+
+ /**
+ * gets the order helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getOrderHelper();
+
+ /**
+ * gets the data helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getDataHelper();
+
+ /**
+ * @return Netresearch_OPS_Helper_Payment_Request
+ */
+ public function getRequestHelper();
+
+ /**
+ * special handling like validation and so on for admin payments
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param $requestParams
+ *
+ * @return mixed
+ */
+ public function handleAdminPayment(Mage_Sales_Model_Quote $quote, $requestParams);
+
+ /**
+ * gets the quote helper
+ *
+ * @return Mage_Core_Helper_Abstract
+ */
+ public function getQuoteHelper();
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Payment/Request.php b/app/code/community/Netresearch/OPS/Helper/Payment/Request.php
new file mode 100644
index 0000000..a0b6a79
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Payment/Request.php
@@ -0,0 +1,738 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Helper_Payment_Request
+{
+ protected $config = null;
+
+ /**
+ * @param Netresearch_OPS_Model_Config $config
+ */
+ public function setConfig($config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig()
+ {
+ if ($this->config === null) {
+ $this->config = Mage::getModel('ops/config');
+ }
+
+ return $this->config;
+ }
+
+ /**
+ * extracts the ship to information from a given address
+ *
+ * @param Mage_Customer_Model_Address_Abstract $address
+ * @param Mage_Sales_Model_Quote || Mage_Sales_Model_Order $salesObject
+ *
+ * @return array - the parameters containing the ship to data
+ */
+ public function extractShipToParameters($address, $salesObject = null)
+ {
+ $paramValues = array();
+
+ if (!$address instanceof Mage_Customer_Model_Address_Abstract) {
+ // virtual carts may not have a shipping address - so fall back to billing
+ if (!is_null($salesObject) && $salesObject->getShippingAddress()) {
+ $address = $salesObject->getShippingAddress();
+ } else {
+ $address = $salesObject->getBillingAddress();
+ }
+
+ if (!$address) {
+ return $paramValues;
+ }
+ }
+
+ $shippingStreet = str_replace("\n", ' ', $address->getStreet(-1));
+ $splittedShippingStreet = Mage::Helper('ops/address')->splitStreet($shippingStreet);
+
+ $paramValues['ECOM_SHIPTO_POSTAL_CITY'] = $address->getCity();
+ $paramValues['ECOM_SHIPTO_POSTAL_POSTALCODE'] = $address->getPostcode();
+ $paramValues['ECOM_SHIPTO_POSTAL_STATE'] = $this->getIsoRegionCode($address);
+ $paramValues['ECOM_SHIPTO_POSTAL_COUNTRYCODE'] = $address->getCountry();
+ $paramValues['ECOM_SHIPTO_POSTAL_NAME_FIRST'] = $address->getFirstname();
+ $paramValues['ECOM_SHIPTO_POSTAL_NAME_LAST'] = $address->getLastname();
+ $paramValues['ECOM_SHIPTO_POSTAL_STREET_LINE1'] = $splittedShippingStreet['street_name'];
+ $paramValues['ECOM_SHIPTO_POSTAL_STREET_NUMBER'] = $splittedShippingStreet['street_number'];
+ $paramValues['ECOM_SHIPTO_POSTAL_STREET_LINE2'] = $splittedShippingStreet['supplement'];
+
+ return $paramValues;
+ }
+
+ /**
+ * Extracts the billing address parameters for the ECOM_BILLTO fields
+ *
+ * @param Mage_Customer_Model_Address_Abstract $address
+ * @param Mage_Sales_Model_Quote || Mage_Sales_Model_Order $salesObject
+ *
+ * @return string[] - array containing the ECOM_BILLTO parameters
+ */
+ public function extractBillToParameters($address, $salesObject = null)
+ {
+ $paramValues = array();
+
+ if (!$address instanceof Mage_Customer_Model_Address_Abstract) {
+ if (!is_null($salesObject)) {
+ $address = $salesObject->getBillingAddress();
+ }
+ if (!$address) {
+ return $paramValues;
+ }
+ }
+
+ $billingStreet = str_replace("\n", ' ', $address->getStreet(-1));
+ $splittedBillingStreet = Mage::Helper('ops/address')->splitStreet($billingStreet);
+
+ $paramValues['ECOM_BILLTO_POSTAL_CITY'] = $address->getCity();
+ $paramValues['ECOM_BILLTO_POSTAL_POSTALCODE'] = $address->getPostcode();
+ $paramValues['ECOM_BILLTO_POSTAL_COUNTY'] = $this->getIsoRegionCode($address);
+ $paramValues['ECOM_BILLTO_POSTAL_COUNTRYCODE'] = $address->getCountry();
+ $paramValues['ECOM_BILLTO_POSTAL_NAME_FIRST'] = $address->getFirstname();
+ $paramValues['ECOM_BILLTO_POSTAL_NAME_LAST'] = $address->getLastname();
+ $paramValues['ECOM_BILLTO_POSTAL_POSTALCODE'] = $address->getPostcode();
+ $paramValues['ECOM_BILLTO_POSTAL_STREET_LINE1'] = $splittedBillingStreet['street_name'];
+ $paramValues['ECOM_BILLTO_POSTAL_STREET_NUMBER'] = $splittedBillingStreet['street_number'];
+ $paramValues['ECOM_BILLTO_POSTAL_STREET_LINE2'] = $splittedBillingStreet['supplement'];
+ $paramValues['ECOM_BILLTO_POSTAL_STREET_LINE3'] = $address->getStreet(3);
+
+ return $paramValues;
+ }
+
+ /**
+ * extraxcts the according Ingenico ePayments owner* parameter
+ *
+ * @param Mage_Customer_Model_Address_Abstract $billingAddress
+ *
+ * @param Mage_Sales_Model_Quote|Mage_Sales_Model_Order $salesObject
+ *
+ * @return string[]
+ */
+ public function getOwnerParams(Mage_Customer_Model_Address_Abstract $billingAddress, $salesObject)
+ {
+ $ownerParams = array();
+ if ($this->getConfig()->canSubmitExtraParameter($salesObject->getStoreId())) {
+ $ownerParams = array(
+ 'OWNERADDRESS' => str_replace("\n", ' ', $billingAddress->getStreet(1)),
+ 'OWNERTOWN' => $billingAddress->getCity(),
+ 'OWNERZIP' => $billingAddress->getPostcode(),
+ 'OWNERTELNO' => $billingAddress->getTelephone(),
+ 'OWNERCTY' => $billingAddress->getCountry(),
+
+ 'ECOM_BILLTO_POSTAL_POSTALCODE' => $billingAddress->getPostcode(),
+ );
+ }
+
+ return $ownerParams;
+ }
+
+ /**
+ * Returns the template parameters and their dependencies
+ *
+ * @return array
+ */
+
+ public function getTemplateParams($storeId = null)
+ {
+ $formFields = array();
+ switch ($this->getConfig()->getConfigData('template')) {
+ case Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_MAGENTO_INTERNAL:
+ $formFields['TP'] = $this->getConfig()->getPayPageTemplate();
+ break;
+ case Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_TEMPLATE:
+ $formFields['TP'] = $this->getConfig()->getTemplateIdentifier($storeId);
+ break;
+ case Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_IFRAME:
+ $formFields['PARAMPLUS'] = 'IFRAME=1';
+ case Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_REDIRECT:
+ $formFields['PMLISTTYPE'] = $this->getConfig()->getConfigData('pmlist', $storeId);
+ $formFields['TITLE'] = $this->getConfig()->getConfigData('html_title', $storeId);
+ $formFields['BGCOLOR'] = $this->getConfig()->getConfigData('bgcolor', $storeId);
+ $formFields['TXTCOLOR'] = $this->getConfig()->getConfigData('txtcolor', $storeId);
+ $formFields['TBLBGCOLOR'] = $this->getConfig()->getConfigData('tblbgcolor', $storeId);
+ $formFields['TBLTXTCOLOR'] = $this->getConfig()->getConfigData('tbltxtcolor', $storeId);
+ $formFields['BUTTONBGCOLOR'] = $this->getConfig()->getConfigData('buttonbgcolor', $storeId);
+ $formFields['BUTTONTXTCOLOR'] = $this->getConfig()->getConfigData('buttontxtcolor', $storeId);
+ $formFields['FONTTYPE'] = $this->getConfig()->getConfigData('fonttype', $storeId);
+ $formFields['LOGO'] = $this->getConfig()->getConfigData('logo', $storeId);
+ $formFields['HOMEURL'] = $this->getConfig()->hasHomeUrl() ? $this->getConfig()->getContinueUrl(
+ array('redirect' => 'home')
+ ) : 'NONE';
+ $formFields['CATALOGURL'] = $this->getConfig()->hasCatalogUrl() ? $this->getConfig()->getContinueUrl(
+ array('redirect' => 'catalog')
+ ) : '';
+ break;
+ default:
+ break;
+ };
+
+ return $formFields;
+
+ }
+
+ /**
+ * extracts the region code in iso format (if possible)
+ *
+ * @param Mage_Customer_Model_Address_Abstract $address
+ *
+ * @return string - the region code in iso format
+ */
+ public function getIsoRegionCode(Mage_Customer_Model_Address_Abstract $address)
+ {
+ $regionCode = trim($address->getRegionCode());
+ $countryCode = $address->getCountry();
+ if ($this->isAlreadyIsoCode($regionCode, $countryCode)) {
+ return $regionCode;
+ }
+ if (0 === strpos($regionCode, $countryCode . '-')) {
+ return str_replace($countryCode . '-', '', $regionCode);
+ }
+
+ return $this->getRegionCodeFromMapping($countryCode, $regionCode);
+ }
+
+ /**
+ * checks if the given region code is already in iso format
+ *
+ * @param string $regionCode
+ * @param string $countryCode
+ *
+ * @return bool
+ */
+ protected function isAlreadyIsoCode($regionCode, $countryCode)
+ {
+ return ((strlen($regionCode) < 3 && !in_array($countryCode, array('AT')))
+ || (strlen($regionCode) === 3 && !in_array($countryCode, array('DE'))));
+ }
+
+ protected function getRegionCodeFromMapping($countryCode, $regionCode)
+ {
+ $countryRegionMapping = $this->getCountryRegionMapping($countryCode);
+ if (array_key_exists($regionCode, $countryRegionMapping)) {
+ return $countryRegionMapping[$regionCode];
+ }
+
+ return $countryCode;
+ }
+
+ /**
+ * retrieves country specific region mapping
+ *
+ * @param $countryCode
+ *
+ * @return array - the country specific region mapping or empty array if mapping could not be found
+ */
+ protected function getCountryRegionMapping($countryCode)
+ {
+ if (strtoupper($countryCode) === 'DE') {
+ return $this->getRegionMappingForGermany();
+ }
+ if (strtoupper($countryCode) === 'AT') {
+ return $this->getRegionMappingForAustria();
+ }
+ if (strtoupper($countryCode) === 'ES') {
+ return $this->getRegionMappingForSpain();
+ }
+ if (strtoupper($countryCode) === 'FI') {
+ return $this->getRegionsMappingForFinland();
+ }
+ if (strtoupper($countryCode) === 'LV') {
+ return $this->getRegionsMappingForLatvia();
+ }
+
+ return array();
+ }
+
+ /**
+ * translates the Magento's region code for germany into ISO format
+ *
+ * @return array
+ */
+ protected function getRegionMappingForGermany()
+ {
+ return array(
+ 'NDS' => 'NI',
+ 'BAW' => 'BW',
+ 'BAY' => 'BY',
+ 'BER' => 'BE',
+ 'BRG' => 'BB',
+ 'BRE' => 'HB',
+ 'HAM' => 'HH',
+ 'HES' => 'HE',
+ 'MEC' => 'MV',
+ 'NRW' => 'NW',
+ 'RHE' => 'RP',
+ 'SAR' => 'SL',
+ 'SAS' => 'SN',
+ 'SAC' => 'ST',
+ 'SCN' => 'SH',
+ 'THE' => 'TH'
+ );
+ }
+
+ /**
+ * translates the Magento's region code for austria into ISO format
+ *
+ * @return array
+ */
+ protected function getRegionMappingForAustria()
+ {
+ return array(
+ 'WI' => '9',
+ 'NO' => '3',
+ 'OO' => '4',
+ 'SB' => '5',
+ 'KN' => '2',
+ 'ST' => '6',
+ 'TI' => '7',
+ 'BL' => '1',
+ 'VB' => '8'
+ );
+ }
+
+ /**
+ * translates the Magento's region code for spain into ISO format
+ *
+ * @return array
+ */
+ protected function getRegionMappingForSpain()
+ {
+ return array(
+ 'A Coruсa' => 'C',
+ 'Alava' => 'VI',
+ 'Albacete' => 'AB',
+ 'Alicante' => 'A',
+ 'Almeria' => 'AL',
+ 'Asturias' => 'O',
+ 'Avila' => 'AV',
+ 'Badajoz' => 'BA',
+ 'Baleares' => 'PM',
+ 'Barcelona' => 'B',
+ 'Caceres' => 'CC',
+ 'Cadiz' => 'CA',
+ 'Cantabria' => 'S',
+ 'Castellon' => 'CS',
+ 'Ceuta' => 'CE',
+ 'Ciudad Real' => 'CR',
+ 'Cordoba' => 'CO',
+ 'Cuenca' => 'CU',
+ 'Girona' => 'GI',
+ 'Granada' => 'GR',
+ 'Guadalajara' => 'GU',
+ 'Guipuzcoa' => 'SS',
+ 'Huelva' => 'H',
+ 'Huesca' => 'HU',
+ 'Jaen' => 'J',
+ 'La Rioja' => 'LO',
+ 'Las Palmas' => 'GC',
+ 'Leon' => 'LE',
+ 'Lleida' => 'L',
+ 'Lugo' => 'LU',
+ 'Madrid' => 'M',
+ 'Malaga' => 'MA',
+ 'Melilla' => 'ML',
+ 'Murcia' => 'MU',
+ 'Navarra' => 'NA',
+ 'Ourense' => 'OR',
+ 'Palencia' => 'P',
+ 'Pontevedra' => 'PO',
+ 'Salamanca' => 'SA',
+ 'Santa Cruz de Tenerife' => 'TF',
+ 'Segovia' => 'Z',
+ 'Sevilla' => 'SG',
+ 'Soria' => 'SE',
+ 'Tarragona' => 'SO',
+ 'Teruel' => 'T',
+ 'Toledo' => 'TE',
+ 'Valencia' => 'TO',
+ 'Valladolid' => 'V',
+ 'Vizcaya' => 'VA',
+ 'Zamora' => 'BI',
+ 'Zaragoza' => 'ZA',
+ );
+ }
+
+ /**
+ * translates the Magento's region code for finland into ISO format
+ *
+ * @return array
+ */
+ protected function getRegionsMappingForFinland()
+ {
+ return array(
+ 'Lappi' => '10',
+ 'Pohjois-Pohjanmaa' => '14',
+ 'Kainuu' => '05',
+ 'Pohjois-Karjala' => '13',
+ 'Pohjois-Savo' => '15',
+ 'Etelä-Savo' => '04',
+ 'Etelä-Pohjanmaa' => '03',
+ 'Pohjanmaa' => '12',
+ 'Pirkanmaa' => '11',
+ 'Satakunta' => '17',
+ 'Keski-Pohjanmaa' => '07',
+ 'Keski-Suomi' => '08',
+ 'Varsinais-Suomi' => '19',
+ 'Etelä-Karjala' => '02',
+ 'Päijät-Häme' => '16',
+ 'Kanta-Häme' => '06',
+ 'Uusimaa' => '18',
+ 'Itä-Uusimaa' => '19',
+ 'Kymenlaakso' => '09',
+ 'Ahvenanmaa' => '01'
+ );
+ }
+
+ /**
+ * translates the Magento's region code for latvia into ISO format
+ *
+ * @return array
+ */
+ protected function getRegionsMappingForLatvia()
+ {
+ return array(
+ 'Ādažu novads' => 'LV',
+ 'Aglonas novads' => '001',
+ 'Aizputes novads' => '003',
+ 'Aknīstes novads' => '004',
+ 'Alojas novads' => '005',
+ 'Alsungas novads' => '006',
+ 'Amatas novads' => '008',
+ 'Apes novads' => '009',
+ 'Auces novads' => '010',
+ 'Babītes novads' => '012',
+ 'Baldones novads' => '013',
+ 'Baltinavas novads' => '014',
+ 'Beverīnas novads' => '017',
+ 'Brocēnu novads' => '018',
+ 'Burtnieku novads' => '019',
+ 'Carnikavas novads' => '020',
+ 'Cesvaines novads' => '021',
+ 'Ciblas novads' => '023',
+ 'Dagdas novads' => '024',
+ 'Dundagas novads' => '027',
+ 'Durbes novads' => '028',
+ 'Engures novads' => '029',
+ 'Ērgļu novads' => 'LV',
+ 'Garkalnes novads' => '031',
+ 'Grobiņas novads' => '032',
+ 'Iecavas novads' => '034',
+ 'Ikšķiles novads' => '035',
+ 'Ilūkstes novads' => '036',
+ 'Inčukalna novads' => '037',
+ 'Jaunjelgavas novads' => '038',
+ 'Jaunpiebalgas novads' => '039',
+ 'Jaunpils novads' => '040',
+ 'Jēkabpils' => '042',
+ 'Kandavas novads' => '043',
+ 'Kārsavas novads' => 'LV',
+ 'Ķeguma novads' => 'LV',
+ 'Ķekavas novads' => 'LV',
+ 'Kokneses novads' => '046',
+ 'Krimuldas novads' => '048',
+ 'Krustpils novads' => '049',
+ 'Lielvārdes novads' => '053',
+ 'Līgatnes novads' => 'LV',
+ 'Līvānu novads' => '056',
+ 'Lubānas novads' => '057',
+ 'Mālpils novads' => '061',
+ 'Mārupes novads' => '062',
+ 'Mazsalacas novads' => '060',
+ 'Naukšēnu novads' => '064',
+ 'Neretas novads' => '065',
+ 'Nīcas novads' => '066',
+ 'Olaines novads' => '068',
+ 'Ozolnieku novads' => '069',
+ 'Pārgaujas novads' => 'LV',
+ 'Pāvilostas novads' => '070',
+ 'Pļaviņu novads' => '072',
+ 'Priekules novads' => '074',
+ 'Priekuļu novads' => '075',
+ 'Raunas novads' => '076',
+ 'Riebiņu novads' => '078',
+ 'Rojas novads' => '079',
+ 'Ropažu novads' => '080',
+ 'Rucavas novads' => '081',
+ 'Rugāju novads' => '082',
+ 'Rūjienas novads' => '084',
+ 'Rundāles novads' => '083',
+ 'Salacgrīvas novads' => '085',
+ 'Salas novads' => '086',
+ 'Salaspils novads' => '087',
+ 'Saulkrastu novads' => '089',
+ 'Sējas novads' => 'LV',
+ 'Siguldas novads' => '091',
+ 'Skrīveru novads' => '092',
+ 'Skrundas novads' => '093',
+ 'Smiltenes novads' => '094',
+ 'Stopiņu novads' => '095',
+ 'Strenču novads' => '096',
+ 'Tērvetes novads' => '098',
+ 'Vaiņodes novads' => '100',
+ 'Valmiera' => 'LV',
+ 'Varakļānu novads' => '102',
+ 'Vārkavas novads' => 'LV',
+ 'Vecpiebalgas novads' => '104',
+ 'Vecumnieku novads' => '105',
+ 'Viesītes novads' => '107',
+ 'Viļakas novads' => '108',
+ 'Viļānu novads' => '109',
+ 'Zilupes novads' => '110'
+ );
+ }
+
+ /**
+ * Returns the mandatory fields for requests to Ingenico ePayments
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return array
+ */
+
+ public function getMandatoryRequestFields(Mage_Sales_Model_Order $order)
+ {
+ $payment = $order->getPayment()->getMethodInstance();
+ $opsOrderId = Mage::helper('ops/order')->getOpsOrderId($order);
+ $formFields = array();
+ $formFields['PSPID'] = $this->getConfig()->getPSPID($order->getStoreId());
+ $formFields['AMOUNT'] = Mage::helper('ops')->getAmount($order->getBaseGrandTotal());
+ $formFields['CURRENCY'] = Mage::app()->getStore()->getBaseCurrencyCode();
+ $formFields['ORDERID'] = $opsOrderId;
+ $formFields['LANGUAGE'] = Mage::app()->getLocale()->getLocaleCode();
+ $formFields['PM'] = $payment->getOpsCode($order->getPayment());
+ $formFields['EMAIL'] = $order->getCustomerEmail();
+
+ $formFields['ACCEPTURL'] = $this->getConfig()->getAcceptUrl();
+ $formFields['DECLINEURL'] = $this->getConfig()->getDeclineUrl();
+ $formFields['EXCEPTIONURL'] = $this->getConfig()->getExceptionUrl();
+ $formFields['CANCELURL'] = $this->getConfig()->getCancelUrl();
+
+ $formFields['BACKURL'] = $this->getConfig()->getPaymentRetryUrl(
+ Mage::helper('ops/payment')->validateOrderForReuse($opsOrderId, $order->getStoreId())
+ );
+
+ $formFields['FP_ACTIV'] = $this->isFingerPrintingActive($order) ? '1' : '0';
+
+ return $formFields;
+ }
+
+ /**
+ * Will return the combination of activiation via config and the state of consent of the customer
+ *
+ * @param $order
+ *
+ * @return bool
+ */
+ protected function isFingerPrintingActive($order)
+ {
+ return $this->getConfig()->getDeviceFingerPrinting($order->getStoreId())
+ && Mage::getSingleton('customer/session')->getData(
+ Netresearch_OPS_Model_Payment_Abstract::FINGERPRINT_CONSENT_SESSION_KEY
+ );
+ }
+
+ /**
+ * Extracts the order item parameters and puts them in a array like
+ *
+ * @param Mage_Sales_Model_Order|Mage_Sales_Model_Order_Invoice $salesObject
+ *
+ * @return mixed[]
+ */
+ public function extractOrderItemParameters($salesObject)
+ {
+ $formFields = array();
+ $formatAmounts = $salesObject instanceof Mage_Sales_Model_Order_Invoice;
+ // add order items
+ $count = 1;
+ $addItemCount = function (&$value, $key, $count) use (&$formFields) {
+ $formFields[$key . $count] = $value;
+ };
+ foreach ($salesObject->getAllItems() as $item) {
+ if ($this->isNonDataItem($item)) {
+ continue;
+ }
+
+ $itemFields = $this->getItemFormFields($item, $formatAmounts);
+ array_walk($itemFields, $addItemCount, $count);
+ $count++;
+ }
+
+ // add discount item
+ /** @var mixed|false $discountItemFormFields */
+ $discountItemFormFields = $this->getDiscountItemFormFields($salesObject, $formatAmounts);
+ if ($discountItemFormFields) {
+ array_walk($discountItemFormFields, $addItemCount, $count);
+ $count++;
+ }
+
+ // add shipping item
+ /** @var mixed|false $shippingItemFields */
+ $shippingItemFields = $this->getShippingItemFormFields($salesObject, $formatAmounts);
+ if ($shippingItemFields) {
+ array_walk($shippingItemFields, $addItemCount, $count);
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * @param Mage_Sales_Model_Order_Item|Mage_Sales_Model_Order_Invoice_Item $item
+ *
+ * @return bool
+ */
+ protected function isNonDataItem($item)
+ {
+ if ($item instanceof Mage_Sales_Model_Order_Invoice_Item) {
+ $item = $item->getOrderItem();
+ }
+
+ return $item->getParentItemId()
+ && $item->getParentItem()->getProductType() == Mage_Catalog_Model_Product_Type::TYPE_CONFIGURABLE
+ || $item->getProductType() == Mage_Catalog_Model_Product_Type::TYPE_BUNDLE;
+ }
+
+ /**
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return float
+ */
+
+ public function getShippingTaxRate($order)
+ {
+ $store = $order->getStore();
+ $taxCalculation = Mage::getModel('tax/calculation');
+ $request = $taxCalculation->getRateRequest(null, null, null, $store);
+ $taxRateId = Mage::getStoreConfig('tax/classes/shipping_tax_class', $store);
+ //taxRateId is the same model id as product tax classes, so you can do this:
+ $percent = $taxCalculation->getRate($request->setProductClassId($taxRateId));
+
+ return $percent;
+ }
+
+ /**
+ * Genereates item array for shipping, returns false if order is virtual
+ *
+ * @param Mage_Sales_Model_Order|Mage_Sales_Model_Order_Invoice $salesObject
+ * @param bool $formatAmount
+ *
+ * @return mixed[] | false
+ */
+ protected function getShippingItemFormFields($salesObject, $formatAmount = false)
+ {
+
+ if ($salesObject instanceof Mage_Sales_Model_Order_Invoice) {
+ /** @var Mage_Sales_Model_Order_Invoice $salesObject */
+ $order = $salesObject->getOrder();
+ } else {
+ /** @var Mage_Sales_Model_Order $salesObject */
+ $order = $salesObject;
+ }
+ /** @var string $taxRate */
+ $taxRate = str_replace(',', '.', (string)(float)$this->getShippingTaxRate($order)) . '%';
+
+ if ($order->getIsNotVirtual() && 0 < $salesObject->getBaseShippingInclTax()) {
+ $formFields = array();
+
+ if ($formatAmount) {
+ $amount = Mage::helper('ops')->getAmount($salesObject->getBaseShippingInclTax());
+ } else {
+ $amount = number_format($salesObject->getBaseShippingInclTax(), 2, '.', '');
+ }
+
+ /* add shipping item */
+ $formFields['ITEMID'] = 'SHIPPING';
+ $formFields['ITEMNAME'] = substr($order->getShippingDescription(), 0, 25);
+ $formFields['ITEMPRICE'] = $amount;
+ $formFields['TAXINCLUDED'] = 1;
+ $formFields['ITEMQUANT'] = 1;
+ $formFields['ITEMVATCODE'] = $taxRate;
+
+ return $formFields;
+ }
+
+ return false;
+ }
+
+ /**
+ * Returns item array for Ingenico ePayments request for the specified item
+ *
+ * @param Mage_Sales_Model_Order_Invoice_Item|Mage_Sales_Model_Order_Item $item
+ * @param bool $formatAmount
+ *
+ * @return array
+ */
+ protected function getItemFormFields($item, $formatAmount = false)
+ {
+ $formFields = array();
+ $formFields['ITEMID'] = $item->getItemId() ?: $item->getOrderItemId();
+ $formFields['ITEMNAME'] = substr($item->getName(), 0, 40);
+ if ($formatAmount) {
+ $amount = Mage::helper('ops')->getAmount($item->getBasePriceInclTax());
+ } else {
+ $amount = number_format($item->getBasePriceInclTax(), 2, '.', '');
+ }
+ $formFields['ITEMPRICE'] = $amount;
+ $formFields['ITEMQUANT'] = (int)$item->getQtyOrdered() ?: $item->getQty();
+ $formFields['ITEMVATCODE'] = str_replace(',', '.', (string)(float)$item->getTaxPercent()) . '%';
+ $formFields['TAXINCLUDED'] = 1;
+
+ return $formFields;
+ }
+
+ /**
+ * Creates array
+ *
+ * @param Mage_Sales_Model_Abstract $salesObject
+ * @param bool $formatAmount
+ *
+ * @return bool|mixed[]
+ */
+ protected function getDiscountItemFormFields(Mage_Sales_Model_Abstract $salesObject, $formatAmount = false)
+ {
+ $formFields = array();
+ if ($salesObject instanceof Mage_Sales_Model_Order_Invoice) {
+ $order = $salesObject->getOrder();
+ } else {
+ $order = $salesObject;
+ }
+ /** @var Mage_Sales_Model_Order $order */
+ /* add coupon item */
+ if ($salesObject->getBaseDiscountAmount() != 0.00) {
+ $couponRuleName = 'DISCOUNT';
+ if ($order->getCouponRuleName() && strlen(trim($order->getCouponRuleName())) > 0) {
+ $couponRuleName = substr(trim($order->getCouponRuleName()), 0, 30);
+ }
+
+ if ($formatAmount) {
+ $couponAmount = Mage::helper('ops')->getAmount($salesObject->getBaseDiscountAmount());
+ } else {
+ $couponAmount = number_format($salesObject->getBaseDiscountAmount(), 2, '.', '');
+ }
+
+ $formFields['ITEMID'] = 'DISCOUNT';
+ $formFields['ITEMNAME'] = $couponRuleName;
+ $formFields['ITEMPRICE'] = $couponAmount;
+ $formFields['ITEMQUANT'] = 1;
+ $formFields['ITEMVATCODE']
+ = str_replace(',', '.', (string)(float)$this->getShippingTaxRate($order)) . '%';
+ $formFields['TAXINCLUDED'] = 1;
+
+ return $formFields;
+
+ }
+
+ return false;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Helper/Quote.php b/app/code/community/Netresearch/OPS/Helper/Quote.php
new file mode 100644
index 0000000..51c4370
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Quote.php
@@ -0,0 +1,164 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Helper_Quote extends Mage_Core_Helper_Abstract
+{
+
+ const PAGE_SIZE = 100;
+
+ const MINUTES_IN_PAST = 15;
+
+ protected $dataHelper = null;
+
+ /**
+ * cleans up old payment information (deletes cvc etc. from additional data)
+ */
+ public function cleanUpOldPaymentInformation()
+ {
+ $allowedTimestamp = new Zend_Db_Expr(
+ sprintf(
+ 'NOW() - INTERVAL %d MINUTE', self::MINUTES_IN_PAST
+ )
+ );
+ /*
+ * fetching possible affected information from the sales_quote_payment table
+ * criteria are:
+ * - ops_cc was used
+ * - the last update is more than 15 minutes ago
+ * - and CVC is included in the additional information
+ */
+ $paymentInformation = Mage::getModel('sales/quote_payment')
+ ->getCollection()
+ ->addFieldToFilter('method', array('eq' => 'ops_cc'))
+ ->addFieldToFilter('updated_at', array('lt' => $allowedTimestamp))
+ ->addFieldToFilter(
+ 'additional_information', array('like' => '%"cvc"%')
+ )
+ ->setOrder('created_at', 'DESC')
+ ->setPageSize(self::PAGE_SIZE);
+ foreach ($paymentInformation as $payment) {
+ if (null != $payment->getAdditionalInformation('cvc')) {
+ // quote needs to be loaded, because saving the payment information would fail otherwise
+ $payment->setQuote(
+ Mage::getModel('sales/quote')->load($payment->getQuoteId())
+ );
+ Mage::helper('ops/alias')->cleanUpAdditionalInformation(
+ $payment, true
+ );
+ $payment->save();
+ }
+
+ }
+
+
+ }
+
+ /**
+ * returns the quote currency
+ *
+ * @param $quote
+ *
+ * @return string - the quotes currency
+ */
+ public function getQuoteCurrency(Mage_Sales_Model_Quote $quote)
+ {
+ if ($quote->hasForcedCurrency()) {
+ return $quote->getForcedCurrency()->getCode();
+ } else {
+ return Mage::app()->getStore($quote->getStoreId())
+ ->getBaseCurrencyCode();
+ }
+ }
+
+ /**
+ * get payment operation code
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return string
+ */
+ public function getPaymentAction($order)
+ {
+ $operation
+ = Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION;
+
+ // different capture operation name for direct debits
+ if ('Direct Debits DE' == $order->getPayment()
+ ->getAdditionalInformation('PM')
+ || 'Direct Debits AT' == $order->getPayment()
+ ->getAdditionalInformation('PM')
+ ) {
+ if ('authorize_capture' == Mage::getModel('ops/config')
+ ->getPaymentAction($order->getStoreId())
+ ) {
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION;
+ }
+
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION;
+ }
+ // no RES for Direct Debits NL, so we'll do the final sale
+ if ('Direct Debits NL' == $order->getPayment()
+ ->getAdditionalInformation('PM')
+ ) {
+ if ('authorize_capture' == Mage::getModel('ops/config')
+ ->getPaymentAction($order->getStoreId())
+ ) {
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_DIRECTDEBIT_NL;
+ }
+
+ return Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION;
+ }
+
+ if ('authorize_capture' == Mage::getModel('ops/config')
+ ->getPaymentAction($order->getStoreId())
+ ) {
+ $operation
+ = Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION;
+ }
+
+ return $operation;
+ }
+
+ /**
+ * @return Mage_Sales_Model_Quote
+ */
+ public function getQuote()
+ {
+ if (Mage::app()->getStore()->isAdmin()) {
+ return Mage::getSingleton('adminhtml/session_quote')->getQuote();
+ }
+
+ return Mage::getSingleton('checkout/session')->getQuote();
+ }
+
+ /**
+ * gets the data helper
+ *
+ * @return Netresearch_OPS_Helper_Data
+ */
+ public function getDataHelper()
+ {
+ if (null === $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+
+ /**
+ * sets the data helper
+ *
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ */
+ public function setDataHelper(Netresearch_OPS_Helper_Data $dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Subscription.php b/app/code/community/Netresearch/OPS/Helper/Subscription.php
new file mode 100644
index 0000000..82aef59
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Subscription.php
@@ -0,0 +1,148 @@
+
+ */
+class Netresearch_OPS_Helper_Subscription extends Mage_Core_Helper_Abstract
+{
+ const SUBSCRIPTION_PREFIX = 'SUB-';
+ const TRIAL_SUFFIX = '-TRIAL';
+
+ /**
+ * Generates subscription id in the following pattern:
+ *
+ * SUB-subscriptionId-TRIAL
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile - the profile itself
+ * @param bool $withTrial - if you wish the trial suffix appended in case the profile has a trial subscription
+ *
+ * @return string
+ */
+ public function generateSubscriptionId(Mage_Payment_Model_Recurring_Profile $profile, $withTrial = false)
+ {
+ $config = Mage::getModel('ops/config');
+ $devPrefix = $config->getConfigData('devprefix');
+
+ $subscriptionId = self::SUBSCRIPTION_PREFIX . $profile->getId();
+ if ($profile->getTrialPeriodUnit() && $withTrial) {
+ $subscriptionId .= self::TRIAL_SUFFIX;
+ }
+
+ return $devPrefix . $subscriptionId;
+ }
+
+ /**
+ * Determine if the given request parameters belong to a subscription
+ *
+ * @param $requestParams
+ *
+ * @return bool
+ */
+ public function isSubscriptionFeedback($requestParams)
+ {
+ $result = false;
+ if (is_array($requestParams)
+ && array_key_exists('orderID', $requestParams)
+ && false != strstr($this->removeDevPrefix($requestParams['orderID']), self::SUBSCRIPTION_PREFIX)
+ ) {
+ $result = true;
+ }
+
+ return $result;
+ }
+
+ /**
+ * Loads the recurring profile for the given ORDERID
+ *
+ * @param $orderId
+ *
+ * @throws Mage_Core_Exception if no profile could be found
+ *
+ * @return Mage_Sales_Model_Order
+ * @throws Mage_Core_Exception
+ */
+ public function getProfileForSubscription($orderId)
+ {
+ $orderId = $this->removeDevPrefix($orderId);
+
+ if ($this->isTrialFeedback($orderId)) {
+ $orderId = substr($orderId, -0, strlen(self::TRIAL_SUFFIX));
+ }
+ $orderId = substr($orderId, strlen(self::SUBSCRIPTION_PREFIX));
+ $profile = Mage::getModel('sales/recurring_profile')->load($orderId);
+ if (!$profile->getId()) {
+ Mage::throwException('Could find no subscription for id ' . $orderId);
+ }
+
+ return $profile;
+ }
+
+ /**
+ * Determines via the given orderId if the feedback request was a from a trial subscription
+ *
+ * @param string $orderId
+ *
+ * @return bool
+ */
+ public function isTrialFeedback($orderId)
+ {
+ return (bool)strstr($orderId, self::TRIAL_SUFFIX);
+ }
+
+ /**
+ * Determine day of billing according to the period unit of the subscription
+ *
+ * @param string $periodUnit @see Mage_Payment_Model_Recurring_Profile
+ * @param int $storeId
+ *
+ * @return int
+ */
+ public function getBillingDayForPeriodUnit($periodUnit, $storeId = null)
+ {
+ $config = Mage::getModel('ops/config');
+ $day = 1;
+
+ switch ($periodUnit) {
+ case Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_MONTH:
+ $day = $config->getMonthlyBillingDay($storeId);
+ break;
+ case Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_WEEK:
+ // offset the day by one, since Magento counts from 0, but Ingenico ePayments from 1
+ $day = $config->getWeeklyBillingDay($storeId) + 1;
+ break;
+ }
+
+ return $day;
+ }
+
+ protected function removeDevPrefix($orderId)
+ {
+ $config = Mage::getModel('ops/config');
+ $devPrefix = $config->getConfigData('devprefix');
+ $orderId = substr($orderId, strlen($devPrefix));
+ return $orderId;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Validation/Checkout/Step.php b/app/code/community/Netresearch/OPS/Helper/Validation/Checkout/Step.php
new file mode 100644
index 0000000..b4ecb56
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Validation/Checkout/Step.php
@@ -0,0 +1,98 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Helper_Validation_Checkout_Step
+{
+
+ const BILLING_STEP = 'billing';
+
+ const SHIPPING_STEP = 'shipping';
+
+ const BILLING_PARAMETER_STRING_VALUE = 'billing';
+
+ const SHIPPING_PARAMETER_STRING_VALUE = 'shipping';
+
+ /**
+ * retrieves the params for pushing back to the billing step
+ *
+ * @return array
+ */
+ protected function determineStep()
+ {
+ $result = array();
+ $mappedParams = $this->getMappedParams();
+
+ foreach ($mappedParams as $paramName => $value) {
+ if (strpos($value, self::BILLING_PARAMETER_STRING_VALUE) === 0) {
+ $result[self::BILLING_PARAMETER_STRING_VALUE][] = $paramName;
+ }
+ if (strpos($value, self::SHIPPING_PARAMETER_STRING_VALUE) === 0) {
+ $result[self::SHIPPING_STEP][] = $paramName;
+ }
+ }
+
+ return $result;
+ }
+
+
+ protected function getMappedParams()
+ {
+ $result = array();
+ $paramLengthFields = $this->getConfig()->getParameterLengths();
+ $frontendFieldMapping = $this->getConfig()->getFrontendFieldMapping();
+
+ foreach (array_keys($paramLengthFields) as $key) {
+ if (isset($frontendFieldMapping[$key])) {
+ $frontendField = !is_array($frontendFieldMapping[$key])
+ ? $frontendFieldMapping[$key]
+ : implode(
+ ',', $frontendFieldMapping[$key]
+ );
+ $result[$key] = $frontendField;
+ }
+ }
+
+ return $result;
+ }
+
+ /**
+ * gets the corresponding checkout step for the erroneous fields
+ *
+ * @param array $erroneousFields
+ *
+ * @return string - the checkout step
+ */
+ public function getStep(array $erroneousFields)
+ {
+ $checkoutStep = '';
+ $stepParams = $this->determineStep();
+ foreach ($erroneousFields as $erroneousField) {
+ if (isset($stepParams[self::BILLING_STEP])
+ && in_array($erroneousField, $stepParams[self::BILLING_STEP])
+ ) {
+ $checkoutStep = self::BILLING_STEP;
+ break;
+ }
+ if (isset($stepParams[self::SHIPPING_STEP])
+ && in_array($erroneousField, $stepParams[self::SHIPPING_STEP])
+ ) {
+ $checkoutStep = self::SHIPPING_STEP;
+ }
+ }
+
+ return $checkoutStep;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ protected function getConfig()
+ {
+ return Mage::getModel('ops/config');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Validation/Result.php b/app/code/community/Netresearch/OPS/Helper/Validation/Result.php
new file mode 100644
index 0000000..992c57d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Validation/Result.php
@@ -0,0 +1,210 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+
+
+class Netresearch_OPS_Helper_Validation_Result
+{
+
+ protected $checkoutStepHelper = null;
+
+ protected $config = null;
+
+ protected $formBlock = null;
+
+ protected $dataHelper = null;
+
+ protected $result = array();
+
+ /**
+ * @param array $result
+ */
+ public function setResult(array $result)
+ {
+ $this->result = $result;
+ }
+
+ /**
+ * @return array
+ */
+ public function getResult()
+ {
+ return $this->result;
+ }
+
+ /**
+ * @param null $checkOutStepHelper
+ */
+ public function setCheckoutStepHelper($checkOutStepHelper)
+ {
+ $this->checkoutStepHelper = $checkOutStepHelper;
+ }
+
+ /**
+ * @return null
+ */
+ public function getCheckoutStepHelper()
+ {
+ if (null === $this->checkoutStepHelper) {
+ $this->checkoutStepHelper = Mage::helper('ops/validation_checkout_step');
+ }
+
+ return $this->checkoutStepHelper;
+ }
+
+ /**
+ * @param null $config
+ */
+ public function setConfig($config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @return null
+ */
+ public function getConfig()
+ {
+ if (null === $this->config) {
+ $this->config = Mage::getModel('ops/config');
+ }
+
+ return $this->config;
+ }
+
+ /**
+ * @param null $dataHelper
+ */
+ public function setDataHelper($dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+ }
+
+ /**
+ * @return null
+ */
+ public function getDataHelper()
+ {
+ if (null === $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+
+ /**
+ * @param null $formBlock
+ */
+ public function setFormBlock($formBlock)
+ {
+ $this->formBlock = $formBlock;
+ }
+
+ /**
+ * @return Netresearch_OPS_Block_Form
+ */
+ public function getFormBlock()
+ {
+ if (null === $this->formBlock) {
+ $this->formBlock = Mage::getBlockSingleton('ops/form');
+ }
+
+ return $this->formBlock;
+ }
+
+
+
+ /**
+ * @param array $messages
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return array
+ */
+ public function getValidationFailedResult($messages, $quote)
+ {
+ $gotoSection = $this->getCheckoutStepHelper()->getStep(array_keys($messages));
+ $this->setBaseErroneousFields($messages, $gotoSection);
+ $this->getFields($messages);
+ $this->addErrorToExistingAddress($quote, $gotoSection);
+ $this->cleanResult();
+
+ return $this->getResult();
+ }
+
+ /**
+ * @param $messages
+ *
+ * @return mixed
+ */
+ protected function getFields($messages)
+ {
+ $mappedFields = $this->getConfig()->getFrontendFieldMapping();
+ $frontendFields = array();
+ foreach ($messages as $key => $value) {
+ if (array_key_exists($key, $mappedFields)) {
+ $frontendFields = $this->getFormBlock()->getFrontendValidationFields(
+ $mappedFields,
+ $key,
+ $value,
+ $frontendFields
+ );
+ }
+ }
+ $this->result['fields'] = $frontendFields;
+
+ return $this;
+ }
+
+ /**
+ * @param Mage_Sales_Model_Quote $quote
+ * @param string $gotoSection
+ *
+ * @return $this
+ */
+ protected function addErrorToExistingAddress($quote, $gotoSection)
+ {
+ if ($gotoSection == 'billing' && 0 < $quote->getBillingAddress()->getId()) {
+ $this->result['fields']['billing-address-select'] = $this->getDataHelper()->__(
+ 'Billing address contains invalid data'
+ );
+ }
+ if ($gotoSection == 'shipping' && 0 < $quote->getShippingAddress()->getId()) {
+ $this->result['fields']['shipping-address-select'] = $this->getDataHelper()->__(
+ 'Shipping address contains invalid data'
+ );
+ }
+
+ return $this;
+ }
+
+ /**
+ * @param string[] $messages
+ * @param string $gotoSection
+ *
+ * @return mixed
+ */
+ protected function setBaseErroneousFields($messages, $gotoSection)
+ {
+ $this->result['error'] = implode(',', array_values($messages));
+ $this->result['goto_section'] = $gotoSection;
+ $this->result['opsError'] = true;
+
+ return $this;
+ }
+
+ protected function cleanResult()
+ {
+ if (array_key_exists('update_section', $this->result)) {
+ unset($this->result['update_section']);
+ }
+
+ return $this;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Helper/Version.php b/app/code/community/Netresearch/OPS/Helper/Version.php
new file mode 100644
index 0000000..d6844ea
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Helper/Version.php
@@ -0,0 +1,66 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Helper_Version extends Mage_Core_Helper_Abstract
+{
+ const CAN_USE_APPLICABLE_FOR_QUOTE_EE_MINOR = 14;
+
+ const CAN_USE_APPLICABLE_FOR_QUOTE_CE_MINOR = 8;
+
+
+ /**
+ * checks if Version is above EE 1.13 or CE 1.7.0.2
+ * useApplicableForQuote was implemented in CE 1.8 / EE 1.14
+ *
+ * @param $edition
+ *
+ * @return bool
+ */
+ public function canUseApplicableForQuote($edition)
+ {
+ $result = false;
+ $versionInfo = $this->getVersionInfo();
+ if (array_key_exists('minor', $versionInfo)
+ && $versionInfo['minor'] >= $this->getVersionForEdition($edition)
+ ) {
+ $result = true;
+ }
+
+ return $result;
+ }
+
+ /**
+ * return allowed version
+ *
+ * @param $edition
+ *
+ * @return int
+ */
+ protected function getVersionForEdition($edition)
+ {
+ if (Mage::EDITION_ENTERPRISE == $edition) {
+ return self::CAN_USE_APPLICABLE_FOR_QUOTE_EE_MINOR;
+ }
+
+ return self::CAN_USE_APPLICABLE_FOR_QUOTE_CE_MINOR;
+ }
+
+ /**
+ * wraps Mage::getVersionInfo since Mage class is final and not testable
+ *
+ * @return array
+ */
+ protected function getVersionInfo()
+ {
+ return Mage::getVersionInfo();
+ }
+
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Alias.php b/app/code/community/Netresearch/OPS/Model/Alias.php
new file mode 100644
index 0000000..e2cae52
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Alias.php
@@ -0,0 +1,70 @@
+_init('ops/alias');
+ parent::_construct();
+ }
+
+ /**
+ * @param $customerId - the id of the customer
+ * @param $billingAddressHash - optional billing address hash
+ * @param $shippingAddressHash - optional shipping address hash
+ * @param $storeId
+ *
+ * @return Netresearch_OPS_Model_Mysql4_Alias_Collection - collection of aliases for given customer
+ */
+ public function getAliasesForCustomer(
+ $customerId,
+ $billingAddressHash = null,
+ $shippingAddressHash = null,
+ $storeId = null
+ )
+ {
+ $collection = $this->getCollection()
+ ->addFieldToFilter('customer_id', $customerId);
+ if (null != $billingAddressHash && null != $shippingAddressHash) {
+ $collection
+ ->addFieldToFilter('billing_address_hash', $billingAddressHash)
+ ->addFieldToFilter('shipping_address_hash', $shippingAddressHash)
+ ->addFieldToFilter('store_id', array('eq' => $storeId, 'null' => 'null'));
+ }
+ return $collection->load();
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Alias/State.php b/app/code/community/Netresearch/OPS/Model/Alias/State.php
new file mode 100644
index 0000000..4dfd83d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Alias/State.php
@@ -0,0 +1,34 @@
+ 30);
+ $http->setConfig($config);
+ $http->write(Zend_Http_Client::POST, $url, '1.1', array(), http_build_query($params));
+ $response = $http->read();
+ $response = substr($response, strpos($response, "__('Ingenico ePayments server is temporarily not available, please try again later.')
+ );
+ }
+
+ return $response;
+ }
+
+ /**
+ * Performs a POST request to the Direct Link Gateway with the given
+ * parameters and returns the result parameters as array
+ *
+ * @param array $requestParams
+ * @param string $url
+ * @param int $storeId
+ *
+ * @return array
+ */
+ public function performRequest($requestParams, $url, $storeId = 0)
+ {
+ $helper = Mage::helper('ops');
+ $params = $this->getEncodedParametersWithHash(
+ array_merge(
+ $requestParams,
+ $this->buildAuthenticationParams($storeId)
+ ),//Merge Logic Operation Data with Authentication Data
+ null,
+ $storeId
+ );
+ $responseParams = $this->getResponseParams($params, $url);
+ $helper->log(
+ $helper->__(
+ "Direct Link Request/Response in Ingenico ePayments \n\nRequest: %s\nResponse: %s\nMagento-URL: %s\nAPI-URL: %s",
+ serialize($params),
+ serialize($responseParams),
+ Mage::helper('core/url')->getCurrentUrl(),
+ $url
+ )
+ );
+
+ $this->checkResponse($responseParams);
+
+ return $responseParams;
+
+ }
+
+ public function getEncodedParametersWithHash($params, $shaCode=null, $storeId)
+ {
+ $hash = Mage::helper('ops/payment')->getSHASign($params, $shaCode, $storeId);
+ $params['SHASIGN'] = Mage::helper('ops/payment')->shaCrypt(iconv('iso-8859-1', 'utf-8', $hash));
+
+ return $params;
+ }
+
+
+ /**
+ *
+ * wraps the request and response handling and repeats request/response
+ * if there are errors
+ *
+ * @param array $params - request params
+ * @param string $url - the url for the request
+ * @param int $retryCount - current request count
+ * @return array | null - null if requests were not successful, array containing Ingenico ePayments payment data otherwise
+ *
+ */
+ protected function getResponseParams($params, $url, $retryCount = 0)
+ {
+ $responseParams = null;
+ $responseXml = null;
+ if ($retryCount < self::MAX_RETRY_COUNT) {
+ try {
+ $responseXml = $this->call($params, $url);
+ $responseParams = $this->getParamArrFromXmlString($responseXml);
+ } catch (Exception $e) {
+ try {
+ $responseParams = $this->getParamArrFromXmlString(utf8_encode($responseXml));
+ } catch (Exception $e) {
+ $ref = '';
+ if (array_key_exists('ORDERID', $params)) {
+ $ref = $params['ORDERID'];
+ } elseif (array_key_exists('PAYID', $params)) {
+ $ref = $params['PAYID'];
+ }
+ Mage::helper('ops')->log(
+ 'DirectLink::getResponseParams failed: ' .
+ $e->getMessage() . ' current retry count: ' . $retryCount . ' for quote ' . $ref
+ );
+ $responseParams = $this->getResponseParams($params, $url, ++$retryCount);
+ }
+ }
+ } else {
+ Mage::throwException(Mage::helper('ops')->__('An error occured during the Ingenico ePayments request. Your action could not be executed.'));
+ }
+ return $responseParams;
+ }
+
+ /**
+ * Return Authentication Params for OPS Call
+ *
+ * @param int $storeId
+ *
+ * @return array
+ */
+ protected function buildAuthenticationParams($storeId = 0)
+ {
+ return array(
+ 'PSPID' => Mage::getModel('ops/config')->getPSPID($storeId),
+ 'USERID' => Mage::getModel('ops/config')->getApiUserId($storeId),
+ 'PSWD' => Mage::getModel('ops/config')->getApiPswd($storeId),
+ );
+ }
+
+ /**
+ * Parses the XML-String to an array with the result data
+ *
+ * @param $xmlString
+ * @return mixed
+ * @throws Exception
+ */
+ public function getParamArrFromXmlString($xmlString)
+ {
+ try {
+ $xml = new SimpleXMLElement($xmlString);
+ foreach ($xml->attributes() as $key => $value) {
+ $arrAttr[$key] = (string)$value;
+ }
+ foreach ($xml->children() as $child) {
+ $arrAttr[$child->getName()] = (string) $child;
+ }
+ return $arrAttr;
+ } catch (Exception $e) {
+ Mage::log('Could not convert string to xml in ' . __FILE__ . '::' . __METHOD__ . ': ' . $xmlString);
+ Mage::logException($e);
+ throw $e;
+ }
+ }
+
+ /**
+ * Check if the Response from OPS reports Errors
+ *
+ * @param $responseParams
+ */
+ public function checkResponse($responseParams)
+ {
+ if (false === is_array($responseParams)
+ || false === array_key_exists('NCERROR', $responseParams)
+ || $responseParams['NCERROR'] > 0
+ )
+ {
+ if (empty($responseParams['NCERRORPLUS'])) {
+ $responseParams['NCERRORPLUS'] = Mage::helper('ops')->__('Invalid payment information')." Errorcode:".$responseParams['NCERROR'];
+ }
+
+ //avoid exception if STATUS is set with special values
+ if (isset($responseParams['STATUS']) && is_numeric($responseParams['STATUS'])) {
+ return;
+ }
+
+ Mage::throwException(
+ Mage::helper('ops')->__("An error occured during the Ingenico ePayments request. Your action could not be executed. Message: '%s.'", $responseParams['NCERRORPLUS'])
+ );
+ }
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Additional/OpenInvoiceNl.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Additional/OpenInvoiceNl.php
new file mode 100644
index 0000000..b1c69ce
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Additional/OpenInvoiceNl.php
@@ -0,0 +1,15 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Model_Backend_Operation_Capture_Additional_OpenInvoiceNl
+ extends Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_OpenInvoiceNlAbstract
+{
+ /**
+ * @see Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_OpenInvoiceNlAbstract
+ */
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Parameter.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Parameter.php
new file mode 100644
index 0000000..be05201
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Capture/Parameter.php
@@ -0,0 +1,51 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Model_Backend_Operation_Capture_Parameter
+ extends Netresearch_OPS_Model_Backend_Operation_Parameter_Abstract
+{
+ /**
+ * checks whether we need to retrieve additional parameter for the capture request or not
+ *
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ *
+ * @return bool - true if we need to retrieve any additional parameters, false otherwise
+ */
+ protected function isPmRequiringAdditionalParams(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod)
+ {
+ $opsPaymentMethodClass = get_class($opsPaymentMethod);
+ $opsPmsRequiringSpecialParams = $this->getOpsConfig()
+ ->getMethodsRequiringAdditionalParametersFor(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_TRANSACTION_TYPE
+ );
+
+ return (in_array($opsPaymentMethodClass, array_values($opsPmsRequiringSpecialParams)));
+ }
+
+ /**
+ * sets the model which retrieves the additional params
+ *
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ */
+ protected function setAdditionalParamsModelFor(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod)
+ {
+ if ($opsPaymentMethod instanceof Netresearch_OPS_Model_Payment_OpenInvoice_Abstract) {
+ $this->additionalParamsModel = Mage::getModel('ops/backend_operation_capture_additional_openInvoiceNl');
+ }
+ }
+
+ /**
+ * Returns the order helper for the corresponding transaction type
+ *
+ * @return Netresearch_OPS_Helper_Order_Abstract
+ */
+ public function getOrderHelper()
+ {
+ return Mage::helper('ops/order_capture');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter.php
new file mode 100644
index 0000000..dd406f2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter.php
@@ -0,0 +1,69 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Model_Backend_Operation_Parameter
+{
+ protected $parameterModel = null;
+
+ protected $dataHelper = null;
+
+ /**
+ * retrieves the neccessary parameter for the given operation
+ *
+ * @param $operation
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ * @param Varien_Object $payment
+ * @param $amount
+ *
+ * @return array
+ */
+ public function getParameterFor(
+ $operation,
+ Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod,
+ Varien_Object $payment,
+ $amount
+ )
+ {
+ return $this->getParameterModel($operation)->getRequestParams($opsPaymentMethod, $payment, $amount);
+ }
+
+ /**
+ * retrieves the parameter model for the given operation
+ *
+ * @param $operation - the operation we need the parameters for
+ *
+ * @throws Mage_Core_Exception - in case the operation is not supported
+ * @return Netresearch_OPS_Model_Backend_Operation_Parameter_Interface - the model for the parameters of the
+ * operation
+ */
+ protected function getParameterModel($operation)
+ {
+ if ($operation === Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_TRANSACTION_TYPE) {
+ return Mage::getModel('ops/backend_operation_capture_parameter');
+ }
+ if ($operation === Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_TRANSACTION_TYPE) {
+ return Mage::getModel('ops/backend_operation_refund_parameter');
+ }
+
+ Mage::throwException($this->getDataHelper()->__('operation %s not supported', $operation));
+ }
+
+ /**
+ * retrieves the data helper
+ *
+ * @return Netresearch_OPS_Helper_Data|null
+ */
+ protected function getDataHelper()
+ {
+ if (null == $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Abstract.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Abstract.php
new file mode 100644
index 0000000..b94cfb6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Abstract.php
@@ -0,0 +1,133 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+abstract class Netresearch_OPS_Model_Backend_Operation_Parameter_Abstract
+ implements Netresearch_OPS_Model_Backend_Operation_Parameter_Interface
+{
+ protected $requestParams = array();
+
+ protected $opsConfig = null;
+ protected $dataHelper = null;
+
+ protected $additionalParamsModel = null;
+
+ /**
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ * @param $payment
+ * @param $amount
+ *
+ * @return array
+ */
+ public function getRequestParams(
+ Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod,
+ Varien_Object $payment,
+ $amount
+ )
+ {
+ $this->getBaseParams($opsPaymentMethod, $payment, $amount);
+ $this->addPmSpecificParams($opsPaymentMethod, $payment, $amount);
+
+ return $this->requestParams;
+ }
+
+ /**
+ * retrieves the basic parameters for a capture call
+ *
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ * @param Varien_Object $payment
+ * @param $amount
+ *
+ * @return $this
+ */
+ protected function getBaseParams(
+ Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod,
+ Varien_Object $payment,
+ $amount
+ )
+ {
+ $this->requestParams['AMOUNT'] = $this->getDataHelper()->getAmount($amount);
+ $this->requestParams['PAYID'] = $payment->getAdditionalInformation('paymentId');
+ $this->requestParams['OPERATION'] = $this->getOrderHelper()->determineOperationCode($payment, $amount);
+ $this->requestParams['CURRENCY'] = Mage::app()->getStore($payment->getOrder()->getStoreId())
+ ->getBaseCurrencyCode();
+
+ return $this;
+ }
+
+ /**
+ * retrieves ops config model
+ *
+ * @return Netresearch_OPS_Model_Config
+ */
+ protected function getOpsConfig()
+ {
+ if (null === $this->opsConfig) {
+ $this->opsConfig = Mage::getModel('ops/config');
+ }
+
+ return $this->opsConfig;
+ }
+
+ /**
+ * if we have to add payment specific paramters to our request, we'll set them here
+ *
+ * @param $opsPaymentMethod
+ * @param $payment
+ * @param $amount
+ *
+ * @return $this
+ */
+ protected function addPmSpecificParams(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod,
+ Varien_Object $payment, $amount
+ )
+ {
+ if ($this->isPmRequiringAdditionalParams($opsPaymentMethod)) {
+ $this->setAdditionalParamsModelFor($opsPaymentMethod);
+ if ($this->additionalParamsModel instanceof
+ Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_Interface
+ ) {
+ $params = $this->additionalParamsModel->extractAdditionalParams($payment);
+ $this->requestParams = array_merge($this->requestParams, $params);
+ }
+ }
+
+ return $this;
+ }
+
+ protected function isPmRequiringAdditionalParams(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod)
+ {
+ return false;
+ }
+
+ protected function setAdditionalParamsModelFor(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod)
+ {
+ $this->additionalParamsModel = null;
+ }
+
+ /**
+ * retrieves the data helper
+ *
+ * @return Netresearch_OPS_Helper_Data|null
+ */
+ protected function getDataHelper()
+ {
+ if (null == $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+
+ /**
+ * Returns the order helper for the corresponding transaction type
+ *
+ * @return Netresearch_OPS_Helper_Order_Abstract
+ */
+ public abstract function getOrderHelper();
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/Interface.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/Interface.php
new file mode 100644
index 0000000..c4daeef
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/Interface.php
@@ -0,0 +1,11 @@
+
+* @category Netresearch
+* @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+* @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+*/
+interface Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_Interface
+{
+ public function extractAdditionalParams(Mage_Sales_Model_Order_Payment $payment);
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/OpenInvoiceNlAbstract.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/OpenInvoiceNlAbstract.php
new file mode 100644
index 0000000..864ef13
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Additional/OpenInvoiceNlAbstract.php
@@ -0,0 +1,151 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+abstract class Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_OpenInvoiceNlAbstract
+ implements Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_Interface
+{
+ protected $_additionalParams = array();
+ protected $_opsDataHelper = null;
+ protected $_itemIdx = 1;
+
+
+ /**
+ * @param Mage_Sales_Model_Order_Payment $payment
+ *
+ * @return array
+ */
+ public function extractAdditionalParams(Mage_Sales_Model_Order_Payment $payment)
+ {
+ $itemContainer = $payment->getInvoice();
+ if ($itemContainer instanceof Mage_Sales_Model_Order_Invoice) {
+ $requestHelper = Mage::helper('ops/payment_request');
+ $this->_additionalParams = $requestHelper->extractOrderItemParameters($itemContainer);
+ }
+
+ return $this->_additionalParams;
+ }
+
+ /**
+ * @deprecated Netresearch_OPS_Helper_Payment_Request should be used instead
+ *
+ * extracts all necessary data from the invoice items
+ *
+ * @param Mage_Sales_Model_Order_Invoice $invoice
+ *
+ * @return Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_Interface
+ */
+ protected function extractFromInvoiceItems(Mage_Sales_Model_Order_Invoice $invoice)
+ {
+ foreach ($invoice->getItemsCollection() as $item) {
+ /** @var $item Mage_Sales_Model_Order_Invoice_Item */
+ // filter out configurable products
+ if (!$this->isDataItem($item)) {
+ continue;
+ }
+ $this->_additionalParams['ITEMID' . $this->_itemIdx] = substr($item->getOrderItemId(), 0, 15);
+ $this->_additionalParams['ITEMNAME' . $this->_itemIdx] = substr($item->getName(), 0, 30);
+ $this->_additionalParams['ITEMPRICE' . $this->_itemIdx] = $this->getOpsDataHelper()->getAmount(
+ $item->getBasePriceInclTax()
+ );
+ $this->_additionalParams['ITEMQUANT' . $this->_itemIdx] = $item->getQty();
+ $this->_additionalParams['ITEMVATCODE' . $this->_itemIdx]
+ = str_replace(',', '.', (string)(float)$item->getTaxPercent()) . '%';
+ $this->_additionalParams['TAXINCLUDED' . $this->_itemIdx] = 1;
+ ++$this->_itemIdx;
+ }
+
+ return $this;
+ }
+
+
+ /**
+ * extract the necessary data from the shipping data of the invoice
+ *
+ * @deprecated Netresearch_OPS_Helper_Payment_Request should be used instead
+ *
+ * @param Mage_Sales_Model_Order_Invoice $invoice
+ *
+ * @return $this
+ */
+ protected function extractFromInvoicedShippingMethod(Mage_Sales_Model_Order_Invoice $invoice)
+ {
+ $amount = $invoice->getBaseShippingInclTax();
+ if (0 < $amount) {
+ $this->_additionalParams['ITEMID' . $this->_itemIdx] = 'SHIPPING';
+ $this->_additionalParams['ITEMNAME' . $this->_itemIdx]
+ = substr($invoice->getOrder()->getShippingDescription(), 0, 30);
+ $this->_additionalParams['ITEMPRICE' . $this->_itemIdx] = $this->getOpsDataHelper()->getAmount($amount);
+ $this->_additionalParams['ITEMQUANT' . $this->_itemIdx] = 1;
+ $this->_additionalParams['ITEMVATCODE' . $this->_itemIdx] = $this->getShippingTaxRate($invoice) . '%';
+ $this->_additionalParams['TAXINCLUDED' . $this->_itemIdx] = 1;
+ ++$this->_itemIdx;
+ }
+
+
+ return $this;
+ }
+
+ /**
+ * @deprecated Netresearch_OPS_Helper_Payment_Request should be used instead
+ *
+ * retrieves used shipping tax rate
+ *
+ * @param Mage_Sales_Model_Order_Invoice $invoice
+ *
+ * @return float
+ */
+ protected function getShippingTaxRate(Mage_Sales_Model_Order_Invoice $invoice)
+ {
+ $taxRate = 0.0;
+ $order = $invoice->getOrder();
+
+ $taxRate = (floatval(Mage::helper('ops/payment_request')->getShippingTaxRate($order)));
+
+ return $taxRate;
+ }
+
+
+ /**
+ * gets the ops data helper
+ *
+ * @return Netresearch_OPS_Helper_Data
+ */
+ protected function getOpsDataHelper()
+ {
+ if (null === $this->_opsDataHelper) {
+ $this->_opsDataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->_opsDataHelper;
+ }
+
+
+ /**
+ * @deprecated Netresearch_OPS_Helper_Payment_Request should be used instead
+ *
+ * @param $invoice
+ */
+ protected function extractFromDiscountData($invoice)
+ {
+ $amount = $invoice->getBaseDiscountAmount();
+ if (0 > $amount) {
+ $couponRuleName = 'DISCOUNT';
+ $order = $invoice->getOrder();
+ if ($order->getCouponRuleName() && strlen(trim($order->getCouponRuleName())) > 0) {
+ $couponRuleName = substr(trim($order->getCouponRuleName()), 0, 30);
+ }
+ $this->_additionalParams['ITEMID' . $this->_itemIdx] = 'DISCOUNT';
+ $this->_additionalParams['ITEMNAME' . $this->_itemIdx] = $couponRuleName;
+ $this->_additionalParams['ITEMPRICE' . $this->_itemIdx] = $this->getOpsDataHelper()->getAmount($amount);
+ $this->_additionalParams['ITEMQUANT' . $this->_itemIdx] = 1;
+ $this->_additionalParams['ITEMVATCODE' . $this->_itemIdx] = $this->getShippingTaxRate($invoice) . '%';
+ $this->_additionalParams['TAXINCLUDED' . $this->_itemIdx] = 1;
+ ++$this->_itemIdx;
+ }
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Interface.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Interface.php
new file mode 100644
index 0000000..fc80ff7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Parameter/Interface.php
@@ -0,0 +1,17 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+interface Netresearch_OPS_Model_Backend_Operation_Parameter_Interface
+{
+ public function getRequestParams(
+ Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod,
+ Varien_Object $payment,
+ $amount
+ );
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Additional/OpenInvoiceNl.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Additional/OpenInvoiceNl.php
new file mode 100644
index 0000000..ed24113
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Additional/OpenInvoiceNl.php
@@ -0,0 +1,138 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Model_Backend_Operation_Refund_Additional_OpenInvoiceNl
+ extends Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_OpenInvoiceNlAbstract
+{
+ /** @var $creditmemo Mage_Sales_Model_Order_Creditmemo */
+ protected $creditmemo = null;
+ protected $amount = 0;
+ protected $refundHelper = null;
+
+ /**
+ * @param Mage_Sales_Model_Order_Payment $itemContainer
+ * @return array
+ */
+ public function extractAdditionalParams(Mage_Sales_Model_Order_Payment $payment = null)
+ {
+ $invoice = $payment->getInvoice();
+
+ if ($invoice == null) {
+ // if invoice is not set we load id hard from the request params
+ $invoice = $this->getRefundHelper()->getInvoiceFromCreditMemoRequest();
+ }
+ $this->creditmemo = $payment->getCreditmemo();
+
+ if ($invoice instanceof Mage_Sales_Model_Order_Invoice) {
+ $this->extractFromCreditMemoItems($invoice);
+ // We dont extract from discount data for the moment, because partial refunds are a problem
+ $this->extractFromInvoicedShippingMethod($invoice);
+ $this->extractFromAdjustments($invoice);
+ // Overwrite amount to fix Magentos rounding problems (eg +1ct)
+ $this->_additionalParams['AMOUNT'] = $this->amount;
+ }
+
+ return $this->_additionalParams;
+ }
+
+ /**
+ * extracts all data from the invoice according to the credit memo items
+ *
+ */
+ protected function extractFromCreditMemoItems()
+ {
+ /** @var Mage_Sales_Model_Order_Creditmemo_Item $item */
+ foreach ($this->creditmemo->getAllItems() as $item) {
+ if ($item->getOrderItem()->getParentItemId()
+ && $item->getOrderItem()->getParentItem()->getProductType() == Mage_Catalog_Model_Product_Type::TYPE_CONFIGURABLE
+ || $item->getOrderItem()->getProductType() == Mage_Catalog_Model_Product_Type::TYPE_BUNDLE
+ ) {
+ continue;
+ }
+ $this->_additionalParams['ITEMID' . $this->_itemIdx] = substr($item->getOrderItemId(), 0, 15);
+ $this->_additionalParams['ITEMNAME' . $this->_itemIdx] = substr($item->getName(), 0, 30);
+ $this->_additionalParams['ITEMPRICE' . $this->_itemIdx] = $this->getOpsDataHelper()->getAmount(
+ $item->getBasePriceInclTax()
+ );
+ $this->amount += $this->getOpsDataHelper()
+ ->getAmount($item->getBasePriceInclTax()) * $item->getQty();
+ $this->_additionalParams['ITEMQUANT' . $this->_itemIdx] = $item->getQty();
+ $this->_additionalParams['ITEMVATCODE' . $this->_itemIdx]
+ = str_replace(',', '.', (string)(float)$item->getOrderItem()->getTaxPercent()) . '%';
+ $this->_additionalParams['TAXINCLUDED' . $this->_itemIdx] = 1;
+ ++$this->_itemIdx;
+ }
+
+ }
+
+
+ protected function extractFromInvoicedShippingMethod(Mage_Sales_Model_Order_Invoice $invoice)
+ {
+ if ($this->creditmemo->getBaseShippingInclTax() > 0) {
+ $this->_additionalParams['ITEMID' . $this->_itemIdx] = 'SHIPPING';
+ $this->_additionalParams['ITEMNAME' . $this->_itemIdx] =
+ substr($invoice->getOrder()->getShippingDescription(), 0, 30);
+ $this->_additionalParams['ITEMPRICE' . $this->_itemIdx] = $this->getOpsDataHelper()
+ ->getAmount($this->creditmemo->getBaseShippingInclTax());
+ $this->amount += $this->getOpsDataHelper()->getAmount($this->creditmemo->getBaseShippingInclTax());
+ $this->_additionalParams['ITEMQUANT' . $this->_itemIdx] = 1;
+ $this->_additionalParams['ITEMVATCODE' . $this->_itemIdx] = $this->getShippingTaxRate($invoice) . '%';
+ $this->_additionalParams['TAXINCLUDED' . $this->_itemIdx] = 1;
+ ++$this->_itemIdx;
+ }
+
+ }
+
+ /**
+ * extracts all data from the adjustment fee/refund
+ *
+ * @param $invoice
+ */
+ protected function extractFromAdjustments(Mage_Sales_Model_Order_Invoice $invoice)
+ {
+
+ if ($this->creditmemo->getBaseAdjustmentPositive() > 0) {
+ $this->_additionalParams['ITEMID' . $this->_itemIdx] = 'ADJUSTREFUND';
+ $this->_additionalParams['ITEMNAME' . $this->_itemIdx] = 'Adjustment Refund';
+ $this->_additionalParams['ITEMPRICE' . $this->_itemIdx] = $this->getOpsDataHelper()
+ ->getAmount($this->creditmemo->getBaseAdjustmentPositive());
+ $this->amount += $this->getOpsDataHelper()->getAmount($this->creditmemo->getBaseAdjustmentPositive());
+ $this->_additionalParams['ITEMQUANT' . $this->_itemIdx] = 1;
+ $this->_additionalParams['ITEMVATCODE' . $this->_itemIdx] = $this->getShippingTaxRate($invoice) . '%';
+ $this->_additionalParams['TAXINCLUDED' . $this->_itemIdx] = 1;
+ ++$this->_itemIdx;
+
+ }
+ if ($this->creditmemo->getBaseAdjustmentNegative() > 0) {
+ $this->_additionalParams['ITEMID' . $this->_itemIdx] = 'ADJUSTFEE';
+ $this->_additionalParams['ITEMNAME' . $this->_itemIdx] = 'Adjustment Fee';
+ $this->_additionalParams['ITEMPRICE' . $this->_itemIdx] = $this->getOpsDataHelper()
+ ->getAmount(-$this->creditmemo->getBaseAdjustmentNegative());
+ $this->amount += $this->getOpsDataHelper()->getAmount(-$this->creditmemo->getBaseAdjustmentNegative());
+ $this->_additionalParams['ITEMQUANT' . $this->_itemIdx] = 1;
+ $this->_additionalParams['ITEMVATCODE' . $this->_itemIdx] = $this->getShippingTaxRate($invoice) . '%';
+ $this->_additionalParams['TAXINCLUDED' . $this->_itemIdx] = 1;
+ ++$this->_itemIdx;
+ }
+ }
+
+ /**
+ * gets the refund helper
+ *
+ * @return Netresearch_OPS_Helper_Order_Refund|null
+ */
+ protected function getRefundHelper()
+ {
+ if (null === $this->refundHelper) {
+ $this->refundHelper = Mage::helper('ops/order_refund');
+ }
+
+ return $this->refundHelper;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Parameter.php b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Parameter.php
new file mode 100644
index 0000000..edb6266
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Backend/Operation/Refund/Parameter.php
@@ -0,0 +1,70 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Model_Backend_Operation_Refund_Parameter
+ extends Netresearch_OPS_Model_Backend_Operation_Parameter_Abstract
+{
+ /**
+ * checks whether we need to retrieve additional parameter for the refund request or not
+ *
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ *
+ * @return bool - true if we need to retrieve any additional parameters, false otherwise
+ */
+ protected function isPmRequiringAdditionalParams(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod)
+ {
+ $opsPaymentMethodClass = get_class($opsPaymentMethod);
+ $opsPmsRequiringSpecialParams = $this->getOpsConfig()
+ ->getMethodsRequiringAdditionalParametersFor(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_TRANSACTION_TYPE
+ );
+
+ return (in_array($opsPaymentMethodClass, array_values($opsPmsRequiringSpecialParams)));
+ }
+
+ /**
+ * sets the model which retrieves the additional params for the refund request
+ *
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ */
+ protected function setAdditionalParamsModelFor(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod)
+ {
+ if ($opsPaymentMethod instanceof Netresearch_OPS_Model_Payment_OpenInvoice_Abstract) {
+ $this->additionalParamsModel = Mage::getModel('ops/backend_operation_refund_additional_openInvoiceNl');
+ }
+ }
+
+ protected function addPmSpecificParams(Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod,
+ Varien_Object $payment, $amount
+ )
+ {
+ if ($this->isPmRequiringAdditionalParams($opsPaymentMethod)) {
+ $this->setAdditionalParamsModelFor($opsPaymentMethod);
+ if ($this->additionalParamsModel instanceof
+ Netresearch_OPS_Model_Backend_Operation_Parameter_Additional_Interface
+ ) {
+ $params = $this->additionalParamsModel->extractAdditionalParams($payment);
+ $this->requestParams = array_merge($this->requestParams, $params);
+ }
+ }
+
+ return $this;
+ }
+
+ /**
+ * Returns the order helper for the corresponding transaction type
+ *
+ * @return Netresearch_OPS_Helper_Order_Abstract
+ */
+ public function getOrderHelper()
+ {
+ return Mage::helper('ops/order_refund');
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Config.php b/app/code/community/Netresearch/OPS/Model/Config.php
new file mode 100644
index 0000000..4030912
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Config.php
@@ -0,0 +1,976 @@
+decrypt($this->getConfigData('secret_key_in', $storeId));
+ }
+
+ /**
+ * Return SHA1-out crypt key from config. Setup on admin place.
+ *
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getShaOutCode($storeId = null)
+ {
+ return Mage::helper('core')->decrypt($this->getConfigData('secret_key_out', $storeId));
+ }
+
+ /**
+ * Return frontend gateway path, get from config. Setup on admin place.
+ *
+ * @param string $path
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getFrontendGatewayPath($storeId = null)
+ {
+ return $this->determineOpsUrl('frontend_gateway', $storeId);
+ }
+
+ /**
+ * Return Direct Link Gateway path, get from config. Setup on admin place.
+ *
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getDirectLinkGatewayPath($storeId = null)
+ {
+ return $this->determineOpsUrl('directlink_gateway', $storeId);
+ }
+
+ public function getDirectLinkGatewayOrderPath($storeId = null)
+ {
+ return $this->determineOpsUrl('directlink_gateway_order', $storeId);
+ }
+
+ /**
+ * Return API User, get from config. Setup on admin place.
+ *
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getApiUserId($storeId = null)
+ {
+ return $this->getConfigData('api_userid', $storeId);
+ }
+
+ /**
+ * Return API Passwd, get from config. Setup on admin place.
+ *
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getApiPswd($storeId = null)
+ {
+ return Mage::helper('core')->decrypt($this->getConfigData('api_pswd', $storeId));
+ }
+
+ /**
+ * Get PSPID, affiliation name in ops system
+ *
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getPSPID($storeId = null)
+ {
+ return $this->getConfigData('pspid', $storeId);
+ }
+
+ public function getPaymentAction($storeId = null)
+ {
+ return $this->getConfigData('payment_action', $storeId);
+ }
+
+ /**
+ * Get paypage template for magento style templates using
+ *
+ * @return string
+ */
+ public function getPayPageTemplate()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'paypage',
+ array('_nosid' => true, '_secure' => $this->isCurrentlySecure())
+ );
+ }
+
+ /**
+ * Return url which ops system will use as accept
+ *
+ * @return string
+ */
+ public function getAcceptUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'accept',
+ array('_nosid' => true, '_secure' => $this->isCurrentlySecure())
+ );
+ }
+
+ /**
+ * Return url which ops system will use as accept for alias generation
+ *
+ * @param int $storeId
+ * @param bool $admin
+ *
+ * @return string
+ */
+ public function getAliasAcceptUrl($storeId = null, $admin = false)
+ {
+ $params = array(
+ '_secure' => $this->isCurrentlySecure(),
+ '_nosid' => true
+ );
+ if (null != $storeId) {
+ $params['_store'] = $storeId;
+ }
+
+ if ($admin) {
+ $params['_nosecret'] = true;
+
+ return Mage::getModel('adminhtml/url')->getUrl('adminhtml/alias/accept', $params);
+ } else {
+ return Mage::getModel('core/url')->getUrl(self::OPS_CONTROLLER_ROUTE_ALIAS . 'accept', $params);
+ }
+ }
+
+ /**
+ * Return url which ops system will use as decline url
+ *
+ * @return string
+ */
+ public function getDeclineUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'decline',
+ array('_nosid' => true, '_secure' => $this->isCurrentlySecure())
+ );
+ }
+
+ /**
+ * Return url which ops system will use as exception url
+ *
+ * @return string
+ */
+ public function getExceptionUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'exception',
+ array('_nosid' => true, '_secure' => $this->isCurrentlySecure())
+ );
+ }
+
+ /**
+ * Return url which ops system will use as exception url for alias generation
+ *
+ * @param int $storeId
+ * @param bool $admin
+ *
+ * @return string
+ */
+ public function getAliasExceptionUrl($storeId = null, $admin = false)
+ {
+ $params = array(
+ '_secure' => $this->isCurrentlySecure(),
+ '_nosid' => true
+ );
+ if (null !=$storeId) {
+ $params['_store'] = $storeId;
+ }
+ if ($admin) {
+ $params['_nosecret'] = true;
+
+ return Mage::getModel('adminhtml/url')->getUrl('adminhtml/alias/exception', $params);
+ } else {
+ return Mage::getModel('core/url')->getUrl(self::OPS_CONTROLLER_ROUTE_ALIAS . 'exception', $params);
+ }
+ }
+
+ /**
+ * Return url which ops system will use as cancel url
+ *
+ * @return string
+ */
+ public function getCancelUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'cancel',
+ array('_nosid' => true, '_secure' => $this->isCurrentlySecure())
+ );
+ }
+
+ /**
+ * Return url which ops system will use as continue shopping url
+ *
+ * @param array $redirect
+ *
+ * @return string
+ */
+ public function getContinueUrl($redirect = array())
+ {
+ $urlParams = array('_nosid' => true, '_secure' => $this->isCurrentlySecure());
+ if (!empty($redirect)) {
+ $urlParams = array_merge($redirect, $urlParams);
+ }
+
+ return Mage::getUrl(self::OPS_CONTROLLER_ROUTE_PAYMENT . 'continue', $urlParams);
+ }
+
+ /**
+ * Return url to redirect after confirming the order
+ *
+ * @return string
+ */
+ public function getPaymentRedirectUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'placeform',
+ array('_secure' => true, '_nosid' => true)
+ );
+ }
+
+ /**
+ * Return 3D Secure url to redirect after confirming the order
+ *
+ * @return string
+ */
+ public function get3dSecureRedirectUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'placeform3dsecure',
+ array('_secure' => true, '_nosid' => true)
+ );
+ }
+
+ public function getSaveCcBrandUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'saveCcBrand',
+ array('_secure' => $this->isCurrentlySecure(), '_nosid' => true)
+ );
+ }
+
+ public function getGenerateHashUrl($storeId = null, $admin = false)
+ {
+ $params = array(
+ '_secure' => $this->isCurrentlySecure(),
+ '_nosid' => true,
+ );
+ if (null != $storeId) {
+ $params['_store'] = $storeId;
+ }
+ if ($admin) {
+ $params['_nosecret'] = true;
+
+ return Mage::getModel('adminhtml/url')->getUrl('adminhtml/alias/generatehash', $params);
+ } else {
+ return Mage::getModel('core/url')->getUrl(self::OPS_CONTROLLER_ROUTE_ALIAS . 'generatehash', $params);
+ }
+
+ }
+
+ /**
+ * Checks if requests should be logged or not regarding configuration
+ *
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function shouldLogRequests($storeId = null)
+ {
+ return $this->getConfigData('debug_flag', $storeId);
+ }
+
+ /**
+ * @return mixed
+ */
+ public function hasCatalogUrl()
+ {
+ return Mage::getStoreConfig('payment_services/ops/showcatalogbutton');
+ }
+
+ /**
+ * @return mixed
+ */
+ public function hasHomeUrl()
+ {
+ return Mage::getStoreConfig('payment_services/ops/showhomebutton');
+ }
+
+ /**
+ * @param $code
+ * @return mixed
+ */
+ public function getAcceptedCcTypes($code)
+ {
+ return Mage::getStoreConfig('payment/' . $code . '/types');
+ }
+
+ /**
+ * Returns the cc types for which inline payments are activated
+ *
+ * @param string $code
+ *
+ * @return string[]
+ */
+ public function getInlinePaymentCcTypes($code)
+ {
+ $redirectAll = (bool)(int)Mage::getStoreConfig('payment/' . $code . '/redirect_all');
+ if ($redirectAll) {
+ return array();
+ }
+
+ $inlineTypes = Mage::getStoreConfig('payment/' . $code . '/inline_types');
+ if (false == is_array($inlineTypes)) {
+ $inlineTypes = explode(',', $inlineTypes);
+ }
+
+ return $inlineTypes;
+ }
+
+ /**
+ * @return mixed
+ */
+ public function get3dSecureIsActive()
+ {
+ return Mage::getStoreConfig('payment/ops_cc/enabled_3dsecure');
+ }
+
+ /**
+ * @return mixed
+ */
+ public function getDirectDebitCountryIds()
+ {
+ return Mage::getStoreConfig('payment/ops_directDebit/countryIds');
+ }
+
+ /**
+ * @return mixed
+ */
+ public function getBankTransferCountryIds()
+ {
+ return Mage::getStoreConfig('payment/ops_bankTransfer/countryIds');
+ }
+
+ /**
+ * @return mixed
+ */
+ public function getDirectEbankingBrands()
+ {
+ return Mage::getStoreConfig('payment/ops_directEbanking/brands');
+ }
+
+ /**
+ * Returns the generated alias (hosted tokenization) url or the special url if needed by vendor
+ *
+ * @param null $storeId
+ *
+ * @return mixed|Simple_Xml|string
+ */
+ public function getAliasGatewayUrl($storeId = null)
+ {
+ $url = $this->determineOpsUrl('ops_alias_gateway', $storeId);
+
+ if ($this->getConfigData('ops_alias_gateway_test') != '') {
+ if ($this->getMode($storeId) == Netresearch_OPS_Model_Source_Mode::TEST) {
+ return $this->getConfigData('ops_alias_gateway_test');
+ } elseif ($this->getMode($storeId) == Netresearch_OPS_Model_Source_Mode::PROD) {
+ $url = str_replace('ncol/prod/', '', $url);
+ }
+ }
+
+ return $url;
+ }
+
+ /**
+ * @param null $storeId
+ * @param bool $admin
+ * @return mixed
+ */
+ public function getCcSaveAliasUrl($storeId = null, $admin = false)
+ {
+ $params = array(
+ '_secure' => $this->isCurrentlySecure()
+ );
+ if (false === is_null($storeId)) {
+ $params['_store'] = $storeId;
+ }
+ if ($admin) {
+ return Mage::getModel('adminhtml/url')->getUrl('ops/admin/saveAlias', $params);
+ } else {
+ return Mage::getUrl('ops/alias/save', $params);
+ }
+ }
+
+ /**
+ * get deeplink to transaction view at Ingenico ePayments
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ *
+ * @return string
+ */
+ public function getOpsAdminPaymentUrl($payment)
+ {
+ return '';
+ }
+
+ public function isCurrentlySecure()
+ {
+ return Mage::app()->getStore()->isCurrentlySecure();
+ }
+
+ public function getIntersolveBrands($storeId = null)
+ {
+ $result = array();
+ $brands = Mage::getStoreConfig('payment/ops_interSolve/brands', $storeId);
+ if (null !=$brands) {
+ $result = unserialize($brands);
+ }
+
+ return $result;
+ }
+
+ /**
+ * @param int $storeId
+ *
+ * @return string[][]
+ */
+ public function getFlexMethods($storeId = null)
+ {
+ $result = array();
+ $methods = Mage::getStoreConfig('payment/ops_flex/methods', $storeId);
+ if (null !=$methods) {
+ $result = unserialize($methods);
+ }
+
+ return $result;
+ }
+
+ /**
+ * @return array
+ */
+ public function getAllCcTypes()
+ {
+ return explode(',', Mage::getStoreConfig('payment/ops_cc/availableTypes'));
+ }
+
+
+ /**
+ * @return array
+ */
+ public function getAllDcTypes()
+ {
+ return explode(',', Mage::getStoreConfig('payment/ops_dc/availableTypes'));
+ }
+
+ /**
+ * get keys of parameters to be shown in scoring information block
+ *
+ * @return array
+ */
+ public function getAdditionalScoringKeys()
+ {
+ return array(
+ 'AAVCHECK',
+ 'ACCEPTANCE',
+ 'CVCCHECK',
+ 'CCCTY',
+ 'IPCTY',
+ 'NBREMAILUSAGE',
+ 'NBRIPUSAGE',
+ 'NBRIPUSAGE_ALLTX',
+ 'NBRUSAGE',
+ 'VC',
+ 'CARDNO',
+ 'ED',
+ 'CN'
+ );
+ }
+
+ /**
+ * @return bool
+ */
+ public function getSendInvoice()
+ {
+ return (bool)(int)Mage::getStoreConfig('payment_services/ops/send_invoice');
+ }
+
+ /**
+ * if payment method with given code is enabled for backend payments
+ *
+ * @param string $code Payment method code
+ *
+ * @return bool
+ */
+ public function isEnabledForBackend($code, $storeId = 0)
+ {
+ return (bool)(int)Mage::getStoreConfig('payment/' . $code . '/backend_enabled', $storeId);
+ }
+
+ /**
+ * @return bool
+ */
+ public function isAliasInfoBlockEnabled()
+ {
+ return (bool)(int)Mage::getStoreConfig('payment/ops_cc/show_alias_manager_info_for_guests');
+ }
+
+ /**
+ * return config value for Alias Manager enabled
+ *
+ * @param $code
+ * @param $storeId
+ *
+ * @return bool
+ */
+ public function isAliasManagerEnabled($code, $storeId = null)
+ {
+ return (bool)Mage::getStoreConfig('payment/' . $code . '/active_alias', $storeId);
+ }
+
+ /**
+ * return configured text for alias usage parameter for new alias creation
+ *
+ * @param $code
+ * @param null $storeId
+ *
+ * @return string
+ */
+ public function getAliasUsageForNewAlias($code, $storeId = null)
+ {
+ return Mage::getStoreConfig('payment/' . $code . '/alias_usage_for_new_alias', $storeId);
+ }
+
+ /**
+ * return configured text for alias usage parameter when using a existing alias
+ *
+ * @param $code
+ * @param null $storeId
+ *
+ * @return string
+ */
+ public function getAliasUsageForExistingAlias($code, $storeId = null)
+ {
+ return Mage::getStoreConfig('payment/' . $code . '/alias_usage_for_existing_alias', $storeId);
+ }
+
+
+ /**
+ * getter for usage of order reference
+ */
+ public function getOrderReference($storeId = null)
+ {
+ return $this->getConfigData('redirectOrderReference', $storeId);
+ }
+
+ /**
+ * @param int $storeId - the store id to use
+ *
+ * @return int whether the QuoteId should be shown in
+ * the order grid (1) or not (0)
+ */
+ public function getShowQuoteIdInOrderGrid($storeId = null)
+ {
+ return $this->getConfigData('showQuoteIdInOrderGrid', $storeId);
+ }
+
+ /**
+ * Check if the current environment is frontend or backend
+ *
+ * @return boolean
+ */
+ public function isFrontendEnvironment()
+ {
+ return (false === Mage::app()->getStore()->isAdmin());
+ }
+
+ /**
+ * getter for the accept route for payments
+ *
+ * @return string
+ */
+ public function getAcceptRedirectRoute()
+ {
+ return self::OPS_CONTROLLER_ROUTE_PAYMENT . 'accept';
+ }
+
+ /**
+ * getter for the cancel route for payments
+ *
+ * @return string
+ */
+ public function getCancelRedirectRoute()
+ {
+ return self::OPS_CONTROLLER_ROUTE_PAYMENT . 'cancel';
+ }
+
+ /**
+ * getter for the decline route for payments
+ *
+ * @return string
+ */
+ public function getDeclineRedirectRoute()
+ {
+ return self::OPS_CONTROLLER_ROUTE_PAYMENT . 'decline';
+ }
+
+ /**
+ * getter for the decline route for payments
+ *
+ * @return string
+ */
+ public function getExceptionRedirectRoute()
+ {
+ return self::OPS_CONTROLLER_ROUTE_PAYMENT . 'exception';
+ }
+
+
+ /**
+ * @param $operation
+ * @return mixed
+ */
+ public function getMethodsRequiringAdditionalParametersFor($operation)
+ {
+ return Mage::getStoreConfig('payment/additional_params_required/' . $operation);
+ }
+
+
+ /**
+ * returns the url for the maintenance api calls
+ *
+ * @param null $storeId
+ *
+ * @return string - the url for the maintenance api calls
+ */
+ public function getDirectLinkMaintenanceApiPath($storeId = null)
+ {
+ return $this->determineOpsUrl('directlink_maintenance_api', $storeId);
+ }
+
+ /**
+ * getter for the iDeal issuers
+ *
+ * @return array
+ */
+ public function getIDealIssuers()
+ {
+ return Mage::getStoreConfig('payment/ops_iDeal/issuer');
+ }
+
+ /**
+ * whether extra parameters needs to be passed to Ingenico ePayments or not
+ *
+ * @param null $storeId
+ *
+ * @return bool - true if it's enabled, false otherwise
+ */
+ public function canSubmitExtraParameter($storeId = null)
+ {
+ return (bool)$this->getConfigData('submitExtraParameters', $storeId);
+ }
+
+ public function getParameterLengths()
+ {
+ return $this->getConfigData('paramLength');
+ }
+
+ /**
+ * @return Simple_Xml
+ */
+ public function getFrontendFieldMapping()
+ {
+ return $this->getConfigData('frontendFieldMapping');
+
+ }
+
+ /**
+ * @return mixed
+ */
+ public function getValidationUrl()
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'validate',
+ array('_secure' => $this->isCurrentlySecure(), '_nosid' => true)
+ );
+ }
+
+ /**
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function getInlineOrderReference($storeId = null)
+ {
+ return $this->getConfigData('inlineOrderReference', $storeId);
+ }
+
+ /**
+ * Returns the mode of the store
+ *
+ * @param null $storeId
+ *
+ * @return string | mode (custom, prod, test) for the store
+ * @see Netresearch_OPS_Model_Source_Mode
+ */
+ public function getMode($storeId = null)
+ {
+ return $this->getConfigData('mode', $storeId);
+ }
+
+ protected function getOpsUrl($path)
+ {
+ return $this->getConfigData('url/' . $path);
+ }
+
+ /**
+ * Will always return the base url (https://secure.domain.tld/ncol/[test, prod]) for the mode of the store
+ *
+ * @return string Url depending of the mode - will be empty for custom mode
+ */
+ public function getOpsBaseUrl($storeId = null)
+ {
+ return $this->getOpsUrl('base_' . $this->getMode($storeId));
+ }
+
+ /**
+ * Returns the default url for the given gateway, depending on the mode, that is set for the the given store
+ *
+ * @param string $path
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getDefaultOpsUrl($path, $storeId = null)
+ {
+ return $this->getOpsBaseUrl($storeId) . $this->getOpsUrl($path);
+ }
+
+ /**
+ * Returns the url for the given gateway depending on the set mode for the given store
+ *
+ * @param $path
+ * @param null $storeId
+ *
+ * @return string
+ */
+ public function determineOpsUrl($path, $storeId = null)
+ {
+ if ($this->getMode($storeId) === Netresearch_OPS_Model_Source_Mode::CUSTOM) {
+ return $this->getConfigData($path, $storeId);
+ } else {
+ return $this->getDefaultOpsUrl($path, $storeId);
+ }
+ }
+
+ /**
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function getTemplateIdentifier($storeId = null)
+ {
+ return $this->getConfigData('template_identifier', $storeId);
+ }
+
+ /**
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function getResendPaymentInfoIdentity($storeId = null)
+ {
+ return $this->getConfigData('resendPaymentInfo_identity', $storeId);
+ }
+
+ /**
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function getResendPaymentInfoTemplate($storeId = null)
+ {
+ return $this->getConfigData('resendPaymentInfo_template', $storeId);
+ }
+
+
+ /**
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function getPayPerMailTemplate($storeId = null)
+ {
+ return $this->getConfigData('payPerMail_template', $storeId);
+ }
+
+ /**
+ * @return Simple_Xml
+ */
+ public function getStateRestriction()
+ {
+ return $this->getConfigData('ops_state_restriction');
+ }
+
+ /**
+ * @param $params
+ * @param null $storeId
+ * @return mixed
+ */
+ public function getPaymentRetryUrl($params, $storeId = null)
+ {
+ return Mage::getUrl(
+ self::OPS_CONTROLLER_ROUTE_PAYMENT . 'retry',
+ array('_secure' => true, '_nosid' => true, '_query' => $params, '_store' => $storeId)
+ );
+ }
+
+ /**
+ * Will return the state of the deviceFingerPrinting:
+ * - true if activated in config
+ * - false if deactivated in config
+ *
+ * @param int $storeId
+ *
+ * @return bool
+ */
+ public function getDeviceFingerPrinting($storeId = null)
+ {
+ return (bool)$this->getConfigData('device_fingerprinting', $storeId);
+ }
+
+ /**
+ * @param null $storeId
+ * @return int
+ */
+ public function getTransActionTimeout($storeId = null)
+ {
+ return (int)$this->getConfigData('ops_rtimeout', $storeId);
+ }
+
+ /**
+ *
+ * @param int|null $storeId
+ *
+ * @return bool
+ */
+ public function getCreditDebitSplit($storeId = null)
+ {
+ return (bool)$this->getConfigData('creditdebit_split', $storeId);
+ }
+
+ /**
+ * @return array
+ */
+ public function getAllRecurringCcTypes()
+ {
+ return explode(',', Mage::getStoreConfig('payment/ops_recurring_cc/availableTypes'));
+ }
+
+ /**
+ * @return array
+ */
+ public function getAcceptedRecurringCcTypes()
+ {
+ return explode(',', Mage::getStoreConfig('payment/ops_recurring_cc/acceptedTypes'));
+ }
+
+ /**
+ * @param null $storeId
+ * @return mixed
+ */
+ public function getMonthlyBillingDay($storeId = null)
+ {
+ return Mage::getStoreConfig(self::OPS_PAYMENT_PATH . 'billing_day_month', $storeId);
+ }
+
+ /**
+ * @param null $storeId
+ * @return mixed
+ */
+ public function getWeeklyBillingDay($storeId = null)
+ {
+ return Mage::getStoreConfig(self::OPS_PAYMENT_PATH . 'billing_day_week', $storeId);
+ }
+
+ /**
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function getSuspendSubscriptionTemplate($storeId = null)
+ {
+ return $this->getConfigData('suspendSubscription_template', $storeId);
+ }
+
+ /**
+ * @param null $storeId
+ * @return Simple_Xml
+ */
+ public function getSuspendSubscriptionIdentity($storeId = null)
+ {
+ return $this->getConfigData('suspendSubscription_identity', $storeId);
+ }
+
+
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Eci/Values.php b/app/code/community/Netresearch/OPS/Model/Eci/Values.php
new file mode 100644
index 0000000..a3067a1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Eci/Values.php
@@ -0,0 +1,35 @@
+_filePath = $path;
+ if (!file_exists($this->_filePath) || !is_readable($this->_filePath)) {
+ Mage::throwException('File '.$this->_filePath.' does not exist or is not readable.');
+ return '';
+ }
+ if (filesize($path) > $threshold) {
+ return $this->_trimFileToThreshold($threshold);
+ } else {
+ return $this->_filePath;
+ }
+ }
+
+ /**
+ * Trims the current file to the given threshold and creates a temporary file
+ *
+ * @param $threshold Max file size
+ * @return string Path to the temporary file
+ * @throws Mage_Core_Exception
+ */
+ protected function _trimFileToThreshold($threshold)
+ {
+ $this->_fileHandler = fopen($this->_filePath, 'r');
+ if (0 > fseek($this->_fileHandler, filesize($this->_filePath)-$threshold, SEEK_SET)) {
+ Mage::throwException('Function fseek on file '. $this->_filePath.' failed.');
+ }
+ $content = fread($this->_fileHandler, $threshold);
+ fclose($this->_fileHandler);
+ $tempFileName = tempnam(sys_get_temp_dir(), 'tempFile');
+ file_put_contents($tempFileName, $content);
+
+ return $tempFileName;
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Kwixo/Category/Mapping.php b/app/code/community/Netresearch/OPS/Model/Kwixo/Category/Mapping.php
new file mode 100644
index 0000000..485670e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Kwixo/Category/Mapping.php
@@ -0,0 +1,57 @@
+_init('ops/kwixo_category_mapping');
+ parent::_construct();
+ }
+
+
+ public function loadByCategoryId($categoryId)
+ {
+ $collection = $this->getCollection()
+ ->addFieldToFilter('category_id', $categoryId)
+ ->load()
+ ->getFirstItem();
+
+ return $collection;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Kwixo/Shipping/Setting.php b/app/code/community/Netresearch/OPS/Model/Kwixo/Shipping/Setting.php
new file mode 100644
index 0000000..edf28e5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Kwixo/Shipping/Setting.php
@@ -0,0 +1,24 @@
+
+ * @category Netresearch
+ * @package ${MODULENAME}
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Kwixo_Shipping_Setting
+ extends Mage_Core_Model_Abstract
+{
+ /**
+ * Constructor
+ *
+ * @see lib/Varien/Varien_Object#_construct()
+ */
+ public function _construct()
+ {
+ $this->_init('ops/kwixo_shipping_setting');
+ parent::_construct();
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Mysql4/Alias.php b/app/code/community/Netresearch/OPS/Model/Mysql4/Alias.php
new file mode 100644
index 0000000..726895b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Mysql4/Alias.php
@@ -0,0 +1,33 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Model_Mysql4_Alias
+ * Netresearch_OPS_Model_Mysql4_Alias
+ * @author Michael Lühr
+ * @author Thomas Birke
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Model_Mysql4_Alias
+ extends Mage_Core_Model_Mysql4_Abstract
+{
+ /**
+ * Constructor
+ *
+ * @see lib/Varien/Varien_Object#_construct()
+ * @return Netresearch_OPS_Model_Mysql4_Alias
+ */
+ public function _construct()
+ {
+ $this->_init('ops/alias', 'id');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Mysql4/Alias/Collection.php b/app/code/community/Netresearch/OPS/Model/Mysql4/Alias/Collection.php
new file mode 100644
index 0000000..1a0c5ec
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Mysql4/Alias/Collection.php
@@ -0,0 +1,29 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Model_Mysql4_Alias_Collection
+ * @author Thomas Birke
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Mysql4_Alias_Collection extends
+ Mage_Core_Model_Mysql4_Collection_Abstract
+{
+
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->_init('ops/alias');
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping.php b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping.php
new file mode 100644
index 0000000..454cf44
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping.php
@@ -0,0 +1,32 @@
+
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Model_Mysql4_Alias
+ * Netresearch_OPS_Model_Mysql4_Alias
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Model_Mysql4_Kwixo_Category_Mapping
+ extends Mage_Core_Model_Mysql4_Abstract
+{
+
+ /**
+ * Constructor
+ *
+ * @see lib/Varien/Varien_Object#_construct()
+ * @return Netresearch_OPS_Model_Mysql4_Kwixo_Category_Mapping
+ */
+ public function _construct()
+ {
+ $this->_init('ops/kwixo_category_mapping', 'id');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping/Collection.php b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping/Collection.php
new file mode 100644
index 0000000..8a3e6d2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Category/Mapping/Collection.php
@@ -0,0 +1,28 @@
+
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Model_Mysql4_Kwixo_Category_Mapping_Collection
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Model_Mysql4_Kwixo_Category_Mapping_Collection
+ extends Mage_Core_Model_Mysql4_Collection_Abstract
+{
+
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->_init('ops/kwixo_category_mapping');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting.php b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting.php
new file mode 100644
index 0000000..ff09fc8
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting.php
@@ -0,0 +1,20 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Mysql4_Kwixo_Shipping_Setting
+ extends Mage_Core_Model_Mysql4_Abstract
+{
+
+ public function _construct()
+ {
+ $this->_init('ops/kwixo_shipping_setting', 'id');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting/Collection.php b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting/Collection.php
new file mode 100644
index 0000000..585c8ce
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Mysql4/Kwixo/Shipping/Setting/Collection.php
@@ -0,0 +1,21 @@
+
+ * @category Netresearch
+ * @package ${MODULENAME}
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Mysql4_Kwixo_Shipping_Setting_Collection
+ extends Mage_Core_Model_Mysql4_Collection_Abstract
+{
+
+ protected function _construct()
+ {
+ parent::_construct();
+ $this->_init('ops/kwixo_shipping_setting');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Observer.php b/app/code/community/Netresearch/OPS/Model/Observer.php
new file mode 100644
index 0000000..7e69de1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Observer.php
@@ -0,0 +1,725 @@
+
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Model_Observer
+ *
+ * @author André Herrn
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Model_Observer
+{
+
+ /**
+ * Get one page checkout model
+ *
+ * @return Mage_Checkout_Model_Type_Onepage
+ */
+ public function getOnepage()
+ {
+ return Mage::getSingleton('checkout/type_onepage');
+ }
+
+ public function getAdminSession()
+ {
+ return Mage::getSingleton('admin/session');
+ }
+
+ public function isAdminSession()
+ {
+
+ if ($this->getAdminSession()->getUser()) {
+ return 0 < $this->getAdminSession()->getUser()->getUserId();
+ }
+
+ return false;
+ }
+
+ public function getHelper($name = null)
+ {
+ if (null === $name) {
+ return Mage::helper('ops');
+ }
+
+ return Mage::helper('ops/' . $name);
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig()
+ {
+ return Mage::getModel('ops/config');
+ }
+
+ /**
+ * trigger ops payment
+ */
+ public function checkoutTypeOnepageSaveOrderBefore($observer)
+ {
+ $quote = $observer->getQuote();
+ $order = $observer->getOrder();
+ $code = $quote->getPayment()->getMethodInstance()->getCode();
+
+ try {
+ if ('ops_directDebit' == $code
+ && Mage::helper('ops/payment')->isInlinePaymentWithQuoteId(
+ $quote->getPayment()
+ )
+ ) {
+ $this->confirmDdPayment($order, $quote );
+ } elseif ($quote->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Abstract) {
+ $requestParams = $quote->getPayment()->getMethodInstance()->getFormFields($order, array(), false);
+ $this->invokeRequestParamValidation($requestParams);
+ }
+ } catch (Exception $e) {
+ $quote->setIsActive(true);
+ $this->getOnepage()->getCheckout()->setGotoSection('payment');
+ Mage::throwException($e->getMessage());
+ }
+ }
+
+ public function salesModelServiceQuoteSubmitFailure($observer)
+ {
+ $quote = $observer->getQuote();
+ if (Mage::helper('ops/payment')->isInlinePaymentWithQuoteId($quote->getPayment())) {
+ $this->handleFailedCheckout(
+ $observer->getQuote(),
+ $observer->getOrder()
+ );
+ }
+ }
+
+ protected function getQuoteCurrency($quote)
+ {
+ if ($quote->hasForcedCurrency()) {
+ return $quote->getForcedCurrency()->getCode();
+ } else {
+ return Mage::app()->getStore($quote->getStoreId())->getBaseCurrencyCode();
+ }
+ }
+
+ public function confirmAliasPayment($order, $quote)
+ {
+ $requestParams = Mage::helper('ops/creditcard')->getDirectLinkRequestParams($quote, $order);
+ $this->invokeRequestParamValidation($requestParams);
+ Mage::helper('ops/alias')->cleanUpAdditionalInformation($quote->getPayment(), true);
+
+ return $this->performDirectLinkRequest($quote, $requestParams, $quote->getStoreId());
+
+ }
+
+ public function confirmDdPayment($order, $quote)
+ {
+ /** @var Netresearch_OPS_Helper_DirectDebit $directDebitHelper */
+ $directDebitHelper = Mage::helper('ops/directDebit');
+ $requestParams = Mage::app()->getRequest()->getParam('ops_directDebit');
+ $directDebitHelper->handleAdminPayment($quote, $requestParams);
+ $requestParams = $directDebitHelper->getDirectLinkRequestParams($quote, $order, $requestParams);
+ $this->invokeRequestParamValidation($requestParams);
+
+ return $this->performDirectLinkRequest($quote, $requestParams, $quote->getStoreId());
+ }
+
+ public function performDirectLinkRequest($quote, $params, $storeId = null)
+ {
+ $url = Mage::getModel('ops/config')->getDirectLinkGatewayOrderPath($storeId);
+ $response = Mage::getSingleton('ops/api_directlink')->performRequest($params, $url, $storeId);
+ /**
+ * allow null as valid state for creating the order with status 'pending'
+ */
+ if (null != $response['STATUS'] && Mage::helper('ops/payment')->isPaymentFailed($response['STATUS'])) {
+ Mage::throwException($this->getHelper()->__('Ingenico ePayments Payment failed'));
+ }
+ $quote->getPayment()->setAdditionalInformation('ops_response', $response)->save();
+
+ }
+
+
+ /**
+ * Check if checkout was made with OPS CreditCart or DirectDebit
+ *
+ * @return boolean
+ */
+ protected function isCheckoutWithExistingTxId($code)
+ {
+ if ('ops_opsid' == $code) {
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ /**
+ * Replace order cancel comfirm message of Magento by a custom message from Ingenico ePayments
+ *
+ * @event adminhtml_block_html_before
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return Netresearch_OPS_Model_Observer
+ */
+ public function updateOrderCancelButton(Varien_Event_Observer $observer)
+ {
+ /* @var $block Mage_Adminhtml_Block_Template */
+ $block = $observer->getEvent()->getBlock();
+
+ //Stop if block is not sales order view
+ if ($block->getType() != 'adminhtml/sales_order_view') {
+ return $this;
+ }
+
+ //If payment method is one of the Ingenico ePayments-ones and order can be cancelled manually
+ if ($block->getOrder()->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Abstract
+ && true === $block->getOrder()->getPayment()->getMethodInstance()->canCancelManually($block->getOrder())
+ ) {
+ //Build message and update cancel button
+ $message = Mage::helper('ops')->__(
+ "Are you sure you want to cancel this order? Warning:" .
+ " Please check the payment status in the back-office of Ingenico ePayments before." .
+ " By cancelling this order you won\\'t be able to update the status in Magento anymore."
+ );
+ $block->updateButton(
+ 'order_cancel',
+ 'onclick',
+ 'deleteConfirm(\'' . $message . '\', \'' . $block->getCancelUrl() . '\')'
+ );
+ }
+
+ return $this;
+ }
+
+ /**
+ *
+ * appends a checkbox for closing the transaction if it's a Ingenico ePayments payment
+ *
+ * @event core_block_abstract_to_html_after
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return string
+ */
+ public function appendCheckBoxToRefundForm($observer)
+ {
+ $html = '';
+ /*
+ * show the checkbox only if the credit memo create page is displayed and
+ * the refund can be done online and the payment is done via Ingenico ePayments
+ */
+ if ($observer->getBlock() instanceof Mage_Adminhtml_Block_Sales_Order_Creditmemo_Totals
+ && $observer->getBlock()->getParentBlock()
+ instanceof Mage_Adminhtml_Block_Sales_Order_Creditmemo_Create_Items
+ && $observer->getBlock()->getParentBlock()->getCreditmemo()->getOrder()->getPayment()
+ && $observer->getBlock()->getParentBlock()->getCreditmemo()->getOrder()->getPayment()->getMethodInstance()
+ instanceof Netresearch_OPS_Model_Payment_Abstract
+ && $observer->getBlock()->getParentBlock()->getCreditmemo()->canRefund()
+ && $observer->getBlock()->getParentBlock()->getCreditmemo()->getInvoice()
+ && $observer->getBlock()->getParentBlock()->getCreditmemo()->getInvoice()->getTransactionId()
+ ) {
+ $transport = $observer->getTransport();
+ $block = $observer->getBlock();
+ $layout = $block->getLayout();
+ $html = $transport->getHtml();
+ $checkBoxHtml = $layout->createBlock(
+ 'ops/adminhtml_sales_order_creditmemo_totals_checkbox',
+ 'ops_refund_checkbox'
+ )
+ ->setTemplate('ops/sales/order/creditmemo/totals/checkbox.phtml')
+ ->renderView();
+ $html = $html . $checkBoxHtml;
+ $transport->setHtml($html);
+ }
+
+ return $html;
+ }
+
+ /**
+ *
+ * fetch the creation of credit memo event and display warning message when
+ * - credit memo could be done online
+ * - payment is a Ingenico ePayments payment
+ * - Ingenico ePayments transaction is closed
+ *
+ * @event core_block_abstract_to_html_after
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return string
+ */
+ public function showWarningForClosedTransactions($observer)
+ {
+ $html = '';
+ /**
+ * - credit memo could be done online
+ * - payment is a Ingenico ePayments payment
+ * - Ingenico ePayments transaction is closed
+ */
+ if ($observer->getBlock() instanceof Mage_Adminhtml_Block_Sales_Order_Creditmemo_Create
+ && $observer->getBlock()->getCreditmemo()->getOrder()->getPayment()
+ && $observer->getBlock()->getCreditmemo()->getOrder()->getPayment()->getMethodInstance()
+ instanceof Netresearch_OPS_Model_Payment_Abstract
+ && $observer->getBlock()->getCreditmemo()->getInvoice()
+ && $observer->getBlock()->getCreditmemo()->getInvoice()->getTransactionId()
+ && false === $observer->getBlock()->getCreditmemo()->canRefund()
+ ) {
+ $transport = $observer->getTransport();
+ $block = $observer->getBlock();
+ $layout = $block->getLayout();
+ $html = $transport->getHtml();
+ $warningHtml = $layout->createBlock(
+ 'ops/adminhtml_sales_order_creditmemo_closedTransaction_warning',
+ 'ops_closed-transaction-warning'
+ )->renderView();
+ $html = $warningHtml . $html;
+ $transport->setHtml($html);
+ }
+
+ return $html;
+ }
+
+
+ /**
+ * triggered by cron for deleting old payment data from the additional payment information
+ *
+ * @param $observer
+ */
+ public function cleanUpOldPaymentData()
+ {
+ Mage::helper('ops/quote')->cleanUpOldPaymentInformation();
+ }
+
+ /**
+ * in some cases the payment method is not set properly by Magento so we need to reset the
+ * payment method in the quote's payment before importing the data
+ *
+ * @event sales_quote_payment_import_data_before
+ *
+ * @param $observer
+ *
+ * @return $this
+ */
+ public function clearPaymentMethodFromQuote(Varien_Event_Observer $observer)
+ {
+ if ($observer->getEventName() == 'sales_quote_payment_import_data_before'
+ && $observer->getEvent()->getPayment() instanceof Mage_Sales_Model_Quote_Payment
+ ) {
+ $observer->getEvent()->getPayment()->setMethod(null);
+ }
+
+ return $this;
+ }
+
+ /**
+ * appends the status update button to the order's button in case it's an Ingenico ePayments payment
+ *
+ * @event core_block_abstract_prepare_layout_before
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return $this
+ */
+ public function addStatusUpdateButtonToOrderView(Varien_Event_Observer $observer)
+ {
+ $block = $observer->getBlock();
+ if ($block instanceof Mage_Adminhtml_Block_Sales_Order_View) {
+ $paymentMethod = $block->getOrder()->getPayment()->getMethodInstance();
+ if ($paymentMethod instanceof Netresearch_OPS_Model_Payment_Abstract
+ && Mage::getSingleton('admin/session')->isAllowed('sales/order/actions/invoice')
+ ) {
+
+ $block->addButton(
+ 'ops_refresh', array(
+ 'label' => Mage::helper('ops/data')->__('Refresh payment status'),
+ 'onclick' => 'setLocation(\'' . $block->getUrl('adminhtml/opsstatus/update') . '\')')
+ );
+ }
+ }
+
+ return $this;
+ }
+
+ /**
+ * @event core_block_abstract_prepare_layout_before
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return $this
+ */
+ public function addCcPaymentMethod(Varien_Event_Observer $observer)
+ {
+ /** @var $block Mage_Payment_Block_Form_Container */
+ $block = $observer->getEvent()->getBlock();
+ if ($block instanceof Mage_Payment_Block_Form_Container
+ && !Mage::helper('ops/version')->canUseApplicableForQuote(Mage::getEdition())
+ ) {
+ Mage::helper('ops/payment')->addCCForZeroAmountCheckout($block);
+ }
+
+ return $this;
+ }
+
+ /**
+ * @event core_block_abstract_prepare_layout_before
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return $this
+ */
+ public function disableCaptureForZeroAmountInvoice(Varien_Event_Observer $observer)
+ {
+ $block = $observer->getEvent()->getBlock();
+ if ($block instanceof Mage_Adminhtml_Block_Sales_Order_Invoice_Create_Items) {
+ $invoice = $block->getInvoice();
+ if ($invoice->getBaseGrandTotal() <= 0.01
+ && $invoice->getOrder()->getPayment()->getMethodInstance() instanceof
+ Netresearch_OPS_Model_Payment_Abstract
+ ) {
+ $invoice->getOrder()->getPayment()->getMethodInstance()->setCanCapture(false);
+ }
+ }
+
+ return $this;
+ }
+
+
+ /**
+ * @param $requestParams
+ *
+ * @throws Mage_Core_Exception
+ * @return Netresearch_OPS_Model_Observer
+ */
+ protected function invokeRequestParamValidation($requestParams)
+ {
+ $validator = Mage::getModel('ops/validator_parameter_factory')->getValidatorFor(
+ Netresearch_OPS_Model_Validator_Parameter_Factory::TYPE_REQUEST_PARAMS_VALIDATION
+ );
+ if (false == $validator->isValid($requestParams)) {
+ $this->getOnepage()->getCheckout()->setGotoSection('payment');
+ Mage::throwException(
+ $this->getHelper()->__('The data you have provided can not be processed by Ingenico ePayments')
+ );
+ }
+
+ return $this;
+ }
+
+
+ /**
+ * validates the input fields after the payment step in OPC
+ *
+ * @event controller_action_postdispatch_checkout_onepage_savePayment
+ *
+ * @param Varien_Event_Observer $event
+ *
+ * @return $this
+ */
+ public function controllerActionCheckoutOnepagePostdispatch(Varien_Event_Observer $event)
+ {
+ $controller = $event->getControllerAction();
+ $quote = $this->getOnepage()->getQuote();
+ if ($quote->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Abstract) {
+ /** @var Netresearch_OPS_Helper_Payment_Request $paramHelper */
+ $paramHelper = Mage::helper('ops/payment_request');
+ $shippingParams = array();
+ $ownerParams = $paramHelper->getOwnerParams($quote->getBillingAddress(), $quote);
+ $billingParams = $paramHelper->extractBillToParameters($quote->getBillingAddress(), $quote);
+ if ($quote->getShippingAddress()) {
+ $shippingParams = $paramHelper->extractShipToParameters($quote->getShippingAddress(), $quote);
+ }
+ $params = array_merge($ownerParams, $shippingParams, $billingParams);
+ $validator = Mage::getModel('ops/validator_parameter_factory')->getValidatorFor(
+ Netresearch_OPS_Model_Validator_Parameter_Factory::TYPE_REQUEST_PARAMS_VALIDATION
+ );
+ if (false == $validator->isValid($params)) {
+ $result = Mage::helper('ops/validation_result')->getValidationFailedResult(
+ $validator->getMessages(),
+ $quote
+ );
+ $controller->getResponse()->setBody(Mage::helper('core/data')->jsonEncode($result));
+ }
+ }
+
+ return $this;
+ }
+
+
+ public function salesOrderPaymentCapture(Varien_Event_Observer $event)
+ {
+ /** @var $payment Mage_Sales_Model_Order_Payment */
+ $payment = $event->getPayment();
+ $invoice = $event->getInvoice();
+ if ($payment->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Abstract) {
+ $payment->setInvoice($invoice);
+ }
+
+
+ return $this;
+ }
+
+ /**
+ * resets the order status back to pending payment in case of directlink payments in Ingenico ePayments authorize status
+ *
+ * @event sales_order_payment_place_end
+ *
+ * @param Varien_Event_Observer $event
+ */
+ public function setOrderStateDirectLink(Varien_Event_Observer $event)
+ {
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $event->getPayment();
+
+ if ($payment->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_DirectLink
+ && Mage::helper('ops/payment')->isInlinePayment($payment)
+ && Netresearch_OPS_Model_Status::AUTHORIZED == $payment->getAdditionalInformation('status')
+ && $payment->getOrder()->getState() != Mage_Sales_Model_Order::STATE_PENDING_PAYMENT
+ ) {
+ $payment->getOrder()->setState(
+ Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, true,
+ $this->getHelper()->__('Payment has been authorized by Ingenico ePayments, but not yet captured.')
+ );
+ }
+ }
+
+
+ /**
+ * appends the resend payment info button to the order's button in case it's an Ingenico ePayments payment
+ * and the payment status is an authorize status
+ *
+ * @event core_block_abstract_prepare_layout_before
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return $this
+ */
+ public function addResendPaymentInfoButtonToOrderView(Varien_Event_Observer $observer)
+ {
+ $block = $observer->getBlock();
+ if ($block instanceof Mage_Adminhtml_Block_Sales_Order_View) {
+ $payment = $block->getOrder()->getPayment();
+ $paymentMethod = $payment->getMethodInstance();
+ if ($paymentMethod instanceof Netresearch_OPS_Model_Payment_Abstract
+ && Mage::getSingleton('admin/session')->isAllowed('sales/order/actions/invoice')
+ && Netresearch_OPS_Model_Status::canResendPaymentInfo($payment->getAdditionalInformation('status'))
+ && !in_array(
+ $block->getOrder()->getState(),
+ array(
+ Mage_Sales_Model_Order::STATE_CANCELED,
+ Mage_Sales_Model_Order::STATE_CLOSED,
+ Mage_Sales_Model_Order::STATE_COMPLETE
+ )
+ )
+ ) {
+ $block->addButton(
+ 'ops_resend_info', array(
+ 'label' => Mage::helper('ops/data')->__('Resend payment information'),
+ 'onclick' => 'setLocation(\'' . $block->getUrl('adminhtml/admin/resendInfo') . '\')')
+ );
+ }
+ }
+ }
+
+ /**
+ * Adjusts the confirmation message text of the recurring profiles cancel and suspend button to inform the merchant
+ * that no call to Ingenico ePayments will happen
+ *
+ * @event adminhtml_block_html_before
+ *
+ * @param Varien_Event_Observer $observer
+ */
+ public function updateRecurringProfileButtons(Varien_Event_Observer $observer)
+ {
+ /** @var $block Mage_Sales_Block_Adminhtml_Recurring_Profile_View */
+ $block = $observer->getEvent()->getBlock();
+
+ if ($block->getType() == 'sales/adminhtml_recurring_profile_view') {
+ $profile = Mage::registry('current_recurring_profile');
+ if ($profile->getMethodCode() == Netresearch_OPS_Model_Payment_Recurring_Cc::CODE) {
+ $cancelMessage = Mage::helper('ops')
+ ->__(
+ 'Are you sure you want to perform this action?' .
+ ' Canceling the subscription here will not actually cancel the subscription on Ingenico ePayments side.' .
+ ' To stop charging the customer you will have to deactivate the subscription there.'
+ );
+ $cancelUrl = $block->getUrl(
+ '*/*/updateState',
+ array('profile' => $profile->getId(), 'action' => 'cancel')
+ );
+
+ $block->updateButton(
+ 'cancel',
+ 'onclick',
+ "confirmSetLocation('{$cancelMessage}', '{$cancelUrl}')"
+ );
+
+ $suspendMessage = Mage::helper('ops')
+ ->__(
+ 'Are you sure you want to perform this action?' .
+ 'Suspending the subscription here will not actually cancel the subscription on Ingenico ePayments side.' .
+ 'To stop charging the customer you will have to deactivate the subscription there.'
+ );
+ $suspendUrl = $block->getUrl(
+ '*/*/updateState',
+ array('profile' => $profile->getId(), 'action' => 'suspend')
+ );
+
+ $block->updateButton(
+ 'suspend',
+ 'onclick',
+ "confirmSetLocation('{$suspendMessage}', '{$suspendUrl}')"
+ );
+ }
+ }
+ }
+
+ /**
+ * Overwrites the state of the recurring profile if necessary
+ *
+ * @event model_save_before - due to lack of event prefix for recurring profile models
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return $this
+ */
+ public function overrideRecurringProfileState(Varien_Event_Observer $observer)
+ {
+ $object = $observer->getObject();
+
+ /** @var $object Mage_Payment_Model_Recurring_Profile */
+ if ($object instanceof Mage_Payment_Model_Recurring_Profile
+ && $object->getMethodCode() === Netresearch_OPS_Model_Payment_Recurring_Cc::CODE
+ && $object->getState() != $object->getNewState()
+ && $object->getOverrideState() === true
+ ) {
+ $object->setState($object->getNewState());
+ }
+
+ return $this;
+ }
+
+
+ /**
+ * @event adminhtml_block_html_before
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @return $this
+ */
+ public function updateRecurringProfileEditForm(Varien_Event_Observer $observer)
+ {
+ if ($observer->getBlock() instanceof Mage_Sales_Block_Adminhtml_Recurring_Profile_Edit_Form
+ && Mage::getModel('ops/payment_recurring_cc')->getConfigData('active')
+ ) {
+ /** @var Mage_Sales_Block_Adminhtml_Recurring_Profile_Edit_Form $form */
+ $html = $observer->getTransport()->getHtml();
+
+ $method = Mage::getModel('ops/payment_recurring_cc');
+
+ $message = Mage::helper('ops')
+ ->__(
+ "When using %s as payment method the settings for '%s' and '%s' will not be processed.",
+ $method->getTitle(),
+ Mage::helper('payment')->__('Allow Initial Fee Failure'),
+ Mage::helper('payment')->__('Maximum Payment Failures')
+ );
+
+ $message = '';
+ $observer->getTransport()->setHtml($html . $message);
+
+
+ }
+
+ return $this;
+ }
+
+ /**
+ * Since there is no other way for inline payments to change the order state, we enforce the pending_payment state
+ * for only authorized, not yet payed orders
+ *
+ * @param Varien_Event_Observer $observer
+ *
+ * @event sales_order_payment_place_end
+ * @return $this
+ */
+ public function enforcePaymentPendingForAuthorizedOrders(Varien_Event_Observer $observer)
+ {
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $observer->getData('payment');
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $payment->getOrder();
+
+ $status = $payment->getAdditionalInformation('status');
+ if ($this->getConfig()->getPaymentAction($order->getStoreId())
+ == Netresearch_OPS_Model_Payment_Abstract::ACTION_AUTHORIZE
+ && Netresearch_OPS_Model_Status::isAuthorize($status)
+ && $order->getState() != Mage_Sales_Model_Order::STATE_PENDING_PAYMENT
+ ) {
+ $message = $this->getHelper()->__('Order has been authorized, but not captured/paid yet.');
+ $order->setState(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, true, $message);
+
+ }
+
+ return $this;
+ }
+
+ /**
+ * Magento does not send order confirmation emails when
+ * - payment action "authorization" is processed in frontend via gateway.
+ * Magento does not send invoice emails when
+ * - payment action "authorization+capture" is processed in frontend or admin
+ *
+ * event: checkout_submit_all_after
+ *
+ * @param Varien_Event_Observer $observer
+ */
+ public function sendTransactionalEmails(Varien_Event_Observer $observer)
+ {
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $observer->getOrder();
+ if ($order == null || !$order->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Abstract) {
+ // ignore third-party payment methods
+ return;
+ }
+
+ /** @var Mage_Sales_Model_Quote $quote */
+ $quote = $observer->getQuote();
+ if ($quote && $quote->getPayment()->getOrderPlaceRedirectUrl()) {
+ // redirect payments require special treatment, may still get cancelled or declined
+ return;
+ }
+
+ try {
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ Mage::helper('ops/data')->sendTransactionalEmail($order->getPayment()->getCreatedInvoice());
+ } catch (Exception $e) {
+ Mage::logException($e);
+ }
+ }
+
+ /**
+ * triggers the email sending for payment method payPerMail
+ *
+ * event: sales_order_place_after
+ *
+ * @param Varien_Event_Observer $observer
+ */
+ public function sendPayPerMailInfo(Varien_Event_Observer $observer)
+ {
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $observer->getOrder();
+ if (!$order->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_PayPerMail) {
+ return;
+ }
+
+ /** @var Netresearch_OPS_Model_Payment_Features_PaymentEmail $sendEmailModel */
+ $sendEmailModel = Mage::getModel('ops/payment_features_paymentEmail');
+ $sendEmailModel->resendPaymentInfo($order);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Abstract.php b/app/code/community/Netresearch/OPS/Model/Payment/Abstract.php
new file mode 100644
index 0000000..1ef1316
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Abstract.php
@@ -0,0 +1,1127 @@
+encoding;
+ }
+
+ /**
+ * @param string $encoding
+ */
+ public function setEncoding($encoding)
+ {
+ $this->encoding = $encoding;
+ }
+
+ /**
+ * @param null $backendOperationParameterModel
+ */
+ public function setBackendOperationParameterModel($backendOperationParameterModel)
+ {
+ $this->backendOperationParameterModel = $backendOperationParameterModel;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Backend_Operation_Parameter
+ */
+ public function getBackendOperationParameterModel()
+ {
+ if (null === $this->backendOperationParameterModel) {
+ $this->backendOperationParameterModel = Mage::getModel('ops/backend_operation_parameter');
+ }
+
+ return $this->backendOperationParameterModel;
+ }
+
+ /**
+ * Return OPS Config
+ *
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig()
+ {
+ if (null === $this->_config) {
+ $this->_config = Mage::getSingleton('ops/config');
+ }
+
+ return $this->_config;
+ }
+
+ public function getConfigPaymentAction()
+ {
+ return $this->getPaymentAction();
+ }
+
+ /**
+ * get the frontend gateway path based on encoding property
+ */
+ public function getFrontendGateWay()
+ {
+ $gateway = $this->getConfig()->getFrontendGatewayPath();
+
+ return $gateway;
+ }
+
+ /**
+ * return if shipment params are needed for request
+ *
+ * @return bool
+ */
+ public function getNeedsShipToParams()
+ {
+ return $this->_needsShipToParams;
+ }
+
+ /**
+ * return if billing params are needed for request
+ *
+ * @return bool
+ */
+ public function getNeedsBillToParams()
+ {
+ return $this->_needsBillToParams;
+ }
+
+ /**
+ * returns the request helper
+ *
+ * @return Netresearch_OPS_Helper_Payment_Request
+ */
+ public function getRequestHelper()
+ {
+ if (null === $this->requestHelper) {
+ $this->requestHelper = Mage::helper('ops/payment_request');
+ }
+
+ return $this->requestHelper;
+ }
+
+ /**
+ * if payment method is available
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return boolean
+ */
+ public function isAvailable($quote = null)
+ {
+
+ $storeId = 0;
+ // allow multi store/site for backend orders with disabled backend payment methods in default store
+ if (null != $quote && null != $quote->getId()) {
+ $storeId = $quote->getStoreId();
+ }
+ if (Mage_Core_Model_App::ADMIN_STORE_ID == Mage::app()->getStore()->getId()
+ && false == $this->isEnabledForBackend($storeId)
+ ) {
+ return false;
+ }
+
+ return parent::isAvailable($quote);
+ }
+
+ /**
+ * if method is enabled for backend payments
+ *
+ * @param int $storeId
+ * @return bool
+ */
+ public function isEnabledForBackend($storeId = 0)
+ {
+ return $this->getConfig()->isEnabledForBackend($this->_code, $storeId);
+ }
+
+ /**
+ * Redirect url to ops submit form
+ *
+ * @return string
+ */
+ public function getOrderPlaceRedirectUrl()
+ {
+ return $this->getConfig()->getPaymentRedirectUrl();
+ }
+
+ public function getOpsBrand($payment = null)
+ {
+ if (null === $payment) {
+ $payment = $this->getInfoInstance();
+ }
+ $brand = trim($payment->getAdditionalInformation('BRAND'));
+ if (!strlen($brand)) {
+ $brand = $this->brand;
+ }
+
+ return $brand;
+ }
+
+ public function getOpsCode($payment = null)
+ {
+ if (null === $payment) {
+ $payment = $this->getInfoInstance();
+ }
+ $pm = trim($payment->getAdditionalInformation('PM'));
+ if (!strlen($pm)) {
+ $pm = $this->pm;
+ }
+
+ return $pm;
+ }
+
+ /**
+ * Return payment_action value from config area
+ *
+ * @return string
+ */
+ public function getPaymentAction()
+ {
+ return $this->getConfig()->getPaymentAction($this->getStoreId());
+ }
+
+ /**
+ * @param Mage_Sales_Model_Order $order
+ * @param string[]|null $requestParams
+ *
+ * @return string[]
+ */
+ public function getMethodDependendFormFields($order, $requestParams = null)
+ {
+ $billingAddress = $order->getBillingAddress();
+ $shippingAddress = $order->getShippingAddress();
+ if (null === $shippingAddress || false === $shippingAddress) {
+ $shippingAddress = $billingAddress;
+ }
+ $payment = $order->getPayment()->getMethodInstance();
+ $quote = Mage::helper('ops/order')->getQuote($order->getQuoteId());
+
+ $formFields = array();
+ $formFields['ORIG'] = Mage::helper("ops")->getModuleVersionString();
+ $formFields['BRAND'] = $payment->getOpsBrand($order->getPayment());
+ if ($this->getConfig()->canSubmitExtraParameter($order->getStoreId())) {
+ $formFields['CN'] = $billingAddress->getFirstname() . ' ' . $billingAddress->getLastname();
+ $formFields['COM'] = $this->_getOrderDescription($order);
+ $formFields['ADDMATCH'] = Mage::helper('ops/order')->checkIfAddressesAreSame($order);
+ $ownerParams = $this->getRequestHelper()->getOwnerParams($billingAddress, $quote);
+ $formFields['ECOM_BILLTO_POSTAL_POSTALCODE'] = $billingAddress->getPostcode();
+ $formFields = array_merge($formFields, $ownerParams);
+ }
+
+ if (Mage::helper('customer/data')->isLoggedIn()) {
+ $formFields['CUID'] = Mage::helper('customer')->getCustomer()->getId();
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * return ship to params if needed otherwise false
+ *
+ * @param $shippingAddress
+ *
+ * @return array|bool
+ */
+ public function getShipToParams($shippingAddress)
+ {
+ $shipToParams = false;
+ if ($this->getNeedsShipToParams()
+ && $this->getConfig()->canSubmitExtraParameter()
+ && $shippingAddress
+ ) {
+ $shipToParams = $this->getRequestHelper()->extractShipToParameters($shippingAddress);
+ }
+
+ return $shipToParams;
+ }
+
+ /**
+ * return ship to params if needed otherwise false
+ *
+ * @param $billingAddress
+ *
+ * @return array|bool
+ */
+ public function getBillToParams($billingAddress)
+ {
+ $billToParams = false;
+ if ($this->getNeedsBillToParams()
+ && $this->getConfig()->canSubmitExtraParameter()
+ && $billingAddress
+ ) {
+ $billToParams = $this->getRequestHelper()->extractBillToParameters($billingAddress);
+ }
+
+ return $billToParams;
+ }
+
+ /**
+ * Prepare params array to send it to gateway page via POST
+ *
+ * @param $order
+ * @param $requestParams
+ * @param bool $isRequest
+ * @return array
+ */
+ public function getFormFields($order, $requestParams, $isRequest = true)
+ {
+ $requestHelper = Mage::helper('ops/payment_request');
+
+ if (empty($order)) {
+ if (!($order = $this->getOrder())) {
+ return array();
+ }
+ }
+
+ // get mandatory parameters
+ $formFields = $this->getMandatoryFormFields($order);
+
+ $paymentAction = $this->_getOPSPaymentOperation();
+ if ($paymentAction ) {
+ $formFields['OPERATION'] = $paymentAction;
+ }
+
+ $formFields = array_merge($formFields, $requestHelper->getTemplateParams($order->getStoreId()));
+
+ $opsOrderId = Mage::helper('ops/order')->getOpsOrderId($order);
+ $formFields['ACCEPTURL'] = $this->getConfig()->getAcceptUrl();
+ $formFields['DECLINEURL'] = $this->getConfig()->getDeclineUrl();
+ $formFields['EXCEPTIONURL'] = $this->getConfig()->getExceptionUrl();
+ $formFields['CANCELURL'] = $this->getConfig()->getCancelUrl();
+ $formFields['BACKURL'] = $this->getConfig()->getPaymentRetryUrl(
+ Mage::helper('ops/payment')->validateOrderForReuse($opsOrderId, $order->getStoreId())
+ );
+
+
+ /** @var $order Mage_Sales_Model_Order */
+ $shipToFormFields = $this->getShipToParams($order->getShippingAddress());
+ if (is_array($shipToFormFields)) {
+ $formFields = array_merge($formFields, $shipToFormFields);
+ }
+
+ $billToFormFields = $this->getBillToParams($order->getBillingAddress());
+ if (is_array($billToFormFields)) {
+ $formFields = array_merge($formFields, $billToFormFields);
+ }
+
+ $cartDataFormFields = $this->getOrderItemData($order);
+
+ if (is_array($cartDataFormFields)) {
+ $formFields = array_merge($formFields, $cartDataFormFields);
+ }
+
+ // get method specific parameters
+ $methodDependendFields = $this->getMethodDependendFormFields($order, $requestParams);
+ if (is_array($methodDependendFields)) {
+ $formFields = array_merge($formFields, $methodDependendFields);
+ }
+
+ $formFields = $this->transliterateParams($formFields);
+
+ $shaSign = Mage::helper('ops/payment')->shaCrypt(
+ Mage::helper('ops/payment')
+ ->getSHASign($formFields, null, $order->getStoreId())
+ );
+
+ if ($isRequest) {
+ $helper = Mage::helper('ops');
+ $helper->log(
+ $helper->__(
+ "Register Order %s in Ingenico ePayments \n\nAll form fields: %s\nIngenico ePayments String to hash: %s\nHash: %s",
+ $order->getIncrementId(),
+ serialize($formFields),
+ Mage::helper('ops/payment')->getSHASign($formFields, null, $order->getStoreId()),
+ $shaSign
+ )
+ );
+ }
+
+ $formFields['SHASIGN'] = $shaSign;
+
+ return $formFields;
+ }
+
+ /**
+ * Get OPS Payment Action value
+ *
+ * @param string
+ *
+ * @return string
+ */
+ protected function _getOPSPaymentOperation()
+ {
+ $value = $this->getPaymentAction();
+ if ($value == Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE) {
+ $value = self::OPS_AUTHORIZE_ACTION;
+ } elseif ($value == Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE) {
+ $value = self::OPS_AUTHORIZE_CAPTURE_ACTION;
+ }
+
+ return $value;
+ }
+
+ /**
+ * get formated order description
+ *
+ * @param Mage_Sales_Model_Order
+ *
+ * @return string
+ */
+ public function _getOrderDescription($order)
+ {
+ /** @var Mage_Sales_Model_Order_Item[] $items */
+ $items = $order->getAllItems();
+ $description = array_reduce(
+ $items,
+ function ($acc, $item) {
+ /** @var Mage_Sales_Model_Order_Item $item */
+ if (!$item->getParentItem()) {
+ $acc .= ($acc != '' ? ', ' : '') . $item->getName();
+ }
+ return $acc;
+ }, ''
+ );
+
+ return $description;
+ }
+
+ /**
+ * Get Main OPS Helper
+ *
+ * @return Netresearch_OPS_Helper_Data
+ */
+ public function getHelper()
+ {
+ return Mage::helper('ops/data');
+ }
+
+ /**
+ * Method that will be executed instead of authorize or capture
+ * if flag isInitializeNeeded set to true
+ *
+ * @param string $paymentAction
+ * @param object $stateObject
+ *
+ * @return Mage_Payment_Model_Abstract
+ */
+ public function initialize($paymentAction, $stateObject)
+ {
+ $stateObject->setState(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT)
+ ->setStatus(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT);
+
+ if (!$paymentAction) {
+ $paymentAction = $this->getConfigPaymentAction();
+ }
+
+ $message = $this->getHelper()
+ ->__('Customer got redirected to Ingenico ePayments for %s. Awaiting feedback.', $paymentAction);
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $this->getInfoInstance()->getOrder();
+
+ $order->addStatusHistoryComment($message);
+
+ return $this;
+ }
+
+ /**
+ * accept payment
+ *
+ * @see \Mage_Sales_Model_Order_Payment::registerPaymentReviewAction
+ *
+ * @param Mage_Payment_Model_Info $payment
+ *
+ * @return boolean
+ * @throws Mage_Core_Exception
+ */
+ public function acceptPayment(Mage_Payment_Model_Info $payment)
+ {
+ parent::acceptPayment($payment);
+ $status = $payment->getAdditionalInformation('status');
+
+ if ($status == Netresearch_OPS_Model_Status::AUTHORIZED
+ || $status == Netresearch_OPS_Model_Status::PAYMENT_REQUESTED)
+ {
+ return true;
+ }
+
+ Mage::throwException(
+ $this->getHelper()->__(
+ 'The order can not be accepted via Magento. For the actual status of the payment check the Ingenico ePayments backend.'
+ )
+ );
+ }
+
+ /**
+ * cancel order if in payment review state
+ *
+ * @see \Mage_Sales_Model_Order_Payment::registerPaymentReviewAction
+ *
+ * @param Mage_Payment_Model_Info $payment
+ *
+ * @return boolean
+ * @throws Mage_Core_Exception
+ */
+ public function denyPayment(Mage_Payment_Model_Info $payment)
+ {
+ parent::denyPayment($payment);
+
+ Mage::getSingleton('admin/session')->addNotice(
+ $this->getHelper()->__(
+ 'Order has been canceled permanently in Magento. Changes in Ingenico ePayments platform will no longer be considered.')
+ );
+
+ return true;
+ }
+
+ /**
+ * check if payment is in payment review state
+ *
+ * @param Mage_Payment_Model_Info $payment
+ *
+ * @return bool
+ */
+ public function canReviewPayment(Mage_Payment_Model_Info $payment)
+ {
+ $status = $payment->getAdditionalInformation('status');
+ return Netresearch_OPS_Model_Status::canResendPaymentInfo($status);
+ }
+
+ /**
+ * Determines if a capture will be processed
+ *
+ * @param Varien_Object $payment
+ * @param float $amount
+ *
+ * @throws Mage_Core_Exception
+ * @return \Mage_Payment_Model_Abstract|void
+ */
+ public function capture(Varien_Object $payment, $amount)
+ {
+ // disallow Ingenico ePayments online capture if amount is zero
+ if ($amount < 0.01) {
+ return parent::capture($payment, $amount);
+ }
+
+ if (true === Mage::registry('ops_auto_capture')) {
+ Mage::unregister('ops_auto_capture');
+
+ return parent::capture($payment, $amount);
+ }
+
+ $orderId = $payment->getOrder()->getId();
+ $arrInfo = Mage::helper('ops/order_capture')->prepareOperation($payment, $amount);
+ $storeId = $payment->getOrder()->getStoreId();
+
+ if ($this->isRedirectNoticed($orderId)) {
+ return $this;
+ }
+ try {
+ $requestParams = $this->getBackendOperationParameterModel()->getParameterFor(
+ self::OPS_CAPTURE_TRANSACTION_TYPE,
+ $this,
+ $payment,
+ $amount
+ );
+ $requestParams = $this->transliterateParams($requestParams);
+ $response = Mage::getSingleton('ops/api_directlink')->performRequest(
+ $requestParams,
+ Mage::getModel('ops/config')->getDirectLinkGatewayPath($storeId),
+ $storeId
+ );
+
+ Mage::getModel('ops/response_handler')->processResponse($response, $this, false);
+
+ } catch (Exception $e) {
+ Mage::getModel('ops/status_update')->updateStatusFor($payment->getOrder());
+ Mage::helper('ops')->log("Exception in capture request:" . $e->getMessage());
+ Mage::throwException($e->getMessage());
+ }
+
+ return $this;
+ }
+
+ /**
+ * Refund
+ *
+ * @param Varien_Object $payment
+ * @param float $amount
+ *
+ * @return \Mage_Payment_Model_Abstract|void
+ */
+ public function refund(Varien_Object $payment, $amount)
+ {
+ /** @var Netresearch_OPS_Helper_Order_Refund $refundHelper */
+ $refundHelper = Mage::helper('ops/order_refund');
+
+ if ($refundHelper->getOpenRefundTransaction($payment)->getId()) {
+ Mage::throwException(
+ $this->getHelper()->__(
+ "There is already one creditmemo in the queue." .
+ "The Creditmemo will be created automatically as soon as Ingenico ePayments sends an acknowledgement."
+ )
+ );
+ }
+
+ $refundHelper->setAmount($amount)->setPayment($payment);
+ $storeId = $payment->getOrder()->getStoreId();
+
+ try {
+ $requestParams = $this->getBackendOperationParameterModel()->getParameterFor(
+ self::OPS_REFUND_TRANSACTION_TYPE,
+ $this,
+ $payment,
+ $amount
+ );
+ $requestParams = $this->transliterateParams($requestParams);
+ $response = Mage::getSingleton('ops/api_directlink')->performRequest(
+ $requestParams,
+ Mage::getModel('ops/config')->getDirectLinkGatewayPath($storeId),
+ $storeId
+ );
+ Mage::getModel('ops/response_handler')->processResponse($response, $this, false);
+ } catch (Exception $e) {
+ Mage::logException($e);
+ Mage::getModel('ops/status_update')->updateStatusFor($payment->getOrder());
+ Mage::throwException($e->getMessage());
+ }
+
+ return $this;
+ }
+
+ /**
+ * Returns the mandatory fields for requests to Ingenico ePayments
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return array
+ */
+ public function getMandatoryFormFields($order)
+ {
+ $formFields = Mage::helper('ops/payment_request')->getMandatoryRequestFields($order);
+ $paymentAction = $this->_getOPSPaymentOperation();
+ if ($paymentAction) {
+ $formFields['OPERATION'] = $paymentAction;
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * determines if the close transaction parameter is set in the credit memo data
+ *
+ * @param array $creditMemoData
+ *
+ * @return bool
+ */
+ protected function getCloseTransactionFromCreditMemoData($creditMemoData)
+ {
+ $closeTransaction = false;
+ if (array_key_exists('ops_close_transaction', $creditMemoData)
+ && strtolower(trim($creditMemoData['ops_close_transaction'])) == 'on'
+ ) {
+ $closeTransaction = true;
+ }
+
+ return $closeTransaction;
+ }
+
+ /**
+ * Custom cancel behavior, deny cancel and force custom to use void instead
+ *
+ * @param Varien_Object $payment
+ *
+ * @return void
+ * @throws Mage_Core_Exception
+ */
+ public function cancel(Varien_Object $payment)
+ {
+ /*
+ * Important: If an order was voided successfully and the user clicks on cancel in order-view
+ * this method is not triggered anymore
+ */
+
+ //Proceed parent cancel method in case that regirstry value ops_auto_void is set
+ if (true === Mage::registry('ops_auto_void')) {
+ Mage::unregister('ops_auto_void');
+ return parent::cancel($payment);
+ }
+
+ //If order has state 'pending_payment' and the payment has Ingenico ePayments-status 0 or null (unknown) then cancel the order
+ if (true === $this->canCancelManually($payment->getOrder())) {
+ $payment->getOrder()->addStatusHistoryComment(
+ $this->getHelper()->__("The order was cancelled manually. The Ingenico ePayments-state is 0 or null.")
+ );
+
+ return parent::cancel($payment);
+ }
+
+ //Abort cancel method by throwing a Mage_Core_Exception
+ Mage::throwException($this->getHelper()->__('Please use void to cancel the operation.'));
+ }
+
+ /**
+ * Custom void behavior, trigger Ingenico ePayments cancel request
+ *
+ * @param Varien_Object $payment
+ * @return $this|void
+ */
+ public function void(Varien_Object $payment)
+ {
+
+ $status = $payment->getAdditionalInformation('status');
+
+ if (!Netresearch_OPS_Model_Status::canVoidTransaction($status)) {
+ Mage::throwException($this->getHelper()->__('Status %s can not be voided.', $status));
+ }
+
+ //Set initital params
+ $orderID = $payment->getOrder()->getId();
+ $order = Mage::getModel("sales/order")->load($orderID);
+
+ //Calculate amount which has to be captured
+ $alreadyCaptured = $payment->getBaseAmountPaidOnline();
+
+ $grandTotal = Mage::helper('ops/payment')
+ ->getBaseGrandTotalFromSalesObject($order);
+ $voidAmount = $grandTotal - $alreadyCaptured;
+ $storeId = $order->getStoreId();
+ //Build void directLink-Request-Params
+ $requestParams = array(
+ 'AMOUNT' => $this->getHelper()->getAmount($voidAmount),
+ 'PAYID' => $payment->getAdditionalInformation('paymentId'),
+ 'OPERATION' => self::OPS_DELETE_AUTHORIZE,
+ 'CURRENCY' => Mage::app()->getStore($storeId)->getBaseCurrencyCode()
+ );
+
+ //Check if there is already a waiting void transaction, if yes: redirect to order view
+ if (Mage::helper('ops/directlink')->checkExistingTransact(
+ self::OPS_VOID_TRANSACTION_TYPE, $orderID
+ )
+ ) {
+ $this->getHelper()->getAdminSession()->addError(
+ $this->getHelper()->__(
+ 'You already sent a void request. Please wait until the void request will be acknowledged.'
+ )
+ );
+
+ return;
+ }
+
+ try {
+ //perform ops cancel request
+ $response = Mage::getSingleton('ops/api_directlink')
+ ->performRequest(
+ $requestParams,
+ Mage::getModel('ops/config')->getDirectLinkGatewayPath($storeId),
+ $order->getStoreId()
+ );
+
+ if ($response['STATUS'] == Netresearch_OPS_Model_Status::INVALID_INCOMPLETE
+ && $payment->getAdditionalInformation('status') == Netresearch_OPS_Model_Status::PAYMENT_REQUESTED
+ ) {
+ Mage::throwException(
+ $this->getHelper()->__('Order can no longer be voided. You have to refund the order online.')
+ );
+ }
+
+
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $this, false);
+
+
+ return $this;
+
+ } catch (Exception $e) {
+ Mage::getModel('ops/status_update')->updateStatusFor($payment->getOrder());
+ Mage::helper('ops')->log(
+ "Exception in void request:" . $e->getMessage()
+ );
+ Mage::throwException($e->getMessage());
+ }
+ }
+
+ /**
+ * get question for fields with disputable value
+ * users are asked to correct the values before redirect to Ingenico ePayments
+ *
+ *
+ * @return string
+ */
+ public function getQuestion()
+ {
+ return '';
+ }
+
+ /**
+ * get an array of fields with disputable value
+ * users are asked to correct the values before redirect to Ingenico ePayments
+ *
+ * @param Mage_Sales_Model_Order $order Current order
+ *
+ * @return array
+ */
+ public function getQuestionedFormFields($order)
+ {
+ return array();
+ }
+
+ /**
+ * if we need some missing form params
+ * users are asked to correct the values before redirect to Ingenico ePayments
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param array $requestParams Parameters sent in current request
+ * @param array $formFields Parameters to be sent to Ingenico ePayments
+ *
+ * @return bool
+ */
+ public function hasFormMissingParams($order, $requestParams, $formFields = null)
+ {
+ if (false == is_array($requestParams)) {
+ $requestParams = array();
+ }
+ if (null === $formFields) {
+ $formFields = $this->getFormFields($order, $requestParams, false);
+ }
+ $availableParams = array_merge($requestParams, $formFields);
+ $requiredParams = $this->getQuestionedFormFields($order);
+ foreach ($requiredParams as $requiredParam) {
+ if (false == array_key_exists($requiredParam, $availableParams)
+ || 0 == strlen($availableParams[$requiredParam])
+ ) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ /**
+ * Check if order can be cancelled manually
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return bool
+ */
+ public function canCancelManually($order)
+ {
+ $payment = $order->getPayment();
+
+ //If payment has Ingenico ePayments-status 0 or null (unknown) or another offline cancelable status
+ $status = $payment->getAdditionalInformation('status');
+
+ return (null === $status)
+ || in_array(
+ $status, array(
+ Netresearch_OPS_Model_Status::INVALID_INCOMPLETE,
+ Netresearch_OPS_Model_Status::CANCELED_BY_CUSTOMER,
+ Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED,
+ Netresearch_OPS_Model_Status::PAYMENT_DELETED
+ )
+ );
+ }
+
+ public function getOpsHtmlAnswer($payment = null)
+ {
+ $returnValue = '';
+ if (null === $payment) {
+ $quoteId = Mage::getSingleton('checkout/session')->getQuote()->getId();
+ if (null === $quoteId) {
+ $orderIncrementId = Mage::getSingleton('checkout/session')->getLastRealOrderId();
+ $order = Mage::getModel('sales/order')->loadByAttribute('increment_id', $orderIncrementId);
+ } else {
+ $order = Mage::getModel('sales/order')->loadByAttribute('quote_id', $quoteId);
+ }
+ if ($order instanceof Mage_Sales_Model_Order && 0 < $order->getId()) {
+ $payment = $order->getPayment();
+ $returnValue = $payment->getAdditionalInformation('HTML_ANSWER');
+ }
+ } elseif ($payment instanceof Mage_Payment_Model_Info) {
+ $returnValue = $payment->getAdditionalInformation('HTML_ANSWER');
+ }
+
+ return $returnValue;
+ }
+
+ public function getShippingTaxRate($order)
+ {
+ return $this->getRequestHelper()->getShippingTaxRate($order);
+ }
+
+ protected function isRedirectNoticed($orderId)
+ {
+ if (Mage::helper('ops/directlink')->checkExistingTransact(self::OPS_CAPTURE_TRANSACTION_TYPE, $orderId)) {
+ $this->getHelper()->redirectNoticed(
+ $orderId,
+ $this->getHelper()->__(
+ 'You already sent a capture request. Please wait until the capture request is acknowledged.'
+ )
+ );
+
+ return true;
+ }
+ if (Mage::helper('ops/directlink')->checkExistingTransact(self::OPS_VOID_TRANSACTION_TYPE, $orderId)) {
+ $this->getHelper()->redirectNoticed(
+ $orderId,
+ $this->getHelper()->__(
+ 'There is one void request waiting. Please wait until this request is acknowledged.'
+ )
+ );
+
+ return true;
+ }
+
+ return false;
+ }
+
+ public function setConfig(Netresearch_OPS_Model_Config $config)
+ {
+ $this->_config = $config;
+ }
+
+ /**
+ * If cart Item information has to be transmitted to Ingenico ePayments
+ *
+ * @return bool
+ */
+
+ public function needsOrderItemDataForRequest()
+ {
+ return $this->_needsCartDataForRequest;
+ }
+
+ /**
+ * Returns array with the order item data formatted in Ingenico ePayments fashion if payment method implementation
+ * needs the data otherwise just returns false.
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return array|false
+ */
+ public function getOrderItemData(Mage_Sales_Model_Order $order)
+ {
+ if (!$this->needsOrderItemDataForRequest()) {
+ return false;
+ }
+
+ return $this->getRequestHelper()->extractOrderItemParameters($order);
+ }
+
+ /**
+ * @inheritDoc
+ */
+ public function canVoid(Varien_Object $payment)
+ {
+ if (Netresearch_OPS_Model_Status::canVoidTransaction($payment->getAdditionalInformation('status'))) {
+ return parent::canVoid($payment);
+ } else {
+ return false;
+ }
+
+ }
+
+ /**
+ * @inheritDoc
+ */
+ public function assignData($data)
+ {
+ parent::assignData($data);
+
+ $paymentInfo = $this->getInfoInstance();
+ if ($data instanceof Varien_Object && $data->getData($this->getCode().'_data')) {
+ foreach ($data->getData($this->getCode().'_data') as $key => $value) {
+ $paymentInfo->setAdditionalInformation($key, $value);
+ }
+ }
+
+ return $this;
+ }
+
+
+ /**
+ * @inheritDoc
+ */
+ public function validate()
+ {
+
+ $paymentInfo = $this->getInfoInstance();
+ if ($paymentInfo instanceof Mage_Sales_Model_Order_Payment) {
+ $billingAddress = $paymentInfo->getOrder()->getBillingAddress();
+ $shippingAddress = $paymentInfo->getOrder()->getShippingAddress();
+ $salesObject = $paymentInfo->getOrder();
+ } else {
+ /** @var Mage_Sales_Model_Quote $salesObject */
+ $salesObject = $paymentInfo->getQuote();
+ $billingAddress = $salesObject->getBillingAddress();
+ $shippingAddress = $salesObject->getShippingAddress();
+ }
+
+ /** @var Netresearch_OPS_Model_Validator_Parameter_Length $validator */
+ $validator = Mage::getModel('ops/validator_parameter_factory')->getValidatorFor(
+ Netresearch_OPS_Model_Validator_Parameter_Factory::TYPE_REQUEST_PARAMS_VALIDATION
+ );
+
+ $params = $this->getRequestHelper()->getOwnerParams($billingAddress, $salesObject);
+ $billingParams = $this->getBillToParams($billingAddress);
+ $shippingParams = $this->getShipToParams($shippingAddress);
+ if ($shippingParams) {
+ $params = array_merge($params, $shippingParams);
+ }
+ if ($billingParams) {
+ $params = array_merge($params, $billingParams);
+ }
+ $params['CN'] = $billingAddress->getFirstname() . ' ' . $billingAddress->getLastname();
+
+ if (false === $validator->isValid($params)) {
+ $result = Mage::helper('ops/validation_result')->getValidationFailedResult(
+ $validator->getMessages(), $salesObject
+ );
+ throw Mage::exception('Mage_Payment', implode(', ', $result['fields']));
+ }
+
+ return parent::validate();
+ }
+
+ /**
+ * Transliterates params if necessary by configuration
+ *
+ * @param string[] $formFields formfields to transliterate
+ *
+ * @return string[]
+ */
+ protected function transliterateParams($formFields)
+ {
+ if (strtoupper($this->getEncoding()) != 'UTF-8') {
+ setlocale(LC_CTYPE, Mage::app()->getLocale()->getLocaleCode());
+ array_walk(
+ $formFields,
+ function (&$value) {
+ $value = iconv('UTF-8', 'ASCII//TRANSLIT', $value);
+ }
+ );
+ }
+
+ return $formFields;
+ }
+
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Backend/OpsId.php b/app/code/community/Netresearch/OPS/Model/Payment/Backend/OpsId.php
new file mode 100644
index 0000000..c8781b1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Backend/OpsId.php
@@ -0,0 +1,36 @@
+
+ * @author Thomas Birke
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Backend_OpsId
+ extends Mage_Payment_Model_Method_Abstract
+{
+ /* allow usage in Magento backend */
+ protected $_canUseInternal = true;
+
+ /* deny usage in Magento frontend */
+ protected $_canUseCheckout = false;
+
+ protected $_canBackendDirectCapture = true;
+
+ protected $_isGateway = false;
+ protected $_canAuthorize = false;
+ protected $_canCapture = true;
+ protected $_canCapturePartial = true;
+ protected $_canRefund = true;
+ protected $_canRefundInvoicePartial = true;
+ protected $_canVoid = true;
+
+ /** payment code */
+ protected $_code = 'ops_opsid';
+
+ protected $_formBlockType = 'ops/form_opsId';
+
+ protected $_infoBlockType = 'ops/info_opsId';
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Bancontact.php b/app/code/community/Netresearch/OPS/Model/Payment/Bancontact.php
new file mode 100644
index 0000000..5b4afce
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Bancontact.php
@@ -0,0 +1,102 @@
+
+ */
+class Netresearch_OPS_Model_Payment_Bancontact
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'CreditCard';
+ protected $brand = 'BCMC';
+ const CODE = 'ops_BCMC';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_bancontact';
+
+ /** payment code */
+ protected $_code = self::CODE;
+
+ protected $_mobileDetectHelper = null;
+
+ /**
+ * add needed params to dependend formfields
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param null $requestParams
+ * @return string[]
+ */
+ public function getMethodDependendFormFields($order, $requestParams = null)
+ {
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+ $formFields['DEVICE'] = $this->getInfoInstance()->getAdditionalInformation('DEVICE');
+
+ return $formFields;
+ }
+
+ /**
+ * @param mixed $data
+ * @return $this
+ */
+ public function assignData($data)
+ {
+ parent::assignData($data);
+ $payment = $this->getInfoInstance();
+ $payment->setAdditionalInformation('DEVICE', $this->getMobileDetectHelper()->getDeviceType());
+
+ return $this;
+ }
+
+ /**
+ * Get Mobile Detect Helper
+ *
+ * @return Netresearch_OPS_Helper_MobileDetect
+ */
+ public function getMobileDetectHelper()
+ {
+ if ($this->_mobileDetectHelper === null) {
+ $this->_mobileDetectHelper = Mage::helper('ops/mobileDetect');
+ }
+ return $this->_mobileDetectHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_MobileDetect $mobileHelper
+ *
+ * @returns $this
+ */
+ public function setMobileDetectHelper($mobileHelper)
+ {
+ $this->_mobileDetectHelper = $mobileHelper;
+
+ return $this;
+ }
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/BankTransfer.php b/app/code/community/Netresearch/OPS/Model/Payment/BankTransfer.php
new file mode 100644
index 0000000..45f14f9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/BankTransfer.php
@@ -0,0 +1,49 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_BankTransfer
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** form block type */
+ protected $_formBlockType = 'ops/form_bankTransfer';
+
+ /** payment code */
+ protected $_code = 'ops_bankTransfer';
+
+
+ /**
+ * Assign data to info model instance
+ *
+ * @param mixed $data
+ * @return Mage_Payment_Model_Info
+ */
+ public function assignData($data)
+ {
+ $countryId = '';
+ if (is_object($data) && $data instanceof Varien_Object) {
+ $countryId = $data->getCountryId();
+ } elseif (is_array($data) && isset($data['country_id'])) {
+ $countryId = $data['country_id'];
+ }
+ $pm = $brand = trim('Bank transfer' . (('*' == $countryId) ? '' : ' ' . $countryId));
+
+ $payment = Mage::getSingleton('checkout/session')->getQuote()->getPayment();
+ $payment->setAdditionalInformation('PM', $pm);
+ $payment->setAdditionalInformation('BRAND', $brand);
+
+ parent::assignData($data);
+ return $this;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/BelfiusDirectNet.php b/app/code/community/Netresearch/OPS/Model/Payment/BelfiusDirectNet.php
new file mode 100644
index 0000000..c3f84c7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/BelfiusDirectNet.php
@@ -0,0 +1,25 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_BelfiusDirectNet
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'Belfius Direct Net';
+ protected $brand = 'Belfius Direct Net';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_belfiusDirectNet';
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/CashU.php b/app/code/community/Netresearch/OPS/Model/Payment/CashU.php
new file mode 100644
index 0000000..16c44dd
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/CashU.php
@@ -0,0 +1,25 @@
+
+ * @author Thomas Kappel
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_CashU
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'cashU';
+ protected $brand = 'cashU';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_cashU';
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/CbcOnline.php b/app/code/community/Netresearch/OPS/Model/Payment/CbcOnline.php
new file mode 100644
index 0000000..b7f6d56
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/CbcOnline.php
@@ -0,0 +1,25 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_CbcOnline
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'CBC Online';
+ protected $brand = 'CBC Online';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_cbcOnline';
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Cc.php b/app/code/community/Netresearch/OPS/Model/Payment/Cc.php
new file mode 100644
index 0000000..e107f0d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Cc.php
@@ -0,0 +1,302 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Cc extends Netresearch_OPS_Model_Payment_DirectLink
+{
+ const CODE = 'ops_cc';
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_cc';
+
+ /** @var string $_formBlockType define a specific form block */
+ protected $_formBlockType = 'ops/form_cc';
+
+ /** payment code */
+ protected $_code = self::CODE;
+
+ protected $featureModel = null;
+
+
+ /**
+ * @param null $payment
+ * @return string
+ */
+ public function getOpsCode($payment = null)
+ {
+ $opsBrand = $this->getOpsBrand($payment);
+ if ('PostFinance card' == $opsBrand) {
+ return 'PostFinance Card';
+ }
+ if ('UNEUROCOM' == $this->getOpsBrand($payment)) {
+ return 'UNEUROCOM';
+ }
+
+ return 'CreditCard';
+ }
+
+ /**
+ * @param null $payment
+ *
+ * @return array|mixed|null
+ */
+ public function getOpsBrand($payment = null)
+ {
+ if (null === $payment) {
+ $payment = Mage::getSingleton('checkout/session')->getQuote()->getPayment();
+ }
+
+ return $payment->getAdditionalInformation('CC_BRAND');
+ }
+
+ /**
+ * If payment is inline there should be no orderPlaceRedirectUrl except for 3d secure cards - if order was placed
+ * through admin it is definitely an inline payment.
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ *
+ * @return bool|string
+ */
+ public function getOrderPlaceRedirectUrl($payment = null)
+ {
+ $salesObject = $this->getInfoInstance()->getOrder() ? : $this->getInfoInstance()->getQuote();
+ if ($this->hasBrandAliasInterfaceSupport($payment) || null === $salesObject->getRemoteIp()) {
+ if ('' == $this->getOpsHtmlAnswer($payment)) {
+ return false;
+ } // Prevent redirect on cc payment
+ else {
+ return $this->getConfig()->get3dSecureRedirectUrl();
+ }
+ }
+
+ return parent::getOrderPlaceRedirectUrl();
+ }
+
+ /**
+ * only some brands are supported to be integrated into onepage checkout
+ *
+ * @return array
+ */
+ public function getBrandsForAliasInterface()
+ {
+ $brands = $this->getConfig()->getInlinePaymentCcTypes($this->getCode());
+
+ return $brands;
+ }
+
+ /**
+ * if cc brand supports ops alias interface
+ *
+ * @param Mage_Payment_Model_Info $payment
+ *
+ * @return bool
+ */
+ public function hasBrandAliasInterfaceSupport($payment = null)
+ {
+ return in_array(
+ $this->getOpsBrand($payment),
+ $this->getBrandsForAliasInterface()
+ );
+ }
+
+ /**
+ * Validates alias for in quote provided addresses
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param Varien_Object $payment
+ *
+ * @throws Mage_Core_Exception
+ */
+ protected function validateAlias($quote, $payment)
+ {
+ $alias = $payment->getAdditionalInformation('alias');
+ if (0 < strlen(trim($alias))
+ && is_numeric($payment->getAdditionalInformation('cvc'))
+ && false === Mage::helper('ops/alias')->isAliasValidForAddresses(
+ $quote->getCustomerId(),
+ $alias,
+ $quote->getBillingAddress(),
+ $quote->getShippingAddress(),
+ $quote->getStoreId()
+ )
+ ) {
+ $this->getOnepage()->getCheckout()->setGotoSection('payment');
+ Mage::throwException(
+ $this->getHelper()->__('Invalid payment information provided!')
+ );
+ }
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Creditcard
+ */
+ public function getRequestParamsHelper()
+ {
+ if (null === $this->requestParamsHelper) {
+ $this->requestParamsHelper = Mage::helper('ops/creditcard');
+ }
+
+ return $this->requestParamsHelper;
+ }
+
+
+ protected function performPreDirectLinkCallActions(
+ Mage_Sales_Model_Quote $quote, Varien_Object $payment,
+ $requestParams = array()
+ )
+ {
+ Mage::helper('ops/alias')->cleanUpAdditionalInformation($payment, true);
+ if (true === Mage::getModel('ops/config')->isAliasManagerEnabled($this->getCode())) {
+ $this->validateAlias($quote, $payment);
+ }
+
+ return $this;
+ }
+
+ protected function performPostDirectLinkCallAction(Mage_Sales_Model_Quote $quote, Mage_Sales_Model_Order $order)
+ {
+ Mage::helper('ops/alias')->setAliasActive($quote, $order);
+
+ return $this;
+ }
+
+ protected function handleAdminPayment(Mage_Sales_Model_Quote $quote)
+ {
+ return $this;
+ }
+
+
+ /**
+ * returns allow zero amount authorization
+ * only TRUE if configured payment action for the store is authorize
+ *
+ * @param mixed null|int $storeId
+ *
+ * @return bool
+ */
+ public function isZeroAmountAuthorizationAllowed($storeId = null)
+ {
+ $result = false;
+ if (
+ $this->getConfig()->getPaymentAction($storeId) == Netresearch_OPS_Model_Payment_Abstract::ACTION_AUTHORIZE
+ && true == Mage::getStoreConfig('payment/ops_cc/zero_amount_checkout', $storeId)
+ ) {
+ $result = true;
+ }
+
+ return $result;
+ }
+
+
+ /**
+ * method was implemented in CE 1.8 / EE 1.14
+ * if Version is CE 1.8 / EE 1.14 use parent method otherwise use our implementation
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param $checksBitMask
+ *
+ * @return bool
+ */
+ public function isApplicableToQuote($quote, $checksBitMask)
+ {
+ $result = true;
+ if (Mage::helper('ops/version')->canUseApplicableForQuote(Mage::getEdition())) {
+ $result = parent::isApplicableToQuote($quote, $checksBitMask);
+ }
+
+ if ($quote->getBaseGrandTotal() < 0.01 && $result === false) {
+ $result = $this->getFeatureModel()->isCCAndZeroAmountAuthAllowed($this, $quote);
+ }
+
+ return $result;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Payment_Features_ZeroAmountAuth
+ */
+ public function getFeatureModel()
+ {
+ if (null === $this->featureModel) {
+ $this->featureModel = Mage::getModel('ops/payment_features_zeroAmountAuth');
+ }
+
+ return $this->featureModel;
+ }
+
+ /**
+ * setter for canCapture from outside, needed for zero amount order since we need to disable online capture
+ * but still need to be able to create a invoice
+ *
+ * @param $canCapture
+ */
+ public function setCanCapture($canCapture)
+ {
+ if ($this->_canCapture != $canCapture) {
+ $this->_canCapture = $canCapture;
+ }
+ }
+
+ /**
+ * Check wether payment method is available for quote
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return bool
+ */
+ public function isAvailable($quote = null)
+ {
+ if (null != $quote && !$quote->getItemsCount() > 0 && $this->getDataHelper()->isAdminSession()) {
+ /* Disable payment method in backend as long as there are no items in quote to
+ * avoid problems with alias creation in EE1.12 & EE1.13
+ */
+ return false;
+ }
+
+ return parent::isAvailable($quote);
+ }
+
+ public function isInitializeNeeded()
+ {
+ return !$this->getPaymentHelper()->isInlinePayment($this->getInfoInstance());
+ }
+
+ /**
+ * @inheritdoc
+ */
+ public function getMethodDependendFormFields($order, $requestParams = null)
+ {
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+ if ($this->getConfig()->getCreditDebitSplit($order->getStoreId())) {
+ $formFields['CREDITDEBIT'] = "C";
+ }
+
+ $alias = $order->getPayment()->getAdditionalInformation('alias');
+
+ if ($alias) {
+ $formFields['ALIAS'] = $alias;
+ $formFields['ALIASOPERATION'] = "BYPSP";
+ $formFields['ECI'] = 9;
+ $formFields['ALIASUSAGE'] = $this->getConfig()->getAliasUsageForExistingAlias(
+ $order->getPayment()->getMethodInstance()->getCode(),
+ $order->getStoreId()
+ );
+ } else {
+ $formFields['ALIAS'] = "";
+ $formFields['ALIASOPERATION'] = "BYPSP";
+ $formFields['ALIASUSAGE'] = $this->getConfig()->getAliasUsageForNewAlias(
+ $order->getPayment()->getMethodInstance()->getCode(),
+ $order->getStoreId()
+ );
+
+ }
+
+ return $formFields;
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/ChinaUnionPay.php b/app/code/community/Netresearch/OPS/Model/Payment/ChinaUnionPay.php
new file mode 100644
index 0000000..758cae0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/ChinaUnionPay.php
@@ -0,0 +1,58 @@
+
+ */
+class Netresearch_OPS_Model_Payment_ChinaUnionPay
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'PAYDOL_UPOP';
+ protected $brand = 'UnionPay';
+ const CODE = 'ops_chinaUnionPay';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** disable partial refund */
+ protected $_canRefundInvoicePartial = false;
+
+ /** disable partial capture */
+ protected $_canCapturePartial = false;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = self::CODE;
+
+ public function getPaymentAction()
+ {
+ return Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE;
+ }
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Debitcard.php b/app/code/community/Netresearch/OPS/Model/Payment/Debitcard.php
new file mode 100644
index 0000000..04f89ff
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Debitcard.php
@@ -0,0 +1,54 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Debitcard extends Netresearch_OPS_Model_Payment_Cc
+{
+
+ /** payment code */
+ protected $_code = 'ops_dc';
+
+
+ /**
+ * @param null $payment
+ * @return string
+ */
+ public function getOpsCode($payment = null)
+ {
+ return 'CreditCard';
+ }
+
+ /**
+ * @inheritdoc
+ */
+ public function getMethodDependendFormFields($order, $requestParams = null)
+ {
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+ if ($this->getConfig()->getCreditDebitSplit($order->getStoreId())) {
+ $formFields['CREDITDEBIT'] = "D";
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Debitcard
+ */
+ public function getRequestParamsHelper()
+ {
+ if (null === $this->requestParamsHelper) {
+ $this->requestParamsHelper = Mage::helper('ops/debitcard');
+ }
+
+ return $this->requestParamsHelper;
+ }
+
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/DirectDebit.php b/app/code/community/Netresearch/OPS/Model/Payment/DirectDebit.php
new file mode 100644
index 0000000..e999967
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/DirectDebit.php
@@ -0,0 +1,61 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_DirectDebit
+ extends Netresearch_OPS_Model_Payment_DirectLink
+{
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /* define a specific form block */
+ protected $_formBlockType = 'ops/form_directDebit';
+
+ /** payment code */
+ protected $_code = 'ops_directDebit';
+
+ public function getOrderPlaceRedirectUrl()
+ {
+ // Prevent redirect on direct debit payment
+ return false;
+ }
+
+
+ /**
+ * @return Netresearch_OPS_Helper_DirectDebit
+ */
+ public function getRequestParamsHelper()
+ {
+ if (null === $this->requestParamsHelper) {
+ $this->requestParamsHelper = Mage::helper('ops/directDebit');
+ }
+
+ return $this->requestParamsHelper;
+ }
+
+ protected function performPreDirectLinkCallActions(
+ Mage_Sales_Model_Quote $quote,
+ Varien_Object $payment, $requestParams = array()
+ )
+ {
+ return $this;
+ }
+
+ protected function performPostDirectLinkCallAction(Mage_Sales_Model_Quote $quote, Mage_Sales_Model_Order $order)
+ {
+ Mage::helper('ops/alias')->setAliasActive($quote, $order);
+
+ return $this;
+ }
+
+ protected function handleAdminPayment(Mage_Sales_Model_Quote $quote)
+ {
+ return $this;
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/DirectEbanking.php b/app/code/community/Netresearch/OPS/Model/Payment/DirectEbanking.php
new file mode 100644
index 0000000..9f316f9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/DirectEbanking.php
@@ -0,0 +1,67 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_DirectEbanking
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** form block type */
+ protected $_formBlockType = 'ops/form_directEbanking';
+
+ /** payment code */
+ protected $_code = 'ops_directEbanking';
+
+ /**
+ * Assign data to info model instance
+ *
+ * @param mixed $data
+ * @return Mage_Payment_Model_Info
+ */
+ public function assignData($data)
+ {
+ $brand = '';
+
+ if (is_object($data) && $data instanceof Varien_Object) {
+ $brand = $data['directEbanking_brand'];
+ } elseif (is_array($data) && isset($data['directEbanking_brand'])) {
+
+ $brand = $data['directEbanking_brand'];
+ }
+
+ $brand = $this->fixSofortUberweisungBrand($brand);
+
+ $payment = $this->getInfoInstance();
+ // brand == pm for all DirectEbanking methods
+ $payment->setAdditionalInformation('PM', $brand);
+ $payment->setAdditionalInformation('BRAND', $brand);
+ parent::assignData($data);
+ return $this;
+ }
+
+
+ /**
+ * Fixes legacy brand value of Sofort Uberweisung for DirectEbanking
+ *
+ * @param string $value
+ * @return string
+ */
+ protected function fixSofortUberweisungBrand($value)
+ {
+ if ($value === 'Sofort Uberweisung') {
+ return 'DirectEbanking';
+ }
+ return $value;
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/DirectLink.php b/app/code/community/Netresearch/OPS/Model/Payment/DirectLink.php
new file mode 100644
index 0000000..8c8c9c8
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/DirectLink.php
@@ -0,0 +1,350 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+abstract class Netresearch_OPS_Model_Payment_DirectLink extends Netresearch_OPS_Model_Payment_Abstract
+{
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** Check if we can capture directly from the backend */
+ protected $_canUseInternal = true;
+
+ protected $config = null;
+
+ protected $directLinkHelper = null;
+
+ protected $paymentHelper = null;
+
+ protected $quoteHelper = null;
+
+ protected $requestParamsHelper = null;
+
+ protected $validationFactory = null;
+
+ protected $dataHelper = null;
+
+ protected $_isInitializeNeeded = false;
+
+ /**
+ * @param Netresearch_OPS_Helper_Payment_DirectLink_RequestInterface $requestParamsHelper
+ */
+ public function setRequestParamsHelper($requestParamsHelper)
+ {
+ $this->requestParamsHelper = $requestParamsHelper;
+ }
+
+
+ /**
+ * sets the quote helper
+ *
+ * @param Netresearch_OPS_Helper_Quote $quoteHelper
+ */
+ public function setQuoteHelper(Netresearch_OPS_Helper_Quote $quoteHelper)
+ {
+ $this->quoteHelper = $quoteHelper;
+ }
+
+ /**
+ * gets the quote helper
+ *
+ * @return Netresearch_OPS_Helper_Quote
+ */
+ public function getQuoteHelper()
+ {
+ if (null === $this->quoteHelper) {
+ $this->quoteHelper = Mage::helper('ops/quote');
+ }
+
+ return $this->quoteHelper;
+ }
+
+
+ /**
+ * @param Netresearch_OPS_Helper_Directlink $directLinkHelper
+ */
+ public function setDirectLinkHelper($directLinkHelper)
+ {
+ $this->directLinkHelper = $directLinkHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Directlink
+ */
+ public function getDirectLinkHelper()
+ {
+ if (null === $this->directLinkHelper) {
+ $this->directLinkHelper = MAge::helper('ops/directlink');
+ }
+
+ return $this->directLinkHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Payment $paymentHelper
+ */
+ public function setPaymentHelper($paymentHelper)
+ {
+ $this->paymentHelper = $paymentHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Payment
+ */
+ public function getPaymentHelper()
+ {
+ if (null === $this->paymentHelper) {
+ $this->paymentHelper = Mage::helper('ops/payment');
+ }
+
+ return $this->paymentHelper;
+ }
+
+
+ /**
+ * @param null $config
+ */
+ public function setConfig(Netresearch_OPS_Model_Config $config)
+ {
+ $this->config = $config;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig()
+ {
+ if (null === $this->config) {
+ $this->config = Mage::getModel('ops/config');
+ }
+
+ return $this->config;
+ }
+
+ /**
+ * @param Varien_Object $payment
+ * @param float $amount
+ *
+ * @return Mage_Payment_Model_Abstract|void
+ */
+
+ public function authorize(Varien_Object $payment, $amount)
+ {
+ if ($this->isInlinePayment($payment)
+ && Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE == $this->getConfigPaymentAction()
+ ) {
+ $order = $payment->getOrder();
+ $quote = $this->getQuoteHelper()->getQuote();
+ $this->confirmPayment($order, $quote, $payment);
+ }
+ }
+
+ /**
+ * Saves the payment model and runs the request to Ingenico ePaymentss webservice
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param Mage_Sales_Model_Quote $quote
+ * @param Varien_Object $payment
+ *
+ * @throws Mage_Core_Exception
+ */
+
+ protected function confirmPayment(Mage_Sales_Model_Order $order, Mage_Sales_Model_Quote $quote,
+ Varien_Object $payment
+ )
+ {
+ $this->handleAdminPayment($quote);
+ $requestParams = $this->getRequestParamsHelper()->getDirectLinkRequestParams($quote, $order, $payment);
+ $this->invokeRequestParamValidation($requestParams);
+ $this->performPreDirectLinkCallActions($quote, $order);
+ $response = $this->getDirectLinkHelper()->performDirectLinkRequest(
+ $quote, $requestParams, $quote->getStoreId()
+ );
+ if ($response) {
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $this, false);
+ $this->performPostDirectLinkCallAction($quote, $order);
+
+ } else {
+ $this->getPaymentHelper()->handleUnknownStatus($order);
+ }
+ }
+
+ /**
+ * Handles backend payments on Magento side
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return Netresearch_OPS_Model_Payment_DirectLink
+ */
+ abstract protected function handleAdminPayment(Mage_Sales_Model_Quote $quote);
+
+ /**
+ * @return Netresearch_OPS_Helper_Payment_DirectLink_RequestInterface
+ */
+ abstract protected function getRequestParamsHelper();
+
+
+ /**
+ * Perform necessary preparation before request to Ingenico ePayments is sent
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param Varien_Object $payment
+ * @param array $requestParams
+ *
+ * @return Netresearch_OPS_Model_Payment_DirectLink
+ */
+ abstract protected function performPreDirectLinkCallActions(Mage_Sales_Model_Quote $quote, Varien_Object $payment,
+ $requestParams = array()
+ );
+
+ /**
+ * Perform necessary work after the Directlink Request was sent and an response was received and processed
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return Netresearch_OPS_Model_Payment_DirectLink
+ */
+ abstract protected function performPostDirectLinkCallAction(Mage_Sales_Model_Quote $quote,
+ Mage_Sales_Model_Order $order
+ );
+
+
+ /**
+ * performs direct link request either for inline payments and
+ * direct sale mode or the normal maintenance call (invoice)
+ *
+ * @override
+ *
+ * @param Varien_Object $payment
+ * @param float $amount
+ *
+ * @return Mage_Payment_Model_Abstract|void
+ */
+ public function capture(Varien_Object $payment, $amount)
+ {
+ /**
+ * process direct sale inline payments (initial request)
+ */
+ if (Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE == $this->getConfigPaymentAction()
+ && $this->getPaymentHelper()->isInlinePayment($payment)
+ ) {
+ $order = $payment->getOrder();
+ $quote = $this->getQuoteHelper()->getQuote();
+ $this->confirmPayment($order, $quote, $payment);
+ } /**
+ * invoice request authorize mode if the payment was placed on Ingenico ePayments side
+ */
+ elseif (0 < strlen(trim($payment->getAdditionalInformation('paymentId')))) {
+ parent::capture($payment, $amount);
+ }
+ }
+
+
+ /**
+ * checks if the selected payment supports inline mode
+ *
+ * @param $payment - the payment to check
+ *
+ * @return bool - true if it's support inline mode, false otherwise
+ */
+ protected function isInlinePayment($payment)
+ {
+ $result = false;
+
+ $methodInstance = $payment->getMethodInstance();
+ if ((
+ $methodInstance instanceof Netresearch_OPS_Model_Payment_Cc
+ && $methodInstance->hasBrandAliasInterfaceSupport($payment)
+ || $this->getDataHelper()->isAdminSession()
+ )
+ || $methodInstance instanceof Netresearch_OPS_Model_Payment_DirectDebit
+ ) {
+ $result = true;
+ }
+
+ return $result;
+ }
+
+
+ /**
+ * Get one page checkout model
+ *
+ * @return Mage_Checkout_Model_Type_Onepage
+ */
+ public function getOnepage()
+ {
+ return Mage::getSingleton('checkout/type_onepage');
+ }
+
+ /**
+ * Validate checkout request parameters
+ *
+ * @param $requestParams
+ *
+ * @throws Mage_Core_Exception
+ * @return Netresearch_OPS_Model_Payment_DirectLink
+ */
+ protected function invokeRequestParamValidation($requestParams)
+ {
+ $validator = $this->getValidationFactory()->getValidatorFor(
+ Netresearch_OPS_Model_Validator_Parameter_Factory::TYPE_REQUEST_PARAMS_VALIDATION
+ );
+ if (false == $validator->isValid($requestParams)) {
+ $this->getOnepage()->getCheckout()->setGotoSection('payment');
+ Mage::throwException(
+ $this->getHelper()->__('The data you have provided can not be processed by Ingenico ePayments')
+ );
+ }
+
+ return $this;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Validator_Parameter_Factory
+ */
+ public function getValidationFactory()
+ {
+ if (null === $this->validationFactory) {
+ $this->validationFactory = Mage::getModel('ops/validator_parameter_factory');
+ }
+
+ return $this->validationFactory;
+ }
+
+ /**
+ * sets the used validation factory
+ *
+ * @param Netresearch_OPS_Model_Validator_Parameter_Factory $validationFactory
+ */
+ public function setValidationFactory(Netresearch_OPS_Model_Validator_Parameter_Factory $validationFactory)
+ {
+ $this->validationFactory = $validationFactory;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ */
+ public function setDataHelper(Netresearch_OPS_Helper_Data $dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Data
+ */
+ public function getDataHelper()
+ {
+ if (null === $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/EDankort.php b/app/code/community/Netresearch/OPS/Model/Payment/EDankort.php
new file mode 100644
index 0000000..fc8cfae
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/EDankort.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_EDankort
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'eDankort';
+ protected $brand = 'eDankort';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_eDankort';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Eps.php b/app/code/community/Netresearch/OPS/Model/Payment/Eps.php
new file mode 100644
index 0000000..4567ef2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Eps.php
@@ -0,0 +1,24 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Eps
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'EPS';
+ protected $brand = 'EPS';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_eps';
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Features/PaymentEmail.php b/app/code/community/Netresearch/OPS/Model/Payment/Features/PaymentEmail.php
new file mode 100644
index 0000000..912f795
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Features/PaymentEmail.php
@@ -0,0 +1,198 @@
+
+ */
+class Netresearch_OPS_Model_Payment_Features_PaymentEmail
+{
+
+ protected function getConfig()
+ {
+ return Mage::getModel('ops/config');
+ }
+
+ /**
+ * Check if payment email is available for order
+ *
+ * @param $order
+ *
+ * @return bool
+ */
+ public function isAvailableForOrder($order)
+ {
+ if ($order instanceof Mage_Sales_Model_Order) {
+ $status = $order->getPayment()->getAdditionalInformation('status');
+
+ return Netresearch_OPS_Model_Status::canResendPaymentInfo($status);
+ }
+
+ return false;
+ }
+
+
+ /**
+ * Resends the payment information and returns true/false, depending if succeeded or not
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return boolean success state
+ */
+ public function resendPaymentInfo(Mage_Sales_Model_Order $order)
+ {
+
+ // reset payment method so the customer can choose freely from all available methods
+ $this->setPaymentMethodToGeneric($order);
+
+ $identity = $this->getIdentity($this->getConfig()->getResendPaymentInfoIdentity($order->getStoreId()));
+
+ if ($order->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_PayPerMail) {
+ $template = $this->getConfig()->getPayPerMailTemplate($order->getStoreId());
+ } else {
+ $template = $this->getConfig()->getResendPaymentInfoTemplate($order->getStoreId());
+ }
+
+ $emailTemplate = $this->prepareTemplate(
+ $template,
+ $identity->getEmail(),
+ $identity->getName()
+ );
+
+ $parameters = array(
+ "order" => $order,
+ "paymentLink" => $this->generatePaymentLink($order),
+ "store" => Mage::app()->getStore($order->getStoreId())
+ );
+
+ return $emailTemplate->send($order->getCustomerEmail(), $order->getCustomerName(), $parameters);
+
+ }
+
+ /**
+ * Generates the payment url
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return string
+ */
+ protected function generatePaymentLink(Mage_Sales_Model_Order $order)
+ {
+ $opsOrderId = Mage::helper('ops/order')->getOpsOrderId($order);
+
+ $url = Mage::getModel('ops/config')->getPaymentRetryUrl(
+ Mage::helper('ops/payment')->validateOrderForReuse($opsOrderId, $order->getStoreId()),
+ $order->getStoreId()
+ );
+
+ return $url;
+ }
+
+ /**
+ * Set payment method to Netresearch_OPS_Model_Payment_Flex
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @throws Exception
+ */
+ protected function setPaymentMethodToGeneric(Mage_Sales_Model_Order $order)
+ {
+ if (!$order->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_PayPerMail) {
+ $order->getPayment()->setMethod(Netresearch_OPS_Model_Payment_Flex::CODE)->save();
+ }
+ }
+
+ /**
+ * Sends suspend subscription mail to configured store contact via configured mail template
+ *
+ * @param Mage_Sales_Model_Recurring_Profile $profile
+ * @param Mage_Customer_Model_Customer $customer
+ *
+ * @return bool
+ */
+ public function sendSuspendSubscriptionMail($profile, $customer)
+ {
+ if (null === $profile || null === $customer) {
+ Mage::throwException('Could not send mail due to internal error!');
+ }
+
+ $emailTemplate = $this->prepareTemplate(
+ $this->getConfig()->getSuspendSubscriptionTemplate($profile->getStoreId()),
+ $customer->getEmail(),
+ $customer->getName()
+ );
+
+ $emailTemplate->addBcc($customer->getEmail());
+
+ $parameters = array(
+ "profile" => $profile,
+ "customer" => $customer,
+ "store" => Mage::app()->getStore($profile->getStoreId())
+ );
+
+ $identity = $this->getIdentity($this->getConfig()->getSuspendSubscriptionIdentity($profile->getStoreId()));
+
+ return $emailTemplate->send($identity->getEmail(), $identity->getName(), $parameters);
+
+ }
+
+
+ /**
+ * Loads email and name of the given store identity
+ *
+ * @param string $key - identity to load, defaults to sales
+ *
+ * @return Varien_Object with data name and email
+ */
+ protected function getIdentity($key = 'sales')
+ {
+ $identity = new Varien_Object();
+ $identity->setName(Mage::getStoreConfig('trans_email/ident_' . $key . '/name'))
+ ->setEmail(Mage::getStoreConfig('trans_email/ident_' . $key . '/email'));
+
+ return $identity;
+ }
+
+ /**
+ * Loads the given template by identifier, sets sender mail and name
+ *
+ * @param string $template
+ * @param string $senderMail
+ * @param string $senderName
+ *
+ * @return Mage_Core_Model_Email_Template
+ */
+ protected function prepareTemplate($template, $senderMail, $senderName)
+ {
+ $emailTemplate = Mage::getModel('core/email_template')->load($template);
+ if (null === $emailTemplate->getTemplateSubject()) {
+ $emailTemplate = $emailTemplate->loadDefault($template);
+ }
+ $emailTemplate->setSenderName($senderName)
+ ->setSenderEmail($senderMail);
+
+ return $emailTemplate;
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Features/ZeroAmountAuth.php b/app/code/community/Netresearch/OPS/Model/Payment/Features/ZeroAmountAuth.php
new file mode 100644
index 0000000..c85d8f2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Features/ZeroAmountAuth.php
@@ -0,0 +1,41 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Features_ZeroAmountAuth
+{
+
+ /**
+ * check if payment method is cc and zero amount authorization is enabled
+ *
+ * @param Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod
+ *
+ * @return bool
+ */
+ public function isCCAndZeroAmountAuthAllowed(
+ Netresearch_OPS_Model_Payment_Abstract $opsPaymentMethod,
+ Mage_Sales_Model_Quote $quote
+ )
+ {
+ $result = false;
+ $storeId = $quote->getStoreId();
+ if ($quote->getBaseGrandTotal() < 0.01
+ && $opsPaymentMethod instanceof Netresearch_OPS_Model_Payment_Cc
+ && $opsPaymentMethod->isZeroAmountAuthorizationAllowed($storeId)
+ && 0 < $quote->getItemsCount()
+ && !$quote->isNominal()
+
+ ) {
+ $result = true;
+ }
+
+ return $result;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Flex.php b/app/code/community/Netresearch/OPS/Model/Payment/Flex.php
new file mode 100644
index 0000000..94320da
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Flex.php
@@ -0,0 +1,41 @@
+getInfoInstance()->getAdditionalInformation(self::INFO_KEY_PM);
+ }
+
+ public function getOpsBrand($payment = null)
+ {
+ return $this->getInfoInstance()->getAdditionalInformation(self::INFO_KEY_BRAND);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/FortisPayButton.php b/app/code/community/Netresearch/OPS/Model/Payment/FortisPayButton.php
new file mode 100644
index 0000000..a18f382
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/FortisPayButton.php
@@ -0,0 +1,25 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_FortisPayButton
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'Fortis Pay Button';
+ protected $brand = 'Fortis Pay Button';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_fortisPayButton';
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/GiroPay.php b/app/code/community/Netresearch/OPS/Model/Payment/GiroPay.php
new file mode 100644
index 0000000..eb9e07d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/GiroPay.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_GiroPay
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'giropay';
+ protected $brand = 'giropay';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_giroPay';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/IDeal.php b/app/code/community/Netresearch/OPS/Model/Payment/IDeal.php
new file mode 100644
index 0000000..e677ca6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/IDeal.php
@@ -0,0 +1,78 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_IDeal
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'iDEAL';
+ protected $brand = 'iDEAL';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ protected $_formBlockType = 'ops/form_ideal';
+
+ /** payment code */
+ protected $_code = 'ops_iDeal';
+
+ /**
+ * adds payment specific information to the payment
+ *
+ * @param mixed $data - data containing the issuer id which should be used
+ *
+ * @return Netresearch_OPS_Model_Payment_IDeal
+ */
+ public function assignData($data)
+ {
+ if ($data instanceof Varien_Object) {
+ $data = $data->getData();
+ }
+ if (array_key_exists('iDeal_issuer_id', $data)) {
+ $this->getInfoInstance()->setAdditionalInformation('iDeal_issuer_id', $data['iDeal_issuer_id']);
+ }
+ parent::assignData($data);
+
+ return $this;
+ }
+
+ /**
+ * getter for the iDeal issuers
+ *
+ * @return array
+ */
+ public function getIDealIssuers()
+ {
+ return Mage::getStoreConfig('payment/ops_iDeal/issuer');
+ }
+
+ /**
+ * add iDeal issuer id to form fields
+ *
+ * @override Netresearch_OPS_Model_Payment_Abstract
+ *
+ * @param $order
+ * @param null $requestParams
+ *
+ * @return array
+ */
+ public function getMethodDependendFormFields($order, $requestParams = null)
+ {
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+ if ($order->getPayment()->getAdditionalInformation('iDeal_issuer_id')) {
+ $formFields['ISSUERID'] = $order->getPayment()->getAdditionalInformation('iDeal_issuer_id');
+ }
+
+ return $formFields;
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/IngHomePay.php b/app/code/community/Netresearch/OPS/Model/Payment/IngHomePay.php
new file mode 100644
index 0000000..280d839
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/IngHomePay.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_IngHomePay
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'ING HomePay';
+ protected $brand = 'ING HomePay';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_ingHomePay';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/InterSolve.php b/app/code/community/Netresearch/OPS/Model/Payment/InterSolve.php
new file mode 100644
index 0000000..70a42ef
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/InterSolve.php
@@ -0,0 +1,51 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_InterSolve
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'InterSolve';
+ protected $brand = 'InterSolve';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+ protected $_formBlockType = 'ops/form_interSolve';
+
+ /** payment code */
+ protected $_code = 'ops_interSolve';
+
+ /**
+ * Assign data to info model instance
+ *
+ * @param mixed $data
+ * @return Mage_Payment_Model_Info
+ */
+ public function assignData($data)
+ {
+
+ $brand = '';
+ if (is_object($data) && $data instanceof Varien_Object) {
+ $brand = $data->getIntersolveBrand();
+ } elseif (is_array($data) && isset($data['intersolve_brand'])) {
+ $brand = $data['intersolve_brand'];
+ }
+ if (strlen(trim($brand)) === 0) {
+ $brand = 'InterSolve';
+ }
+ $payment = $this->getInfoInstance();
+ $payment->setAdditionalInformation('BRAND', $brand);
+
+ parent::assignData($data);
+ return $this;
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/KbcOnline.php b/app/code/community/Netresearch/OPS/Model/Payment/KbcOnline.php
new file mode 100644
index 0000000..35a8aa3
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/KbcOnline.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_KbcOnline
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'KBC Online';
+ protected $brand = 'KBC Online';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_kbcOnline';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Kwixo/Abstract.php b/app/code/community/Netresearch/OPS/Model/Payment/Kwixo/Abstract.php
new file mode 100644
index 0000000..c318044
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Kwixo/Abstract.php
@@ -0,0 +1,551 @@
+getShippingAddress()) {
+ $isVirtual = false;
+ $carrierCode = $order->getShippingCarrier()->getCarrierCode();
+ $this->loadShippingSettingForCarrierCode($carrierCode);
+ $shippingMethod = $carrierCode;
+ }
+
+ $formFields['ECOM_ESTIMATEDELIVERYDATE']
+ = $this->getEstimatedDeliveryDate(
+ $this->getCode(), $order->getStoreId()
+ );
+ $formFields['RNPOFFERT'] = $this->getRnpFee(
+ $this->getCode(), $order->getStoreId()
+ );
+ $formFields['ECOM_SHIPMETHODTYPE'] = $this->getShippingMethodType(
+ $this->getCode(), $order->getStoreId(), $isVirtual
+ );
+ $formFields['ECOM_SHIPMETHODSPEED'] = $this->getShippingMethodSpeed(
+ $this->getCode(), $order->getStoreId()
+ );
+ $shipMethodDetails = $this->getShippingMethodDetails(
+ $this->getCode(), $order->getStoreId()
+ );
+ if (0 < strlen(trim($shipMethodDetails))) {
+ $formFields['ECOM_SHIPMETHODDETAILS'] = $shipMethodDetails;
+ }
+ if (4 == $formFields['ECOM_SHIPMETHODTYPE']
+ && !array_key_exists(
+ 'ECOM_SHIPMETHODDETAILS', $formFields
+ )
+ ) {
+ $address = $order->getShippingAddress()
+ ? $order->getShippingAddress()->toString()
+ : $order->getBillingAddress()->toString();
+ $formFields['ECOM_SHIPMETHODDETAILS'] = substr($address, 0, 50);
+ }
+
+ $formFields['ORDERSHIPMETH'] = $shippingMethod;
+
+ $formFields['CIVILITY']
+ = $this->getGender($order) == 'Male' ? 'Mr' : 'Mrs';
+ $formFields = array_merge(
+ $formFields, $this->getKwixoBillToParams($order)
+ );
+ $formFields = array_merge(
+ $formFields, $this->getKwixoShipToParams($order)
+ );
+ $formFields = array_merge(
+ $formFields, $this->getItemParams($order)
+ );
+
+ $formFields['ORDERID'] = Mage::helper('ops/order')->getOpsOrderId(
+ $order, false
+ );
+ $formFields = $this->populateFromArray(
+ $formFields, $requestParams, $order
+ );
+
+ return $formFields;
+ }
+
+
+ protected function getKwixoCategoryFromOrderItem(
+ Mage_Sales_Model_Order_Item $item
+ )
+ {
+ $product = Mage::getModel('catalog/product')->load(
+ $item->getProductId()
+ );
+ $kwixoCategoryId = null;
+ foreach ($product->getCategoryIds() as $categoryId) {
+ $kwixoCategory = Mage::getModel('ops/kwixo_category_mapping')
+ ->loadByCategoryId($categoryId);
+ if (null != $kwixoCategory->getId()) {
+ $kwixoCategoryId = $kwixoCategory->getKwixoCategoryId();
+ break;
+ }
+ }
+
+ return $kwixoCategoryId;
+ }
+
+ /**
+ *
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return array
+ */
+ public function getKwixoBillToParams(Mage_Sales_Model_Order $order)
+ {
+ $formFields = array();
+ $billingAddress = $order->getBillingAddress();
+
+ $billingStreet = str_replace("\n", ' ', $billingAddress->getStreet(-1));
+ $splittedBillingStreet = Mage::Helper('ops/address')->splitStreet($billingStreet);
+
+ $formFields['ECOM_BILLTO_POSTAL_NAME_FIRST'] = $billingAddress->getFirstname();
+ $formFields['ECOM_BILLTO_POSTAL_NAME_LAST'] = $billingAddress->getLastname();
+ $formFields['OWNERADDRESS'] = $splittedBillingStreet['street_name'];
+ $formFields['OWNERADDRESS2'] = $splittedBillingStreet['supplement'];
+ $formFields['ECOM_BILLTO_POSTAL_STREET_NUMBER'] = $splittedBillingStreet['street_number'];
+ $formFields['OWNERTELNO'] = $billingAddress->getTelephone();
+
+ return $formFields;
+ }
+
+ /**
+ * return the shipping parameters as array based on shipping method type
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return array
+ */
+ public function getKwixoShipToParams(Mage_Sales_Model_Order $order)
+ {
+ $formFields = array();
+ $shippingAddress = $order->getShippingAddress();
+
+ if ($shippingAddress === false) {
+ $shippingAddress = $order->getBillingAddress();
+ }
+
+ $shippingStreet = str_replace("\n", ' ', $shippingAddress->getStreet(-1));
+ $splittedShippingStreet = Mage::Helper('ops/address')->splitStreet($shippingStreet);
+ $shippingMethodType = (int)$this->getShippingMethodType($this->getCode(), $order->getStoreId());
+
+ if (in_array($shippingMethodType, $this->getShippingMethodTypeValues())) {
+ if (4 === $shippingMethodType) {
+ $formFields['ECOM_SHIPTO_POSTAL_NAME_PREFIX'] = $shippingAddress->getPrefix();
+ }
+
+ $company = trim($shippingAddress->getCompany());
+ if (0 < strlen($company)) {
+ $formFields['ECOM_SHIPTO_COMPANY'] = $company;
+ }
+
+ $fax = trim($shippingAddress->getFax());
+ if (0 < strlen($fax)) {
+ $formFields['ECOM_SHIPTO_TELECOM_FAX_NUMBER'] = $fax;
+ }
+
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_LINE1'] = $shippingAddress->getStreet1();
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_LINE1'] = $splittedShippingStreet['street_name'];
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_LINE2'] = $splittedShippingStreet['supplement'];
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_NUMBER'] = $splittedShippingStreet['street_number'];
+ $formFields['ECOM_SHIPTO_POSTAL_POSTALCODE'] = $shippingAddress->getPostcode();
+ $formFields['ECOM_SHIPTO_POSTAL_CITY'] = $shippingAddress->getCity();
+ $formFields['ECOM_SHIPTO_POSTAL_COUNTRYCODE'] = $shippingAddress->getCountryId();
+ }
+
+ $formFields['ECOM_SHIPTO_POSTAL_NAME_FIRST'] = $shippingAddress->getFirstname();
+ $formFields['ECOM_SHIPTO_POSTAL_NAME_LAST'] = $shippingAddress->getLastname();
+ $formFields['ECOM_SHIPTO_TELECOM_PHONE_NUMBER'] = $shippingAddress->getTelephone();
+
+ return $formFields;
+ }
+
+ /**
+ * return item params for the order
+ * for each item a ascending number will be added to the parameter name
+ *
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return array
+ */
+ public function getItemParams(Mage_Sales_Model_Order $order)
+ {
+ $formFields = array();
+ $items = $order->getAllItems();
+ $subtotal = 0;
+ if (is_array($items)) {
+ $itemCounter = 1;
+ foreach ($items as $item) {
+ if ($item->getParentItemId()) {
+ continue;
+ }
+
+ $subtotal += $item->getBasePriceInclTax(
+ ) * $item->getQtyOrdered();
+ $formFields['ITEMFDMPRODUCTCATEG' . $itemCounter]
+ = $this->getKwixoCategoryFromOrderItem(
+ $item
+ );
+ $formFields['ITEMID' . $itemCounter] = $item->getItemId();
+ $formFields['ITEMNAME' . $itemCounter] = substr(
+ $item->getName(), 0, 40
+ );
+ $formFields['ITEMPRICE' . $itemCounter] = number_format(
+ $item->getBasePriceInclTax(), 2, '.', ''
+ );
+ $formFields['ITEMQUANT' . $itemCounter]
+ = (int)$item->getQtyOrdered(
+ );
+ $formFields['ITEMVAT' . $itemCounter] = str_replace(
+ ',', '.', (string)(float)$item->getBaseTaxAmount()
+ );
+ $formFields['TAXINCLUDED' . $itemCounter] = 1;
+ $itemCounter++;
+ }
+ $shippingPrice = $order->getBaseShippingAmount();
+ $shippingPriceInclTax = $order->getBaseShippingInclTax();
+ $subtotal += $shippingPriceInclTax;
+ $shippingTaxAmount = $shippingPriceInclTax - $shippingPrice;
+
+ $roundingError = $order->getBaseGrandTotal() - $subtotal;
+ $shippingPrice += $roundingError;
+ /* add shipping item */
+ $formFields['ITEMFDMPRODUCTCATEG' . $itemCounter] = 1;
+ $formFields['ITEMID' . $itemCounter] = 'SHIPPING';
+ $shippingDescription
+ =
+ 0 < strlen(trim($order->getShippingDescription()))
+ ? $order->getShippingDescription() : 'shipping';
+ $formFields['ITEMNAME' . $itemCounter] = substr(
+ $shippingDescription, 0, 30
+ );
+ $formFields['ITEMPRICE' . $itemCounter] = number_format(
+ $shippingPrice, 2, '.', ''
+ );
+ $formFields['ITEMQUANT' . $itemCounter] = 1;
+ $formFields['ITEMVAT' . $itemCounter] = number_format(
+ $shippingTaxAmount, 2, '.', ''
+ );
+ }
+
+ return $formFields;
+ }
+
+
+ /**
+ * returns the delivery date as date based on actual date and adding
+ * the configurated value as days to it
+ *
+ * @param string $code
+ * @param string $storeId
+ *
+ * @return bool|string
+ */
+ public function getEstimatedDeliveryDate($code, $storeId = null)
+ {
+ $dateNow = date("Y-m-d");
+ $dayValue = (string)Mage::getStoreConfig(
+ 'payment/' . $code . "/delivery_date", $storeId
+ );
+ $deliveryDate = strtotime($dateNow . "+" . $dayValue . "days");
+
+ return date("Y-m-d", $deliveryDate);
+ }
+
+ /**
+ * return the RNP Fee value
+ *
+ * @param string $code
+ * @param int $storeId
+ *
+ * @return boolean
+ */
+ public function getRnpFee($code, $storeId = null)
+ {
+ return (int)(bool)Mage::getStoreConfig(
+ "payment/" . $code . "/rnp_fee", $storeId
+ );
+ }
+
+ /**
+ * returns the Shipping Method Type configured in backend
+ *
+ * @param $code
+ * @param null $storeId
+ * @param bool $isVirtual
+ * @return int
+ */
+ public function getShippingMethodType(
+ $code, $storeId = null, $isVirtual = false
+ )
+ {
+ // use download type for orders containing virtual products only
+ if ($isVirtual) {
+ return Netresearch_OPS_Model_Source_Kwixo_ShipMethodType::DOWNLOAD;
+ }
+ $shippingMethodType = $this->getKwixoShippingModel()
+ ->getKwixoShippingType();
+ if (null === $shippingMethodType) {
+ $shippingMethodType = Mage::getStoreConfig(
+ "payment/" . $code . "/ecom_shipMethodType", $storeId
+ );
+ }
+
+ return $shippingMethodType;
+ }
+
+ /**
+ * return the shipping method speed configured in backend
+ *
+ * @param string $code
+ * @param int $storeId
+ *
+ * @return int
+ */
+ public function getShippingMethodSpeed($code, $storeId = null)
+ {
+ $shippingMethodSpeed = $this->getKwixoShippingModel()
+ ->getKwixoShippingMethodSpeed();
+ if (null === $shippingMethodSpeed) {
+ $shippingMethodSpeed = Mage::getStoreConfig(
+ "payment/" . $code . "/ecom_shipMethodSpeed", $storeId
+ );
+ }
+
+ return (int)$shippingMethodSpeed;
+ }
+
+ /**
+ * return the item product categories configured in backend as array
+ *
+ * @param string $code
+ * @param int $storeId
+ *
+ * @return array
+ */
+ public function getItemFmdProductCateg($code, $storeId = null)
+ {
+ return explode(
+ ",", Mage::getStoreConfig(
+ "payment/" . $code . "/product_categories", $storeId
+ )
+ );
+ }
+
+ /**
+ * return the shipping method detail text
+ *
+ * @param string $code
+ * @param int $storeId
+ *
+ * @return string
+ */
+ public function getShippingMethodDetails($code, $storeId = null)
+ {
+ $shippingMethodDetails = $this->getKwixoShippingModel()
+ ->getKwixoShippingDetails();
+ if (null === $shippingMethodDetails) {
+ $shippingMethodDetails = Mage::getStoreConfig(
+ "payment/" . $code . "/shiping_method_details", $storeId
+ );
+ }
+
+ return $shippingMethodDetails;
+ }
+
+ /**
+ * get question for fields with disputable value
+ * users are asked to correct the values before redirect to Ingenico ePayments
+ *
+ *
+ * @return string
+ */
+ public function getQuestion()
+ {
+ return Mage::helper('ops/data')->__(
+ 'Please make sure that the displayed data is correct.'
+ );
+ }
+
+ /**
+ * get an array of fields with disputable value
+ * users are asked to correct the values before redirect to Ingenico ePayments
+ *
+ * @param Mage_Sales_Model_Order $order Current order
+ *
+ * @return array
+ */
+ public function getQuestionedFormFields($order)
+ {
+
+ $questionedFormFields = array(
+ 'CIVILITY',
+ 'OWNERADDRESS',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER',
+
+ );
+ $storeId = null;
+ if ($order instanceof Mage_Sales_Model_Order) {
+ $storeId = $order->getStoreId();
+ }
+ $shippingMethodType = (int)$this->getShippingMethodType(
+ $this->getCode(), $storeId
+ );
+ if (in_array($shippingMethodType, $this->getShippingMethodTypeValues())) {
+ $questionedFormFields [] = 'ECOM_SHIPTO_POSTAL_STREET_NUMBER';
+ $questionedFormFields [] = 'ECOM_SHIPTO_POSTAL_STREET_LINE1';
+ }
+
+ if ($shippingMethodType === 4) {
+ $questionedFormFields [] = 'ECOM_SHIPTO_TELECOM_PHONE_NUMBER';
+ $questionedFormFields [] = 'ECOM_SHIPTO_POSTAL_NAME_PREFIX';
+ }
+
+ return $questionedFormFields;
+ }
+
+ /**
+ * return shipping method values except for the type download
+ *
+ * @return array
+ */
+ public function getShippingMethodTypeValues()
+ {
+ return array(1, 2, 3, 4);
+ }
+
+ /**
+ * populates an array with the values from another if the keys are matching
+ *
+ * @param array $formFields - the array to populate
+ * @param null $dataArray - the array containing the data
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return array - the populated array
+ */
+ protected function populateFromArray(
+ array $formFields, $dataArray = null, $order
+ )
+ {
+ // copy some already known values, but only the ones from the questioned
+ // form fields
+ if (is_array($dataArray)) {
+ foreach ($dataArray as $key => $value) {
+ if (array_key_exists($key, $formFields)
+ && in_array(
+ $key,
+ $this->getQuestionedFormFields($order), true
+ )
+ || $key == 'CIVILITY'
+ ) {
+ $formFields[$key] = $value;
+ }
+ }
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * get gender text for customer
+ *
+ * @param Mage_Sales_Model_Order $order
+ */
+ public function getGender(Mage_Sales_Model_Order $order)
+ {
+ $gender = Mage::getSingleton('eav/config')
+ ->getAttribute('customer', 'gender')
+ ->getSource()
+ ->getOptionText($order->getCustomerGender());
+
+ return $gender;
+ }
+
+ /**
+ * sets the kwixo shipping setting model
+ *
+ * @param Netresearch_OPS_Model_Kwixo_Shipping_Setting $kwixoShippingModel
+ */
+ public function setKwixoShippingModel(
+ Netresearch_OPS_Model_Kwixo_Shipping_Setting $kwixoShippingModel
+ )
+ {
+ $this->kwixoShippingModel = $kwixoShippingModel;
+ }
+
+ /**
+ * returns the kwixo shipping setting model
+ *
+ * @return Netresearch_OPS_Model_Kwixo_Shipping_Setting
+ */
+ public function getKwixoShippingModel()
+ {
+ if (null === $this->kwixoShippingModel) {
+ $this->kwixoShippingModel = Mage::getModel(
+ 'ops/kwixo_shipping_setting'
+ );
+ }
+
+ return $this->kwixoShippingModel;
+ }
+
+ /**
+ * @param $carrierCode
+ * @return null
+ */
+ protected function loadShippingSettingForCarrierCode($carrierCode)
+ {
+ $this->shippingSettings = $this->getKwixoShippingModel()->load(
+ $carrierCode, 'shipping_code'
+ );
+
+ return $this->shippingSettings;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/KwixoApresReception.php b/app/code/community/Netresearch/OPS/Model/Payment/KwixoApresReception.php
new file mode 100644
index 0000000..baf2d12
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/KwixoApresReception.php
@@ -0,0 +1,25 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_KwixoApresReception extends Netresearch_OPS_Model_Payment_Kwixo_Abstract
+{
+ protected $pm = 'KWIXO_RNP';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ protected $_formBlockType = 'ops/form_kwixo_apresReception';
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_kwixoApresReception';
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/KwixoComptant.php b/app/code/community/Netresearch/OPS/Model/Payment/KwixoComptant.php
new file mode 100644
index 0000000..de961f5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/KwixoComptant.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_KwixoComptant extends Netresearch_OPS_Model_Payment_Kwixo_Abstract
+{
+ protected $pm = 'KWIXO_STANDARD';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ protected $_formBlockType = 'ops/form_kwixo_comptant';
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_kwixoComptant';
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/KwixoCredit.php b/app/code/community/Netresearch/OPS/Model/Payment/KwixoCredit.php
new file mode 100644
index 0000000..2492496
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/KwixoCredit.php
@@ -0,0 +1,27 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_KwixoCredit extends Netresearch_OPS_Model_Payment_Kwixo_Abstract
+{
+ protected $pm = 'KWIXO_CREDIT';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+
+ protected $_formBlockType = 'ops/form_kwixo_credit';
+
+ /** payment code */
+ protected $_code = 'ops_kwixoCredit';
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Masterpass.php b/app/code/community/Netresearch/OPS/Model/Payment/Masterpass.php
new file mode 100644
index 0000000..523b20e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Masterpass.php
@@ -0,0 +1,27 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Masterpass
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'MasterPass';
+ protected $brand = 'MasterPass';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_Masterpass';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoice/Abstract.php b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoice/Abstract.php
new file mode 100644
index 0000000..f6f1574
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoice/Abstract.php
@@ -0,0 +1,104 @@
+setEncoding($this->getConfigData('encoding'));
+
+ }
+
+ public function getMethodDependendFormFields($order, $requestParams = null)
+ {
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+ $billingAddress = $order->getBillingAddress();
+ $birthday = new DateTime($order->getCustomerDob());
+ $gender = $order->getCustomerGender() == 1 ? 'M' : 'F';
+ $street = str_replace("\n", ' ', $billingAddress->getStreet(-1));
+ $regexp = '/^([^0-9]*)([0-9].*)$/';
+
+ if (!preg_match($regexp, $street, $splittedStreet)) {
+ $splittedStreet[1] = $street;
+ $splittedStreet[2] = '';
+ }
+
+ $formFields['OWNERADDRESS'] = trim($splittedStreet[1]);
+ $formFields['ECOM_BILLTO_POSTAL_STREET_NUMBER'] = trim($splittedStreet[2]);
+ $formFields['ECOM_BILLTO_POSTAL_NAME_FIRST'] = substr($billingAddress->getFirstname(), 0, 50);
+ $formFields['ECOM_BILLTO_POSTAL_NAME_LAST'] = substr($billingAddress->getLastname(), 0, 50);
+ $formFields['ECOM_SHIPTO_DOB'] = $birthday->format('d/m/Y');
+ $formFields['ECOM_CONSUMER_GENDER'] = $gender;
+
+ return $formFields;
+ }
+
+ /**
+ * @return string title for invoice termes configured in backend
+ */
+ public function getInvoiceTermsTitle()
+ {
+ return $this->getConfigData('invoice_terms_title');
+ }
+
+ /**
+ * @return string url to the invoice terms configured in backend
+ */
+ public function getInvoiceTermsUrl()
+ {
+ return $this->getConfigData('invoice_terms_url');
+ }
+
+ /**
+ * @return bool if invoice terms should be displayed in checkout
+ */
+ public function showInvoiceTermsLink()
+ {
+ return (bool) $this->getConfigData('show_invoice_terms');
+ }
+
+ /**
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return bool
+ */
+ public function isAvailable($quote = null)
+ {
+ if ($quote && !$quote->isVirtual() && !$quote->getShippingAddress()->getSameAsBilling()) {
+ return false;
+ }
+
+ return parent::isAvailable($quote);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceAt.php b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceAt.php
new file mode 100644
index 0000000..88c5e2b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceAt.php
@@ -0,0 +1,107 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_OpenInvoiceAt
+ extends Netresearch_OPS_Model_Payment_OpenInvoice_Abstract
+{
+ protected $pm = 'Open Invoice AT';
+ protected $brand = 'Open Invoice AT';
+
+ /** if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = false;
+ protected $_canCapturePartial = false;
+ protected $_canRefundInvoicePartial = false;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_openInvoiceAt';
+
+ /**
+ * Open Invoice AT is not available if quote has a coupon
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return boolean
+ */
+ public function isAvailable( $quote = null )
+ {
+ /* availability depends on quote */
+ if ( false == $quote instanceof Mage_Sales_Model_Quote ) {
+ return false;
+ }
+
+ /* not available if quote contains a coupon and allow_discounted_carts is disabled */
+ if ( !$this->isAvailableForDiscountedCarts()
+ && $quote->getSubtotal() != $quote->getSubtotalWithDiscount()
+ ) {
+ return false;
+ }
+
+ /* not available if there is no gender or no birthday */
+ if ($quote->getCustomerGender() == null || $quote->getCustomerDob() == null) {
+ return false;
+ }
+
+ return parent::isAvailable($quote);
+ }
+
+ public function getPaymentAction()
+ {
+ return Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE;
+ }
+
+ /**
+ * @param Mage_Sales_Model_Order $order
+ * @param array|null $requestParams
+ *
+ * @return array
+ */
+ public function getMethodDependendFormFields( $order, $requestParams = null )
+ {
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+
+ $shippingAddress = $order->getShippingAddress();
+
+ $gender = Mage::getSingleton('eav/config')
+ ->getAttribute('customer', 'gender')
+ ->getSource()
+ ->getOptionText($order->getCustomerGender());
+
+ $formFields[ 'CIVILITY' ] = $gender == 'Male' ? 'Herr' : 'Frau';
+ $formFields[ 'ECOM_CONSUMER_GENDER' ] = $gender == 'Male' ? 'M' : 'F';
+
+ // Change address format to make austrian addresses compatible with platform data transfer to Klarna
+ $billToParams = $this->getRequestHelper()->extractBillToParameters($order->getBillingAddress(), $order);
+ $formFields['OWNERADDRESS'] = $billToParams['ECOM_BILLTO_POSTAL_STREET_LINE1'] . ' '
+ . $billToParams['ECOM_BILLTO_POSTAL_STREET_NUMBER'];
+ $formFields['ECOM_BILLTO_POSTAL_STREET_NUMBER'] = ' ';
+
+ if (!$this->getConfig()->canSubmitExtraParameter($order->getStoreId()) ) {
+ // add the shipto parameters even if the submitOption is false, because they are required for OpenInvoice
+ $shipToParams = $this->getRequestHelper()->extractShipToParameters($shippingAddress, $order);
+ $formFields = array_merge($formFields, $shipToParams);
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * getter for the allow_discounted_carts
+ *
+ * @return bool
+ */
+ protected function isAvailableForDiscountedCarts()
+ {
+ return (bool) $this->getConfigData('allow_discounted_carts');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceDe.php b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceDe.php
new file mode 100644
index 0000000..62c1038
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceDe.php
@@ -0,0 +1,95 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_OpenInvoiceDe
+ extends Netresearch_OPS_Model_Payment_OpenInvoice_Abstract
+{
+ protected $pm = 'Open Invoice DE';
+ protected $brand = 'Open Invoice DE';
+
+ /** if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = false;
+
+ protected $_canCapturePartial = false;
+ protected $_canRefundInvoicePartial = false;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_openInvoiceDe';
+
+ /**
+ * Open Invoice DE is not available if quote has a coupon
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @return boolean
+ */
+ public function isAvailable($quote=null)
+ {
+ /* availability depends on quote */
+ if (false == $quote instanceof Mage_Sales_Model_Quote) {
+ return false;
+ }
+
+ /* not available if quote contains a coupon and allow_discounted_carts is disabled */
+ if (!$this->isAvailableForDiscountedCarts()
+ && $quote->getSubtotal() != $quote->getSubtotalWithDiscount()
+ ) {
+ return false;
+ }
+
+ /* not available if there is no gender or no birthday */
+ if (null === $quote->getCustomerGender() || is_null($quote->getCustomerDob())) {
+ return false;
+ }
+
+ return parent::isAvailable($quote);
+ }
+
+ public function getPaymentAction()
+ {
+ return Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE;
+ }
+
+ public function getMethodDependendFormFields($order, $requestParams=null)
+ {
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+
+ $shippingAddress = $order->getShippingAddress();
+
+ $gender = Mage::getSingleton('eav/config')
+ ->getAttribute('customer', 'gender')
+ ->getSource()
+ ->getOptionText($order->getCustomerGender());
+
+ $formFields[ 'CIVILITY' ] = $gender == 'Male' ? 'Herr' : 'Frau';
+ $formFields[ 'ECOM_CONSUMER_GENDER' ] = $gender == 'Male' ? 'M' : 'F';
+
+ if (!$this->getConfig()->canSubmitExtraParameter($order->getStoreId())) {
+ // add the shipto parameters even if the submitOption is false, because they are required for OpenInvoice
+ $shipToParams = $this->getRequestHelper()->extractShipToParameters($shippingAddress, $order);
+ $formFields = array_merge($formFields, $shipToParams);
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * getter for the allow_discounted_carts
+ *
+ * @return array
+ */
+ protected function isAvailableForDiscountedCarts()
+ {
+ return (bool) $this->getConfigData('allow_discounted_carts');
+ }
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceNl.php b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceNl.php
new file mode 100644
index 0000000..ebfc182
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/OpenInvoiceNl.php
@@ -0,0 +1,140 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_OpenInvoiceNl
+ extends Netresearch_OPS_Model_Payment_OpenInvoice_Abstract
+{
+ protected $pm = 'Open Invoice NL';
+ protected $brand = 'Open Invoice NL';
+
+ /** if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = false;
+
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_openInvoiceNl';
+
+
+ /**
+ * Open Invoice NL is not available if quote has a coupon
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @return boolean
+ */
+ public function isAvailable($quote=null)
+ {
+ /* availability depends on quote */
+ if (false == $quote instanceof Mage_Sales_Model_Quote) {
+ return false;
+ }
+
+ /* not available if there is no gender or no birthday */
+ if (null === $quote->getCustomerGender() || is_null($quote->getCustomerDob())) {
+ return false;
+ }
+
+ return parent::isAvailable($quote);
+ }
+
+ /**
+ * get some method dependend form fields
+ *
+ * @param Mage_Sales_Model_Quote $order
+ * @param array $requestParams
+ * @return array
+ */
+ public function getMethodDependendFormFields($order, $requestParams=null)
+ {
+ $billingAddress = $order->getBillingAddress();
+ $shippingAddress = $order->getShippingAddress();
+ $billingStreet = str_replace("\n", ' ', $billingAddress->getStreet(-1));
+
+ $splittedBillingStreet = Mage::helper('ops/address')->splitStreet($billingStreet);
+ $formFields = parent::getMethodDependendFormFields($order, $requestParams);
+
+ $gender = Mage::getSingleton('eav/config')
+ ->getAttribute('customer', 'gender')
+ ->getSource()
+ ->getOptionText($order->getCustomerGender());
+
+ $formFields['CIVILITY'] = $gender == 'Male' ? 'M' : 'V';
+ $formFields['ECOM_CONSUMER_GENDER'] = $gender == 'Male' ? 'M' : 'V';
+ $formFields['OWNERADDRESS'] = $splittedBillingStreet['street_name'];
+ $formFields['ECOM_BILLTO_POSTAL_STREET_NUMBER'] = $splittedBillingStreet['street_number'];
+ $formFields['OWNERZIP'] = $billingAddress->getPostcode();
+ $formFields['OWNERTOWN'] = $billingAddress->getCity();
+ $formFields['OWNERCTY'] = $billingAddress->getCountry();
+ $formFields['OWNERTELNO'] = $billingAddress->getTelephone();
+
+ $shippingStreet = str_replace("\n", ' ', $shippingAddress->getStreet(-1));
+
+ $splittedShippingStreet = Mage::Helper('ops/address')->splitStreet($shippingStreet);
+
+ $formFields['ECOM_SHIPTO_POSTAL_NAME_PREFIX'] = $shippingAddress->getPrefix();
+ $formFields['ECOM_SHIPTO_POSTAL_NAME_FIRST'] = $shippingAddress->getFirstname();
+ $formFields['ECOM_SHIPTO_POSTAL_NAME_LAST'] = $shippingAddress->getLastname();
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_LINE1'] = $splittedShippingStreet['street_name'];
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_NUMBER'] = $splittedShippingStreet['street_number'];
+ $formFields['ECOM_SHIPTO_POSTAL_POSTALCODE'] = $shippingAddress->getPostcode();
+ $formFields['ECOM_SHIPTO_POSTAL_CITY'] = $shippingAddress->getCity();
+ $formFields['ECOM_SHIPTO_POSTAL_COUNTRYCODE'] = $shippingAddress->getCountry();
+
+ // copy some already known values
+ $formFields['ECOM_SHIPTO_ONLINE_EMAIL'] = $order->getCustomerEmail();
+
+ if (is_array($requestParams)) {
+ if (array_key_exists('OWNERADDRESS', $requestParams)) {
+ $formFields['OWNERADDRESS'] = $requestParams['OWNERADDRESS'];
+ }
+ if (array_key_exists('ECOM_BILLTO_POSTAL_STREET_NUMBER', $requestParams)) {
+ $formFields['ECOM_BILLTO_POSTAL_STREET_NUMBER'] = $requestParams['ECOM_BILLTO_POSTAL_STREET_NUMBER'];
+ }
+ if (array_key_exists('ECOM_SHIPTO_POSTAL_STREET_LINE1', $requestParams)) {
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_LINE1'] = $requestParams['ECOM_SHIPTO_POSTAL_STREET_LINE1'];
+ }
+ if (array_key_exists('ECOM_SHIPTO_POSTAL_STREET_NUMBER', $requestParams)) {
+ $formFields['ECOM_SHIPTO_POSTAL_STREET_NUMBER'] = $requestParams['ECOM_SHIPTO_POSTAL_STREET_NUMBER'];
+ }
+ }
+
+ return $formFields;
+ }
+
+ /**
+ * get question for fields with disputable value
+ * users are asked to correct the values before redirect to Ingenico ePayments
+ *
+ * @return string
+ */
+ public function getQuestion()
+ {
+ return Mage::helper('ops')->__('Please make sure that your street and house number are correct.');
+ }
+
+ /**
+ * get an array of fields with disputable value
+ * users are asked to correct the values before redirect to Ingenico ePayments
+ *
+ *
+ * @return array
+ */
+ public function getQuestionedFormFields($order)
+ {
+ return array(
+ 'OWNERADDRESS',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1',
+ 'ECOM_SHIPTO_POSTAL_STREET_NUMBER',
+ );
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/PayPerMail.php b/app/code/community/Netresearch/OPS/Model/Payment/PayPerMail.php
new file mode 100644
index 0000000..bec2d49
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/PayPerMail.php
@@ -0,0 +1,41 @@
+getInfoInstance()->getAdditionalInformation(self::INFO_KEY_PM);
+ }
+
+ public function getOpsBrand($payment = null)
+ {
+ return $this->getInfoInstance()->getAdditionalInformation(self::INFO_KEY_BRAND);
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Paypal.php b/app/code/community/Netresearch/OPS/Model/Payment/Paypal.php
new file mode 100644
index 0000000..55caa8d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Paypal.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Paypal
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'PAYPAL';
+ protected $brand = 'PAYPAL';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_paypal';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Paysafecard.php b/app/code/community/Netresearch/OPS/Model/Payment/Paysafecard.php
new file mode 100644
index 0000000..bf8ae66
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Paysafecard.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_Paysafecard
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'paysafecard';
+ protected $brand = 'paysafecard';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_paysafecard';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/PingPing.php b/app/code/community/Netresearch/OPS/Model/Payment/PingPing.php
new file mode 100644
index 0000000..4a5e75f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/PingPing.php
@@ -0,0 +1,26 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_PingPing
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'PingPing';
+ protected $brand = 'PingPing';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_pingPing';
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/PostFinanceEFinance.php b/app/code/community/Netresearch/OPS/Model/Payment/PostFinanceEFinance.php
new file mode 100644
index 0000000..c749e71
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/PostFinanceEFinance.php
@@ -0,0 +1,25 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Model_Payment_PostFinanceEFinance
+ extends Netresearch_OPS_Model_Payment_Abstract
+{
+ protected $pm = 'PostFinance e-finance';
+ protected $brand = 'PostFinance e-finance';
+
+ /** Check if we can capture directly from the backend */
+ protected $_canBackendDirectCapture = true;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_redirect';
+
+ /** payment code */
+ protected $_code = 'ops_postFinanceEFinance';
+}
+
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc.php b/app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc.php
new file mode 100644
index 0000000..6372646
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc.php
@@ -0,0 +1,391 @@
+
+ */
+class Netresearch_OPS_Model_Payment_Recurring_Cc
+ extends Netresearch_OPS_Model_Payment_Cc
+ implements Mage_Payment_Model_Recurring_Profile_MethodInterface
+{
+ const CODE = 'ops_recurring_cc';
+ protected $_code = self::CODE;
+
+ protected $_canFetchTransactionInfo = false;
+ protected $_canManageRecurringProfiles = true;
+ protected $_canUseInternal = false;
+
+ /** info source path */
+ protected $_infoBlockType = 'ops/info_recurringCc';
+
+ /** @var string $_formBlockType define a specific form block */
+ protected $_formBlockType = 'ops/form_recurringCc';
+
+ protected $parameterModel = null;
+ protected $subscriptionManager = null;
+
+ /**
+ * @return Netresearch_OPS_Model_Subscription_Manager
+ */
+ public function getSubscriptionManager()
+ {
+ if (null === $this->subscriptionManager) {
+ $this->subscriptionManager = Mage::getModel('ops/subscription_manager');
+ }
+
+ return $this->subscriptionManager;
+ }
+
+ /**
+ * @param Netresearch_OPS_Model_Subscription_Manager $subscriptionManager
+ *
+ * @returns $this
+ */
+ public function setSubscriptionManager($subscriptionManager)
+ {
+ $this->subscriptionManager = $subscriptionManager;
+
+ return $this;
+ }
+
+
+ /**
+ * @return Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag
+ */
+ public function getParameterModel()
+ {
+ if (null === $this->parameterModel) {
+ $this->parameterModel = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ }
+
+ return $this->parameterModel;
+ }
+
+ /**
+ * @param Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag $parameterModel
+ *
+ * @returns $this
+ */
+ public function setParameterModel($parameterModel)
+ {
+ $this->parameterModel = $parameterModel;
+
+ return $this;
+ }
+
+
+ /**
+ * Validate data
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ *
+ * @throws Mage_Core_Exception
+ */
+ public function validateRecurringProfile(Mage_Payment_Model_Recurring_Profile $profile)
+ {
+ if ($profile->getState() === Mage_Sales_Model_Recurring_Profile::STATE_UNKNOWN) {
+ $this->invokeRequestParamValidation(
+ $this->getParameterModel()->collectProfileParameters($profile)->toArray()
+ );
+ }
+ }
+
+ /**
+ * Submits the trial subscription to the Ingenico ePayments webservice
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ * @param Mage_Payment_Model_Info $paymentInfo
+ *
+ */
+ protected function submitTrialSubscription(
+ Mage_Payment_Model_Recurring_Profile $profile,
+ Mage_Payment_Model_Info $paymentInfo
+ )
+ {
+ if ($profile->getTrialPeriodUnit()) {
+ $requestParams = $this->getParameterModel()->collectAllParametersForTrial($paymentInfo, $profile);
+ $this->getParameterModel()->unsetData();
+ $response = $this->getDirectLinkHelper()->performDirectLinkRequest(
+ $profile->getQuote(), $requestParams, $profile->getQuote()->getStoreId()
+ );
+
+ if ($this->getPaymentHelper()->isPaymentFailed($response['STATUS'])
+ || $response['creation_status'] == Netresearch_OPS_Model_Subscription_Manager::CREATION_FAILED
+ ) {
+ Mage::throwException($this->getDataHelper()->__('Placing of trial subscription transaction failed'));
+ }
+ }
+ }
+
+ /**
+ * Submit to the gateway
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ * @param Mage_Payment_Model_Info $paymentInfo
+ */
+ public function submitRecurringProfile(
+ Mage_Payment_Model_Recurring_Profile $profile,
+ Mage_Payment_Model_Info $paymentInfo
+ )
+ {
+ $this->performPreDirectLinkCallActions($profile->getQuote(), $paymentInfo);
+
+ $this->submitTrialSubscription($profile, $paymentInfo);
+
+ $this->submitRegularSubscription($profile, $paymentInfo);
+
+ $this->submitInitialFee($profile, $paymentInfo);
+ }
+
+ /**
+ * Fetch details
+ *
+ * @param string $referenceId
+ * @param Varien_Object $result
+ */
+ public function getRecurringProfileDetails($referenceId, Varien_Object $result)
+ {
+ Mage::throwException('Fetching profile details from Ingenico ePayments not supported');
+ }
+
+ /**
+ * Check whether can get recurring profile details
+ *
+ * @return bool
+ */
+ public function canGetRecurringProfileDetails()
+ {
+ // querying the subscription status via API is not possible
+ return false;
+ }
+
+ /**
+ * Update data
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ */
+ public function updateRecurringProfile(Mage_Payment_Model_Recurring_Profile $profile)
+ {
+ Mage::throwException('Function not supported');
+ }
+
+ /**
+ * Manage status update according to given new state on the profile
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ */
+ public function updateRecurringProfileStatus(Mage_Payment_Model_Recurring_Profile $profile)
+ {
+ /** @var Mage_Sales_Model_Recurring_Profile $profile */
+ switch ($profile->getNewState()) {
+ case Mage_Sales_Model_Recurring_Profile::STATE_ACTIVE:
+ if (Mage::getSingleton('admin/session')->isLoggedIn()) {
+ $this->addAdminNotice(
+ 'To actually activate the subscription an update in the Ingenico ePayments backend is needed.'
+ );
+ } else {
+ Mage::throwException(
+ $this->getDataHelper()->__(
+ 'Automatic activation not possible. Please contact our support team.'
+ )
+ );
+ }
+ break;
+ case Mage_Sales_Model_Recurring_Profile::STATE_CANCELED:
+ if (Mage::getSingleton('admin/session')->isLoggedIn()) {
+ $this->addAdminNotice(
+ 'To actually cancel the subscription an update in the Ingenico ePayments backend is needed.'
+ );
+ } else {
+ $this->sendSuspendMail($profile);
+ }
+ break;
+ case Mage_Sales_Model_Recurring_Profile::STATE_SUSPENDED:
+ if (Mage::getSingleton('admin/session')->isLoggedIn()) {
+ $this->addAdminNotice(
+ 'To actually suspend the subscription an update in the Ingenico ePayments backend is needed.'
+ );
+ } else {
+ $this->sendSuspendMail($profile);
+ }
+ break;
+ case Mage_Sales_Model_Recurring_Profile::STATE_EXPIRED:
+ Mage::throwException('Expire function not implemented!');
+ break;
+ default:
+ $message = $this->getDataHelper()->__('Action for state %s not supported', $profile->getNewState());
+ Mage::throwException($message);
+ break;
+ }
+ }
+
+ /**
+ * Adds translated message to admin session as notice
+ *
+ * @param string $message
+ */
+ protected function addAdminNotice($message)
+ {
+ Mage::getSingleton('adminhtml/session')->addNotice($this->getDataHelper()->__($message));
+ }
+
+ /**
+ *
+ * @param Mage_Sales_Model_Recurring_Profile $profile
+ *
+ * @throws Mage_Core_Exception
+ */
+ protected function sendSuspendMail($profile)
+ {
+ $session = Mage::getSingleton('customer/session');
+ $mailModel = Mage::getModel('ops/payment_features_paymentEmail');
+ if ($session->getCustomer()->getId() != $profile->getCustomerId()) {
+ // prevent access to subscriptions not of the customers account
+ Mage::throwException(
+ $this->getDataHelper()->__('You are not allowed to suspend this subscription!')
+ );
+ }
+ $customer = Mage::getModel('customer/customer')->load($profile->getCustomerId());
+ $result = $mailModel->sendSuspendSubscriptionMail($profile, $customer);
+ if ($result) {
+ // mail successfully sent
+ $profile->setNewState($profile::STATE_PENDING);
+ $profile->setOverrideState(true);
+ $session->addSuccess(
+ $this->getDataHelper()
+ ->__(
+ 'Your suspend request was successfully sent. A copy of the email will be sent to your address.'
+ )
+ );
+ } else {
+ // sending the mail failed
+ Mage::throwException(
+ $this->getDataHelper()
+ ->__('Could not send suspend mail, please try again or contact our support directly.')
+ );
+ }
+ }
+
+ /**
+ * Check wether payment method is available for quote
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ *
+ * @return bool
+ */
+ public function isAvailable($quote = null)
+ {
+ if ($quote && !$quote->isNominal()) {
+ // allow only nominal quotes
+ return false;
+ }
+
+ return parent::isAvailable($quote);
+
+ }
+
+ public function hasBrandAliasInterfaceSupport($payment = null)
+ {
+ // only support inline, since we need the alias
+ return true;
+ }
+
+ public function getOrderPlaceRedirectUrl($payment = null)
+ {
+ if ('' == $this->getOpsHtmlAnswer($payment)) {
+ // Prevent redirect on cc payment
+ return false;
+ } else {
+ // 3ds redirect
+ return Mage::getModel('ops/config')->get3dSecureRedirectUrl();
+
+ }
+ }
+
+ public function isZeroAmountAuthorizationAllowed($storeId = null)
+ {
+ return false;
+ }
+
+ public function getBrandsForAliasInterface()
+ {
+ return $this->getConfigData('availableTypes');
+ }
+
+ /**
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ * @param Mage_Payment_Model_Info $paymentInfo
+ *
+ * @throws Mage_Core_Exception
+ */
+ protected function submitRegularSubscription(Mage_Payment_Model_Recurring_Profile $profile,
+ Mage_Payment_Model_Info $paymentInfo
+ )
+ {
+ $requestParams = $this->getParameterModel()->collectAllParameters($paymentInfo, $profile);
+ $this->getParameterModel()->unsetData();
+ $response = $this->getDirectLinkHelper()->performDirectLinkRequest(
+ $profile->getQuote(), $requestParams, $profile->getQuote()->getStoreId()
+ );
+
+ if ($this->getPaymentHelper()->isPaymentFailed($response['STATUS'])
+ || $response['creation_status'] == Netresearch_OPS_Model_Subscription_Manager::CREATION_FAILED
+ ) {
+ Mage::throwException($this->getDataHelper()->__('Placing of subscription transaction failed'));
+ }
+
+ $this->getSubscriptionManager()->processSubscriptionFeedback($response, $profile);
+ }
+
+ protected function submitInitialFee(
+ Mage_Payment_Model_Recurring_Profile $profile,
+ Mage_Payment_Model_Info $paymentInfo
+ )
+ {
+ /** @var $profile Mage_Sales_Model_Recurring_Profile */
+ if ($profile->getInitAmount() > 0) {
+ $order = $this->getSubscriptionManager()->createInitialOrder($profile);
+
+ $requestParams = $this->getParameterModel()
+ ->collectAllParametersForInitialFee($paymentInfo, $profile, $order);
+ $this->getParameterModel()->unsetData();
+ try{
+
+ $response = $this->getDirectLinkHelper()->performDirectLinkRequest(
+ $profile->getQuote(), $requestParams, $profile->getQuote()->getStoreId()
+ );
+ } catch (Exception $e){
+ Mage::logException($e);
+ }
+
+ $this->getSubscriptionManager()->processSubscriptionFeedback($response, $profile, $order);
+
+ }
+
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc/ParameterBag.php b/app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc/ParameterBag.php
new file mode 100644
index 0000000..535fbb1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Payment/Recurring/Cc/ParameterBag.php
@@ -0,0 +1,533 @@
+
+ */
+?>
+subscriptionHelper) {
+ $this->subscriptionHelper = Mage::helper('ops/subscription');
+ }
+
+ return $this->subscriptionHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Subscription $subscriptionHelper
+ *
+ * @returns $this
+ */
+ public function setSubscriptionHelper($subscriptionHelper)
+ {
+ $this->subscriptionHelper = $subscriptionHelper;
+
+ return $this;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Data
+ */
+ public function getDataHelper()
+ {
+ if (null === $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops');
+ }
+
+ return $this->dataHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ *
+ * @returns $this
+ */
+ public function setDataHelper($dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+
+ return $this;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Quote
+ */
+ public function getQuoteHelper()
+ {
+ if (null === $this->quoteHelper) {
+ $this->quoteHelper = Mage::helper('ops/quote');
+ }
+
+ return $this->quoteHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Quote $quoteHelper
+ *
+ * @returns $this
+ */
+ public function setQuoteHelper($quoteHelper)
+ {
+ $this->quoteHelper = $quoteHelper;
+
+ return $this;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getConfig()
+ {
+ if (null === $this->config) {
+ $this->config = Mage::getModel('ops/config');
+ }
+
+ return $this->config;
+ }
+
+ /**
+ * @param Netresearch_OPS_Model_Config $config
+ *
+ * @returns $this
+ */
+ public function setConfig($config)
+ {
+ $this->config = $config;
+
+ return $this;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Payment_Request
+ */
+ public function getRequestHelper()
+ {
+ if (null === $this->requestHelper) {
+ $this->requestHelper = Mage::helper('ops/payment_request');
+ }
+
+ return $this->requestHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Payment_Request $requestHelper
+ *
+ * @returns $this
+ */
+ public function setRequestHelper($requestHelper)
+ {
+ $this->requestHelper = $requestHelper;
+
+ return $this;
+ }
+
+ /**
+ * Maps the Magento recurring profile units to the Ingenico ePayments ones
+ *
+ * @param string $unit
+ *
+ * @return string
+ */
+ protected function mapUnit($unit)
+ {
+ switch ($unit) {
+ case Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_DAY:
+ return self::PERIOD_UNIT_DAY;
+ case Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_MONTH:
+ return self::PERIOD_UNIT_MONTH;
+ case Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_WEEK:
+ case Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_SEMI_MONTH:
+ return self::PERIOD_UNIT_WEEK;
+ case Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_YEAR:
+ return self::PERIOD_UNIT_MONTH;
+ default:
+ return '';
+ }
+ }
+
+ /**
+ * Some period units are not supported by default by Ingenico, therefore we must adjust the frequency for
+ * the following period units to match the MONTH unit:
+ *
+ * Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_SEMI_MONTH
+ * Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_YEAR
+ *
+ * @param string $unit
+ * @param int $frequency
+ *
+ * @return int adjusted frequency
+ */
+ protected function adjustFrequencyToUnitSpecialCases($unit, $frequency)
+ {
+ switch ($unit) {
+ case Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_SEMI_MONTH:
+ $frequency *= 2;
+ break;
+ case Mage_Payment_Model_Recurring_Profile::PERIOD_UNIT_YEAR:
+ $frequency *= 12;
+ break;
+ default:
+ break;
+ }
+
+ return $frequency;
+ }
+
+ /**
+ * Collects parameters specific to customer (addresses) and quote
+ *
+ * @param Mage_Payment_Model_Info $paymentInfo
+ *
+ * @return Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag
+ */
+ public function collectPaymentParameters(Mage_Payment_Model_Info $paymentInfo)
+ {
+ $this->setData('CN', $paymentInfo->getAdditionalInformation('CC_CN'))
+ ->setData('ALIAS', $paymentInfo->getAdditionalInformation('alias'))
+ ->setData('BRAND', $paymentInfo->getAdditionalInformation('CC_BRAND'))
+ ->setData('CURRENCY', $this->getQuoteHelper()->getQuoteCurrency($paymentInfo->getQuote()))
+ ->setData('OPERATION', Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION)
+ ->setData('ORIG', $this->getDataHelper()->getModuleVersionString())
+ ->setData('REMOTE_ADDR', $paymentInfo->getQuote()->getRemoteIp());
+
+
+ if ($paymentInfo->getMethodInstance()->getConfigData('enabled_3dsecure')) {
+ $this->addData(
+ array(
+ 'FLAG3D' => 'Y',
+ 'WIN3DS' => Netresearch_OPS_Model_Payment_Abstract::OPS_DIRECTLINK_WIN3DS,
+ 'LANGUAGE' => Mage::app()->getLocale()->getLocaleCode(),
+ 'HTTP_ACCEPT' => '*/*',
+ 'HTTP_USER_AGENT' => 'Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0)',
+ 'ACCEPTURL' => $this->getConfig()->getAcceptUrl(),
+ 'DECLINEURL' => $this->getConfig()->getDeclineUrl(),
+ 'EXCEPTIONURL' => $this->getConfig()->getExceptionUrl(),
+ )
+ );
+ }
+
+ return $this;
+ }
+
+ /**
+ * Collects profile specific request parameters
+ *
+ * @see http://payment-services.ingenico.com/int/en/ogone/support/guides/integration%20guides/subscription-manager/via-e-commerce-and-directlink
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ * @param boolean $trial - if the array should contain the parameters necessary for the trial period
+ *
+ * @return $this
+ */
+ public function collectProfileParameters(Mage_Payment_Model_Recurring_Profile $profile, $trial = false)
+ {
+ /** @var Mage_Sales_Model_Recurring_Profile $profile */
+
+ // get subscription amount from profile values
+ list($subscriptionAmount) = $this->getProfileValues($profile, $trial);
+
+ // determine dates and adjust period values depending on trial parameter
+ list($startDate, $endDate, $periodUnit, $periodFrequency) = $this->generateDates($profile, $trial);
+
+ $subOrderId = $this->getSubscriptionHelper()->generateSubscriptionId($profile, $trial);
+
+ $this->setData('SUB_COM', $profile->getScheduleDescription())
+ ->setData('SUB_ORDERID', $subOrderId)
+ ->setData('SUB_PERIOD_NUMBER', $periodFrequency)
+ ->setData('SUB_PERIOD_UNIT', $periodUnit)
+ ->setData('SUB_STARTDATE', $startDate->format('d/m/Y'))
+ ->setData('SUB_ENDDATE', $endDate ? $endDate->format('d/m/Y') : '')
+ ->setData('SUB_STATUS', 1)
+ ->setData('SUBSCRIPTION_ID', $subOrderId)
+ ->setData('ORDERID', $subOrderId)
+ ->setData('SUB_AMOUNT', $this->getDataHelper()->getAmount($subscriptionAmount))
+ // amount is always 0 for subscription transactions
+ ->setData('AMOUNT', 0)
+ ->setData(
+ 'SUB_PERIOD_MOMENT',
+ $this->getSubscriptionHelper()->getBillingDayForPeriodUnit($periodUnit, $profile->getStoreId())
+ );
+
+ // add OWNER* and ECOM_BILLTO_* and ECOM_SHIPTO_* parameters
+ $this->collectAddressParameters($profile);
+
+ return $this;
+ }
+
+
+ /**
+ * Calculates the end date of the profile from the start date, frequency, period unit and maximum cycles
+ *
+ * @param DateTime $startDate | start date of the subscription
+ * @param string $periodUnit | unit of the frequency (d, w, m)
+ * @param int $frequency | every nth unit the customer will be charged
+ * @param int $maxCycles | maximum amount of cycles
+ *
+ * @return DateTime|null - the end date or null if no maximum cycle amount is set
+ */
+ public function calculateEndDate(DateTime $startDate, $periodUnit, $frequency, $maxCycles)
+ {
+ if (!$this->isMappedUnit($periodUnit)) {
+ $frequency = $this->adjustFrequencyToUnitSpecialCases($periodUnit, $frequency);
+ $periodUnit = $this->mapUnit($periodUnit);
+ }
+
+ $endDate = null;
+ if ($maxCycles) {
+ $endDate = clone $startDate;
+ if ($endDate->format('d') > 28 && $periodUnit != self::PERIOD_UNIT_DAY) {
+ $endDate->sub(new DateInterval('P3D'));
+ }
+
+ $dateDiff = $frequency * $maxCycles;
+ // fix period unit for week, since the payment provider requests a strange unit
+ $periodUnit = $periodUnit == self::PERIOD_UNIT_WEEK ? 'w' : $periodUnit;
+
+ $endDate->add(new DateInterval('P' . $dateDiff . strtoupper($periodUnit)));
+ }
+ return $endDate;
+ }
+
+ /**
+ * Tests if the given unit is already mapped to the Ingenico types
+ *
+ * @param string $unit - unit to check
+ *
+ * @return bool
+ */
+ protected function isMappedUnit($unit)
+ {
+ return in_array(
+ $unit, array(
+ self::PERIOD_UNIT_DAY,
+ self::PERIOD_UNIT_WEEK,
+ self::PERIOD_UNIT_MONTH
+ )
+ );
+ }
+
+ /**
+ * Collects all parameters from the given objects and returns the parameter array
+ *
+ * @param Mage_Payment_Model_Info $paymentInfo
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ *
+ * @return mixed[] - utf8_encoded request parameters
+ */
+ public function collectAllParameters(Mage_Payment_Model_Info $paymentInfo,
+ Mage_Payment_Model_Recurring_Profile $profile
+ )
+ {
+ $this->collectProfileParameters($profile)
+ ->collectPaymentParameters($paymentInfo);
+
+ return $this->encodeValues()->toArray();
+ }
+
+ /**
+ * Collects all parameters relevant for the trial period from the given objects and returns the parameter array
+ *
+ * @param Mage_Payment_Model_Info $paymentInfo
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ *
+ * @return mixed[] - utf8_encoded request parameters
+ */
+ public function collectAllParametersForTrial(Mage_Payment_Model_Info $paymentInfo,
+ Mage_Payment_Model_Recurring_Profile $profile
+ )
+ {
+ $this->collectProfileParameters($profile, true)
+ ->collectPaymentParameters($paymentInfo, true);
+
+ return $this->encodeValues()->toArray();
+ }
+
+ /**
+ * collects all relevant parameters for the initial fee
+ *
+ * @param Mage_Payment_Model_Info $paymentInfo
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return string[] - utf8 encoded request parameters
+ */
+ public function collectAllParametersForInitialFee(Mage_Payment_Model_Info $paymentInfo,
+ Mage_Payment_Model_Recurring_Profile $profile,
+ Mage_Sales_Model_Order $order
+ )
+ {
+ /** @var $profile Mage_Sales_Model_Recurring_Profile */
+ $this->collectPaymentParameters($paymentInfo)->collectAddressParameters($profile);
+
+ $this->setData('AMOUNT', $this->getDataHelper()->getAmount($profile->getInitAmount()));
+ $this->setData('ORDERID', Mage::helper('ops/order')->getOpsOrderId($order));
+
+ return $this->encodeValues()->toArray();
+ }
+
+ /**
+ * utf8_decodes all parameters
+ *
+ * @return $this
+ */
+ protected function encodeValues()
+ {
+ foreach ($this->getData() as $key => $value) {
+ $this->setData($key, utf8_decode($value));
+ }
+
+ return $this;
+ }
+
+ /**
+ * Determines base values for the subscription depending on the trial parameter
+ *
+ * @param Mage_Sales_Model_Recurring_Profile $profile
+ * @param $trial - if the values for the trial subscription should be used or not
+ *
+ * @return string[] - containing the following:
+ * [0] => amount for the subscription,
+ * [1] => period Unit,
+ * [2] => periodFrequency,
+ * [3] => max
+ */
+ protected function getProfileValues($profile, $trial)
+ {
+ // subscription equals shipping for the product + the product amount+tax itself
+ if ($trial) {
+ $subscriptionAmount = $profile->getTrialBillingAmount() + $profile->getShippingAmount();
+ $periodUnit = $this->mapUnit($profile->getTrialPeriodUnit());
+ $periodFrequency = $this->adjustFrequencyToUnitSpecialCases(
+ $profile->getTrialPeriodUnit(), $profile->getTrialPeriodFrequency()
+ );
+ $maxCycles = $profile->getTrialPeriodMaxCycles();
+
+ } else {
+ $subscriptionAmount
+ = $profile->getBillingAmount() + $profile->getTaxAmount() + $profile->getShippingAmount();
+ $periodUnit = $this->mapUnit($profile->getPeriodUnit());
+ $periodFrequency = $this->adjustFrequencyToUnitSpecialCases(
+ $profile->getPeriodUnit(), $profile->getPeriodFrequency()
+ );
+ $maxCycles = $profile->getPeriodMaxCycles();
+
+ }
+
+ return array($subscriptionAmount, $periodUnit, $periodFrequency, $maxCycles);
+ }
+
+ /**
+ * Determines the start and end date from the given values.
+ *
+ * @param Mage_Sales_Model_Recurring_Profile $profile
+ * @param $trial
+ *
+ * @return string[] - containing the following:
+ * 0 => updated start date
+ * 1 => updated enddate
+ * 2 => updated period unit
+ * 3 => updated period frequency
+ */
+ protected function generateDates($profile, $trial)
+ {
+ // get profile values - subscription amount is not needed here
+ list(, $periodUnit, $periodFrequency, $maxCycles) = $this->getProfileValues($profile, $trial);
+
+ if (!$profile->getTrialPeriodUnit() && !$trial || $trial) {
+ // if we collect the trial parameters, or if we don't have a trial period at all
+ $startDate = new DateTime($profile->getStartDateTime());
+ $endDate = $this->calculateEndDate(
+ $startDate, $periodUnit, $periodFrequency, $maxCycles
+ );
+ } else {
+ // if we collect the regular subscription and a trial is existent
+ $trialStartDate = new DateTime($profile->getStartDateTime());
+ $trialPeriodUnit = $this->mapUnit($profile->getTrialPeriodUnit());
+ $trialPeriodFrequency = $this->adjustFrequencyToUnitSpecialCases(
+ $profile->getTrialPeriodUnit(), $profile->getTrialPeriodFrequency()
+ );
+ // calculate trial end date and use it as start date for the regular subscription
+ $trialEndDate = $this->calculateEndDate(
+ $trialStartDate, $trialPeriodUnit, $trialPeriodFrequency, $profile->getTrialPeriodMaxCycles()
+ );
+
+ $startDate = clone $trialEndDate;
+ $periodUnit = $this->mapUnit($profile->getPeriodUnit());
+ $periodFrequency = $this->adjustFrequencyToUnitSpecialCases(
+ $profile->getPeriodUnit(), $profile->getPeriodFrequency()
+ );
+ $maxCycles = $profile->getPeriodMaxCycles();
+ $endDate = $this->calculateEndDate(
+ $trialEndDate, $periodUnit, $periodFrequency, $maxCycles
+ );
+ }
+
+ return array($startDate, $endDate, $periodUnit, $periodFrequency);
+ }
+
+ /**
+ * Add address data to the bag if it is available
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ */
+ protected function collectAddressParameters(Mage_Payment_Model_Recurring_Profile $profile)
+ {
+ /** @var $profile Mage_Sales_Model_Recurring_Profile */
+ if ($profile->getQuote()) {
+ $this->addData(
+ $this->getRequestHelper()->getOwnerParams(
+ $profile->getQuote()->getBillingAddress(), $profile->getQuote()
+ )
+ )->addData($this->getRequestHelper()->extractBillToParameters($profile->getQuote()->getBillingAddress()));
+
+ if ($profile->getQuote()->getShippingAddress()) {
+ $this->addData(
+ $this->getRequestHelper()->extractShipToParameters($profile->getQuote()->getShippingAddress())
+ );
+ }
+ }
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Response/Handler.php b/app/code/community/Netresearch/OPS/Model/Response/Handler.php
new file mode 100644
index 0000000..eb77bbd
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/Handler.php
@@ -0,0 +1,77 @@
+
+ */
+?>
+getTypeHandler($responseArray['status'])
+ ->handleResponse($responseArray, $paymentMethod, $shouldRegisterFeedback);
+ }
+
+ /**
+ * @param $status
+ *
+ * @return Netresearch_OPS_Model_Response_TypeInterface
+ */
+ protected function getTypeHandler($status)
+ {
+ $type = null;
+
+ if (Netresearch_OPS_Model_Status::isCapture($status)) {
+ $type = Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_TRANSACTION_TYPE;
+ } elseif (Netresearch_OPS_Model_Status::isRefund($status)) {
+ $type = Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_TRANSACTION_TYPE;
+ } elseif (Netresearch_OPS_Model_Status::isVoid($status)) {
+ $type = Netresearch_OPS_Model_Payment_Abstract::OPS_VOID_TRANSACTION_TYPE;
+ } elseif (Netresearch_OPS_Model_Status::isAuthorize($status)) {
+ $type = Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_TRANSACTION_TYPE;
+ } elseif (Netresearch_OPS_Model_Status::isSpecialStatus($status)) {
+ $type = 'special';
+ } else {
+ Mage::throwException(Mage::helper('ops')->__('Can not handle status %s.', $status));
+ }
+
+ return Mage::getModel('ops/response_type_' . $type);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Response/Type/Abstract.php b/app/code/community/Netresearch/OPS/Model/Response/Type/Abstract.php
new file mode 100644
index 0000000..b55e5d5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/Type/Abstract.php
@@ -0,0 +1,373 @@
+
+ */
+?>
+getData('config') === null) {
+ $this->setData('config', Mage::getModel('ops/config'));
+ }
+
+ return $this->getData('config');
+ }
+
+ /**
+ * Performs the necessary actions for Magento to progress the order state correctly and automatically build the
+ * create sales objects
+ *
+ * @param array $responseArray
+ * @param Netresearch_OPS_Model_Payment_Abstract $paymentMethod
+ * @param bool $shouldRegisterFeedback
+ * determines if the Mage_Sales_Model_Order_Payments register*Feedback
+ * functions get called, defaults to true
+ *
+ * @return Netresearch_OPS_Model_Response_TypeInterface
+ */
+ public function handleResponse($responseArray, Netresearch_OPS_Model_Payment_Abstract $paymentMethod,
+ $shouldRegisterFeedback = true
+ ) {
+ $this->setData(array_change_key_case($responseArray, CASE_LOWER));
+ $this->setMethodInstance($paymentMethod);
+ $this->setShouldRegisterFeedback($shouldRegisterFeedback);
+
+ if ($this->getStatus() == $this->getMethodInstance()->getInfoInstance()->getAdditionalInformation('status')
+ && $this->getTransactionId() == $paymentMethod->getInfoInstance()->getLastTransId()
+ ) {
+ return $this;
+ }
+
+ $this->setGeneralTransactionInfo();
+ $this->_handleResponse();
+ $this->updateAdditionalInformation();
+
+ if ($this->getShouldRegisterFeedback() && $this->hasAlias()) {
+ Mage::helper('ops/alias')->saveAlias($responseArray);
+ }
+
+ return $this;
+ }
+
+ /**
+ * Handles the specific actions for the concrete payment status
+ */
+ protected abstract function _handleResponse();
+
+
+ /**
+ * Updates the additional information of the payment info object
+ *
+ * @see \Netresearch_OPS_Model_Response_Type_Abstract::updateDefaultInformation
+ * @see \Netresearch_OPS_Model_Response_Type_Abstract::setFraudDetectionParameters
+ */
+ protected function updateAdditionalInformation()
+ {
+ $this->getMethodInstance()->getInfoInstance()->setLastTransId($this->getTransactionId());
+ $this->updateDefaultInformation();
+ $this->setFraudDetectionParameters();
+ $this->setDeviceInformationParameters();
+ }
+
+ /**
+ * Updates default information in additional information of the payment info object
+ */
+ protected function updateDefaultInformation()
+ {
+ $payment = $this->getMethodInstance()->getInfoInstance();
+
+ $payment->setAdditionalInformation('paymentId', $this->getPayid())
+ ->setAdditionalInformation('status', $this->getStatus());
+
+ if ($this->hasAlias()) {
+ $payment->setAdditionalInformation('alias', $this->getAlias());
+ }
+
+ if ($this->hasAcceptance()) {
+ $payment->setAdditionalInformation('acceptence', $this->getAcceptance());
+ }
+
+ if ($this->hasBrand() && $this->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Cc) {
+ $payment->setAdditionalInformation('CC_BRAND', $this->getBrand());
+ }
+ }
+
+ protected function setDeviceInformationParameters()
+ {
+ if (!$this->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Bancontact) {
+ return;
+ }
+
+ $payment = $this->getMethodInstance()->getInfoInstance();
+ if ($this->hasMobilemode()) {
+ $payment->setAdditionalInformation('MOBILEMODE', $this->getMobilemode());
+ }
+ }
+
+ /**
+ * Sets Transaction details (TransactionId etc.)
+ */
+ protected function setGeneralTransactionInfo()
+ {
+ $payment = $this->getMethodInstance()->getInfoInstance();
+
+ $payment->setTransactionParentId($this->getPayid());
+
+ if (!$this->hasPayidsub()) {
+ $transId = $payment->getLastTransId();
+ } else {
+ $transId = $this->getTransactionId();
+ }
+
+ $payment->setTransactionId($transId);
+ $payment->setIsTransactionClosed(false);
+ }
+
+ /**
+ * Updates fraud detection information on additional information of the payment info object
+ */
+ protected function setFraudDetectionParameters()
+ {
+ $payment = $this->getMethodInstance()->getInfoInstance();
+ if ($this->hasScoring()) {
+ $payment->setAdditionalInformation('scoring', $this->getScoring());
+ }
+
+ if ($this->hasScoCategory()) {
+ $payment->setAdditionalInformation('scoringCategory', $this->getScoCategory());
+ }
+
+ $additionalScoringData = array();
+ foreach ($this->getConfig()->getAdditionalScoringKeys() as $key) {
+ if ($this->hasData(strtolower($key))) {
+ if (false === mb_detect_encoding($this->getData(strtolower($key)), 'UTF-8', true)) {
+ $additionalScoringData[$key] = utf8_encode($this->getData(strtolower($key)));
+ } else {
+ $additionalScoringData[$key] = $this->getData(strtolower($key));
+ }
+
+ }
+ }
+
+ $payment->setAdditionalInformation('additionalScoringData', $additionalScoringData);
+ }
+
+ /**
+ * @param string $orderComment
+ * @param string $additionalInfo
+ *
+ */
+ protected function addOrderComment($orderComment, $additionalInfo = '')
+ {
+ $orderComment = $this->getOrderComment($orderComment, $additionalInfo);
+ $this->getMethodInstance()->getInfoInstance()->getOrder()->addStatusHistoryComment($orderComment);
+ }
+
+ /**
+ * Add order comment about final status
+ *
+ * @param string $additionalInfo
+ */
+ protected function addFinalStatusComment($additionalInfo = '')
+ {
+ $this->addOrderComment($this->getFinalStatusComment($additionalInfo));
+ }
+
+ /**
+ * Add order comment about intermediate status
+ *
+ * @param string $additionalInfo
+ */
+ protected function addIntermediateStatusComment($additionalInfo = '')
+ {
+ $this->addOrderComment($this->getIntermediateStatusComment($additionalInfo));
+ }
+
+ /**
+ * Add order comment about refused status
+ *
+ * @param string $additionalInfo
+ */
+ protected function addRefusedStatusComment($additionalInfo = '')
+ {
+ $this->addOrderComment($this->getRefusedStatusComment($additionalInfo));
+ }
+
+ /**
+ * Add order comment about fraud status
+ *
+ * @param string $additionalInfo
+ */
+ protected function addFraudStatusComment($additionalInfo = '')
+ {
+ $this->addOrderComment($this->getFraudStatusComment($additionalInfo));
+ }
+
+
+ /**
+ * @param string $additionalInfo
+ *
+ * @return string
+ */
+ protected function getFinalStatusComment($additionalInfo = '')
+ {
+ $orderComment = Mage::helper('ops')->__(
+ 'Received Ingenico ePayments feedback status update with final status %s.',
+ $this->getStatus()
+ );
+
+ return $this->getOrderComment($orderComment, $additionalInfo);
+
+ }
+
+ /**
+ * @param string $additionalInfo
+ *
+ * @return string
+ */
+ protected function getIntermediateStatusComment($additionalInfo = '')
+ {
+ $orderComment = Mage::helper('ops')->__(
+ 'Received Ingenico ePayments feedback status update with intermediate status %s.',
+ $this->getStatus()
+ );
+
+ return $this->getOrderComment($orderComment, $additionalInfo);
+ }
+
+ /**
+ * @param string $additionalInfo
+ *
+ * @return string
+ */
+ protected function getRefusedStatusComment($additionalInfo = '')
+ {
+ $orderComment = Mage::helper('ops')->__(
+ 'Received Ingenico ePayments feedback status update with refused status %s.',
+ $this->getStatus()
+ );
+
+ return $this->getOrderComment($orderComment, $additionalInfo);
+ }
+
+ /**
+ * @param string $additionalInfo
+ *
+ * @return string
+ */
+ protected function getFraudStatusComment($additionalInfo = '')
+ {
+ $orderComment = Mage::helper('ops')->__(
+ 'Received Ingenico ePayments feedback status update with suspected fraud status %s.',
+ $this->getStatus()
+ );
+
+ return $this->getOrderComment($orderComment, $additionalInfo);
+ }
+
+ /**
+ * @param string $additionalInfo
+ * @param string $orderComment
+ *
+ * @return string
+ */
+ protected function getOrderComment($orderComment, $additionalInfo = '')
+ {
+ if ($additionalInfo) {
+ $orderComment .= ' ' . $additionalInfo;
+ }
+
+ return $orderComment;
+ }
+
+ /**
+ * Merges the PAYID with the PAYIDSUB, if the latter is present, otherwise just returns the PAYID
+ *
+ * @return string
+ */
+ public function getTransactionId()
+ {
+ $transId = $this->getPayid();
+ if ($this->hasPayidsub()) {
+ $transId .= '/' . $this->getPayidsub();
+ }
+
+ return $transId;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Response/Type/Authorize.php b/app/code/community/Netresearch/OPS/Model/Response/Type/Authorize.php
new file mode 100644
index 0000000..336b675
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/Type/Authorize.php
@@ -0,0 +1,251 @@
+
+ */
+?>
+getStatus())) {
+ Mage::throwException(Mage::helper('ops')->__('%s is not a authorize status!', $this->getStatus()));
+ }
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $this->getMethodInstance()->getInfoInstance()->getOrder();
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $this->getMethodInstance()->getInfoInstance();
+
+ // if no parent transaction id has been set yet set the parentTransactionId so we can void
+ if (!$payment->getParentTransactionId()) {
+ $payment->setParentTransactionId($this->getPayid());
+ }
+
+ if (Netresearch_OPS_Model_Status::isFinal($this->getStatus())) {
+ $this->processFinalStatus($order, $payment);
+ } else {
+ $this->processIntermediateState($payment, $order);
+ }
+
+ $this->persistSalesObject($payment, $order);
+ }
+
+ /**
+ * in CE 1.7 Mage_Sales_Model_Order::registerCancellation will always fail with exception if the
+ * order is in payment_review state. we therefore cancel the order 'manually'.
+ *
+ * below code is c&p from Mage_Sales_Model_Order::registerCancellation:
+ *
+ * @see Mage_Sales_Model_Order::registerCancellation
+ *
+ * @param Mage_Sales_Model_Order $order
+ */
+ protected function registerCancellation($order)
+ {
+ $cancelState = Mage_Sales_Model_Order::STATE_CANCELED;
+ /** @var Mage_Sales_Model_Order_Item $item */
+ foreach ($order->getAllItems() as $item) {
+ if ($cancelState != Mage_Sales_Model_Order::STATE_PROCESSING
+ && $item->getQtyToRefund()
+ ) {
+ if ($item->getQtyToShip() > $item->getQtyToCancel()) {
+ $cancelState = Mage_Sales_Model_Order::STATE_PROCESSING;
+ } else {
+ $cancelState = Mage_Sales_Model_Order::STATE_COMPLETE;
+ }
+ }
+ $item->cancel();
+ }
+
+ $order->setSubtotalCanceled($order->getSubtotal() - $order->getSubtotalInvoiced());
+ $order->setBaseSubtotalCanceled(
+ $order->getBaseSubtotal() - $order->getBaseSubtotalInvoiced()
+ );
+
+ $order->setTaxCanceled($order->getTaxAmount() - $order->getTaxInvoiced());
+ $order->setBaseTaxCanceled($order->getBaseTaxAmount() - $order->getBaseTaxInvoiced());
+
+ $order->setShippingCanceled($order->getShippingAmount() - $order->getShippingInvoiced());
+ $order->setBaseShippingCanceled(
+ $order->getBaseShippingAmount() - $order->getBaseShippingInvoiced()
+ );
+
+ $order->setDiscountCanceled(
+ abs($order->getDiscountAmount()) - $order->getDiscountInvoiced()
+ );
+ $order->setBaseDiscountCanceled(
+ abs($order->getBaseDiscountAmount()) - $order->getBaseDiscountInvoiced()
+ );
+
+ $order->setTotalCanceled($order->getGrandTotal() - $order->getTotalPaid());
+ $order->setBaseTotalCanceled($order->getBaseGrandTotal() - $order->getBaseTotalPaid());
+
+ $order->setState($cancelState, true, $this->getFinalStatusComment());
+ }
+
+ /**
+ * process final state
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param Mage_Sales_Model_Order_Payment $payment
+ */
+ protected function processFinalStatus($order, $payment)
+ {
+ // handle authorization declined
+ // thrown exception gets catched by core and order will not been created
+ if ($this->getStatus() == Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED
+ ) {
+ $this->processAuthorizationDeclined($order, $payment);
+
+ } elseif ($this->getStatus() == Netresearch_OPS_Model_Status::CANCELED_BY_CUSTOMER) {
+ $order->registerCancellation($this->getFinalStatusComment());
+ }
+
+ if ($this->getShouldRegisterFeedback()) {
+ if ($order->getState() === Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW) {
+ $this->processFinalStatusInPaymentReview($order, $payment);
+ } elseif ($order->getState() === Mage_Sales_Model_Order::STATE_PENDING_PAYMENT
+ || $order->getState() === Mage_Sales_Model_Order::STATE_NEW
+ ) {
+ $payment->registerAuthorizationNotification($this->getAmount());
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, true, $this->getFinalStatusComment()
+ );
+
+ }
+ } else {
+ $this->addFinalStatusComment();
+ }
+ }
+
+ /**
+ * save payment and order object and send transaction email if order state is not canceled
+ *
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param Mage_Sales_Model_Order $order
+ */
+ protected function persistSalesObject($payment, $order)
+ {
+ if ($this->getShouldRegisterFeedback()) {
+ $payment->save();
+ $order->save();
+
+ // gateway payments do not send confirmation emails by default
+ if ($order->getState() != Mage_Sales_Model_Order::STATE_CANCELED) {
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ }
+ }
+ }
+
+ /**
+ * process non final state
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param Mage_Sales_Model_Order $order
+ */
+ protected function processIntermediateState($payment, $order)
+ {
+ $payment->setIsTransactionPending(true);
+ if ($this->getStatus() == Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT) {
+ $payment->setIsFraudDetected(true);
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW,
+ Mage_Sales_Model_Order::STATUS_FRAUD,
+ $this->getFraudStatusComment(
+ Mage::helper('ops')->__('Please have a look in Ingenico ePayments backend for more information.')
+ )
+ );
+ } else {
+ $order->addStatusHistoryComment($this->getIntermediateStatusComment());
+ }
+ if ($this->getShouldRegisterFeedback()) {
+ $payment->registerAuthorizationNotification($this->getAmount());
+ }
+ }
+
+ /**
+ * process authorization declined feedback
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param Mage_Sales_Model_Order_Payment $payment
+ */
+ protected function processAuthorizationDeclined($order, $payment)
+ {
+ if (!$this->getShouldRegisterFeedback()) {
+ Mage::throwException(
+ Mage::helper('ops')->__(
+ 'Payment failed because the authorization was declined! Please choose another payment method.'
+ )
+ );
+ } elseif ($order->getState() === Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW) {
+
+ try {
+ // if the payment was previously in payment review/has status 46
+ // the identification obviously failed and the order gets canceled
+ $payment->setNotificationResult(true);
+ $payment->registerPaymentReviewAction(
+ Mage_Sales_Model_Order_Payment::REVIEW_ACTION_DENY, false
+ );
+ } catch (Mage_Core_Exception $e) {
+ // perform manual cancellation if we are on CE1.7 and receive the error message
+ if ($e->getMessage() === Mage::helper('sales')->__('Order does not allow to be canceled.')) {
+ $this->registerCancellation($order);
+ }
+ }
+ }
+ }
+
+ /**
+ * If order is in payment_review and we receive a final status, the order needs to be moved to
+ * new the proper order state, e.g. canceled for failed payments or processing for successful ones
+ *
+ * @param Mage_Sales_Model_Order $order
+ * @param Mage_Sales_Model_Order_Payment $payment
+ */
+ protected function processFinalStatusInPaymentReview($order, $payment)
+ {
+ $action = Mage_Sales_Model_Order_Payment::REVIEW_ACTION_ACCEPT;
+ $targetState = Mage_Sales_Model_Order::STATE_PENDING_PAYMENT;
+ if (Netresearch_OPS_Model_Status::canResendPaymentInfo($this->getStatus())
+ && Mage::helper('ops/payment')->isInlinePayment($payment)
+ ) {
+ $targetState = Mage_Sales_Model_Order::STATE_CANCELED;
+ $action = Mage_Sales_Model_Order_Payment::REVIEW_ACTION_DENY;
+ }
+ $payment->setNotificationResult(true);
+ $payment->registerPaymentReviewAction($action, false);
+ if ($order->getState() != $targetState) {
+ $order->setState($targetState, true, $this->getFinalStatusComment());
+ }
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Response/Type/Capture.php b/app/code/community/Netresearch/OPS/Model/Response/Type/Capture.php
new file mode 100644
index 0000000..4c134d3
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/Type/Capture.php
@@ -0,0 +1,151 @@
+
+ */
+?>
+getStatus())) {
+ Mage::throwException(Mage::helper('ops')->__('%s is not a capture status!', $this->getStatus()));
+ }
+
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $this->getMethodInstance()->getInfoInstance();
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $payment->getOrder();
+
+
+ /**
+ * Basically we have to check the following things here:
+ *
+ * Order state - payment_review suggests an already existing intermediate status
+ * - pending_payment or new suggests no feedback yet
+ *
+ * payment status - intermediate and not failed -> move to payment review or add another comment
+ * - intermediate and failed -> if recoverable let the order open and place comment
+ * - finished - finish invoice dependent on order state
+ */
+
+ if (Netresearch_OPS_Model_Status::isIntermediate($this->getStatus())) {
+ $this->processIntermediateState($payment, $order);
+ } else {
+ // final means state 9 or 95
+ $this->processFinalState($order, $payment);
+ }
+
+ if ($this->getShouldRegisterFeedback()) {
+ $this->registerFeedBack($payment, $order);
+ }
+ }
+
+ /**
+ * process intermediate state
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param Mage_Sales_Model_Order $order
+ */
+ protected function processIntermediateState($payment, $order)
+ {
+ $message = $this->getIntermediateStatusComment();
+ $payment->setIsTransactionPending(true);
+ if ($order->getState() == Mage_Sales_Model_Order::STATE_PENDING_PAYMENT
+ || $order->getState() == Mage_Sales_Model_Order::STATE_PROCESSING
+ ) {
+ // transaction was placed on PSP, initial feedback to shop or partial capture case
+ $payment->setPreparedMessage($message);
+ if ($this->getShouldRegisterFeedback()) {
+ $payment->registerCaptureNotification($this->getAmount());
+ }
+
+ } elseif ($order->getState() == Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW) {
+ // payment was pending and is still pending
+ $payment->setIsTransactionApproved(false);
+ $payment->setIsTransactionDenied(false);
+ $payment->setPreparedMessage($message);
+
+ if ($this->getShouldRegisterFeedback()) {
+ $payment->setNotificationResult(true);
+ $payment->registerPaymentReviewAction(Mage_Sales_Model_Order_Payment::REVIEW_ACTION_UPDATE, false);
+ }
+ }
+ }
+
+ /**
+ * process final state
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param Mage_Sales_Model_Order $order
+ */
+ protected function processFinalState($order, $payment)
+ {
+ $message = $this->getFinalStatusComment();
+ if ($order->getState() == Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW) {
+ $payment->setNotificationResult(true);
+ $payment->setPreparedMessage($message);
+ if ($this->getShouldRegisterFeedback()) {
+ $payment->registerPaymentReviewAction(Mage_Sales_Model_Order_Payment::REVIEW_ACTION_ACCEPT, false);
+ $transaction = $payment->getTransaction($payment->getLastTransId());
+ if ($transaction) {
+ $transaction->close(true);
+ }
+ }
+ } else {
+ $payment->setPreparedMessage($message);
+ if ($this->getShouldRegisterFeedback()) {
+ $payment->registerCaptureNotification($this->getAmount());
+ }
+ }
+ }
+
+ /**
+ * save payment and order object and send transaction email
+ *
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @param Mage_Sales_Model_Order $order
+ */
+ protected function registerFeedBack($payment, $order)
+ {
+ $payment->save();
+ $order->save();
+
+ // gateway payments do not send confirmation emails by default
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+
+ /** @var Mage_Sales_Model_Order_Invoice $invoice */
+ $invoice = Mage::getModel('sales/order_invoice')->load($this->getTransactionId(), 'transaction_id');
+ if ($invoice->getId()) {
+ Mage::helper('ops')->sendTransactionalEmail($invoice);
+ }
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Response/Type/Refund.php b/app/code/community/Netresearch/OPS/Model/Response/Type/Refund.php
new file mode 100644
index 0000000..75b7675
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/Type/Refund.php
@@ -0,0 +1,193 @@
+
+ */
+?>
+getStatus())) {
+ Mage::throwException(Mage::helper('ops')->__('%s is not a refund status!', $this->getStatus()));
+ }
+
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $this->getMethodInstance()->getInfoInstance();
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $payment->getOrder();
+
+ if (!$this->hasPayidsub()) {
+ $creditMemo = $this->determineCreditMemo();
+ $payment->setRefundTransactionId($creditMemo->getTransactionId());
+ } else {
+ $creditMemo = Mage::getModel('sales/order_creditmemo')->load(
+ $this->getTransactionId(), 'transaction_id'
+ );
+ $payment->setRefundTransactionId($this->getTransactionId());
+ }
+
+ if ($creditMemo->getId()) {
+ if (Netresearch_OPS_Model_Status::isFinal($this->getStatus())
+ && $creditMemo->getState() == Mage_Sales_Model_Order_Creditmemo::STATE_OPEN
+ ) {
+ $creditMemo->setState(Mage_Sales_Model_Order_Creditmemo::STATE_REFUNDED);
+ $this->closeRefundTransaction($creditMemo);
+ $this->addFinalStatusComment();
+ } elseif ($this->getStatus() == Netresearch_OPS_Model_Status::REFUND_REFUSED) {
+ $order = $this->processRefundRefused($creditMemo);
+ } else {
+ $this->addIntermediateStatusComment();
+ }
+
+ } else {
+ if ($this->getShouldRegisterFeedback()) {
+ $payment->setParentTransactionId($this->getPayid());
+ $payment->setTransactionId($this->getTransactionId());
+ $payment->setIsTransactionClosed(Netresearch_OPS_Model_Status::isFinal($this->getStatus()));
+ $payment->registerRefundNotification($this->getAmount());
+ }
+ if (Netresearch_OPS_Model_Status::isFinal($this->getStatus())) {
+ $this->addFinalStatusComment();
+ } else {
+ $this->addIntermediateStatusComment();
+ $creditMemo = $payment->getCreatedCreditMemo() ?: $payment->getCreditmemo();
+ if ($creditMemo) {
+ $creditMemo->setState(Mage_Sales_Model_Order_Creditmemo::STATE_OPEN);
+ }
+ }
+ }
+
+ if ($this->getShouldRegisterFeedback()) {
+ $this->registerFeedBack($order, $payment, $creditMemo);
+ }
+
+ }
+
+ /**
+ * Will load the creditmemo by identifying open refund transactions
+ *
+ * @return Mage_Sales_Model_Order_Creditmemo|null
+ */
+ protected function determineCreditMemo()
+ {
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $this->getMethodInstance()->getInfoInstance();
+ $refundTransaction = Mage::helper('ops/order_refund')->getOpenRefundTransaction($payment);
+ /** @var Mage_Sales_Model_Order_Creditmemo $creditmemo */
+ $creditmemo = Mage::getModel('sales/order_creditmemo')->load(
+ $refundTransaction->getTxnId(), 'transaction_id'
+ );
+
+ return $creditmemo;
+ }
+
+ /**
+ * Closes the refund transaction for the given creditmemo
+ *
+ * @param $creditMemo
+ */
+ protected function closeRefundTransaction($creditMemo)
+ {
+ $refundTransaction = $this->getMethodInstance()->getInfoInstance()->lookupTransaction(
+ $creditMemo->getTransactionId(), Mage_Sales_Model_Order_Payment_Transaction::TYPE_REFUND
+ );
+ if ($refundTransaction) {
+ $refundTransaction->setIsClosed(true)
+ ->save();
+ }
+ }
+
+ /**
+ * process refund refused response
+ *
+ * @param $creditMemo
+ * @return mixed
+ */
+ protected function processRefundRefused($creditMemo)
+ {
+ $order = $creditMemo->getOrder();
+ $creditMemo->cancel()->save();
+ $this->closeRefundTransaction($creditMemo);
+ $invoice = Mage::getModel('sales/order_invoice')->load($creditMemo->getInvoiceId());
+ $invoice->setIsUsedForRefund(0)
+ ->setBaseTotalRefunded(
+ $invoice->getBaseTotalRefunded() - $creditMemo->getBaseGrandTotal()
+ );
+ $creditMemo->setInvoice($invoice);
+ /** @var Mage_Sales_Model_Order_Creditmemo_Item $item */
+ foreach ($creditMemo->getAllItems() as $item) {
+ $item->getOrderItem()->setAmountRefunded(
+ $item->getOrderItem()->getAmountRefunded() - $item->getRowTotal()
+ );
+ $item->getOrderItem()->setBaseAmountRefunded(
+ $item->getOrderItem()->getBaseAmountRefunded() - $item->getBaseRowTotal()
+ );
+ }
+ $order->setTotalRefunded($order->getTotalRefunded() - $creditMemo->getBaseGrandTotal());
+ $order->setBaseTotalRefunded($order->getBaseTotalRefunded() - $creditMemo->getBaseGrandTotal());
+
+ $this->addRefusedStatusComment();
+ $state = Mage_Sales_Model_Order::STATE_COMPLETE;
+ if ($order->canShip() || $order->canInvoice()) {
+ $state = Mage_Sales_Model_Order::STATE_PROCESSING;
+ }
+ $order->setState(
+ $state,
+ true,
+ $this->getRefusedStatusComment(Mage::helper('ops')->__('Refund refused by Ingenico ePayments.'))
+ );
+
+ return $order;
+ }
+
+ /**
+ * register feedback
+ *
+ * @param $order
+ * @param $payment
+ * @param $creditMemo
+ */
+ protected function registerFeedBack($order, $payment, $creditMemo)
+ {
+ $transactionSave = Mage::getModel('core/resource_transaction')
+ ->addObject($order)
+ ->addObject($payment)
+ ->addObject($creditMemo);
+
+ if ($creditMemo->getInvoice()) {
+ $transactionSave->addObject($creditMemo->getInvoice());
+ }
+ $transactionSave->save();
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Response/Type/Special.php b/app/code/community/Netresearch/OPS/Model/Response/Type/Special.php
new file mode 100644
index 0000000..c81e954
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/Type/Special.php
@@ -0,0 +1,87 @@
+
+ */
+?>
+getStatus())) {
+ Mage::throwException(Mage::helper('ops')->__('%s is not a special status!', $this->getStatus()));
+ }
+
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $this->getMethodInstance()->getInfoInstance();
+ $order = $payment->getOrder();
+ $helper = Mage::helper('ops');
+
+ if ($this->getStatus() == Netresearch_OPS_Model_Status::WAITING_FOR_IDENTIFICATION) {
+ $payment->setIsTransactionPending(true);
+ $payment->setAdditionalInformation('HTML_ANSWER', $this->getHtmlAnswer());
+ $order->addStatusHistoryComment(
+ $this->getIntermediateStatusComment($helper->__('Customer redirected for 3DS authorization.'))
+ );
+ }
+
+ if ($this->getStatus() == Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT) {
+ $order->addStatusHistoryComment(
+ $this->getIntermediateStatusComment(
+ $helper->__(
+ 'Customer received your payment instructions, waiting for actual payment.'
+ )
+ )
+ );
+
+ // gateway payments do not send confirmation emails by default
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ }
+
+ if ($this->getStatus() == Netresearch_OPS_Model_Status::INVALID_INCOMPLETE) {
+ //save status information to order before exception
+ if($this->getShouldRegisterFeedback()){
+ $this->updateAdditionalInformation();
+ $payment->save();
+ }
+
+
+ $message = Mage::helper('ops')->__('Ingenico ePayments status 0, the action failed.');
+ if ($helper->isAdminSession()) {
+ $message .= ' ' . $this->getNcerror() . ' ' . $this->getNcerrorplus();
+ }
+ Mage::throwException($message);
+ }
+
+ $payment->save();
+ $order->save();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Response/Type/Void.php b/app/code/community/Netresearch/OPS/Model/Response/Type/Void.php
new file mode 100644
index 0000000..40d5891
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/Type/Void.php
@@ -0,0 +1,67 @@
+
+ */
+?>
+getStatus())) {
+ Mage::throwException(Mage::helper('ops')->__('%s is not a void status!', $this->getStatus()));
+ }
+
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $this->getMethodInstance()->getInfoInstance();
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $payment->getOrder();
+ if (Netresearch_OPS_Model_Status::isFinal($this->getStatus())) {
+ if ($this->getShouldRegisterFeedback()) {
+
+ $payment->setMessage(
+ Mage::helper('ops')->__('Received Ingenico ePayments status %s. Order cancelled.', $this->getStatus())
+ );
+ $payment->registerVoidNotification($this->getAmount());
+
+ // payment void does not cancel the order, but sets it to processing.
+ // We therefore need to cancel the order ourselves.
+ $order->registerCancellation($this->getFinalStatusComment(), true);
+ } else {
+ $this->addFinalStatusComment();
+ }
+ } else {
+ $payment->setMessage($this->getIntermediateStatusComment());
+ }
+
+ $order->save();
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Response/TypeInterface.php b/app/code/community/Netresearch/OPS/Model/Response/TypeInterface.php
new file mode 100644
index 0000000..cd5e3d2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Response/TypeInterface.php
@@ -0,0 +1,51 @@
+
+ */
+?>
+options) {
+ $this->options = Mage::getResourceModel('directory/country_collection')->loadData()->toOptionArray(false);
+ if (!$isMultiselect) {
+ array_unshift(
+ $this->options,
+ array(
+ 'value'=>'',
+ 'label'=> Mage::helper('adminhtml')->__('--Please Select--')
+ )
+ );
+ }
+ foreach ($this->options as $offset=>$option) {
+ if (!in_array($option['value'], $this->countries)) {
+ unset($this->options[$offset]);
+ }
+ }
+ $this->options['*'] = array(
+ 'value'=>'*',
+ 'label'=> Mage::helper('adminhtml')->__(Mage::helper('ops')->__('Miscellaneous Countries'))
+ );
+ }
+
+ return $this->options;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Cc/AliasInterfaceEnabledTypes.php b/app/code/community/Netresearch/OPS/Model/Source/Cc/AliasInterfaceEnabledTypes.php
new file mode 100644
index 0000000..5a025cf
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Cc/AliasInterfaceEnabledTypes.php
@@ -0,0 +1,62 @@
+getAllCcTypes(),
+ $this->getAliasInterfaceCompatibleTypes()
+ );
+ foreach ($types as $type) {
+ $options[] = array(
+ 'value' => $type,
+ 'label' => Mage::helper('ops')->__($type)
+ );
+ }
+ return $options;
+ }
+
+ public function getAliasInterfaceCompatibleTypes()
+ {
+ return array(
+ 'American Express',
+ 'Diners Club',
+ 'MaestroUK',
+ 'MasterCard',
+ 'VISA',
+ );
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Cc/RecurringTypes.php b/app/code/community/Netresearch/OPS/Model/Source/Cc/RecurringTypes.php
new file mode 100644
index 0000000..6ca88fa
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Cc/RecurringTypes.php
@@ -0,0 +1,50 @@
+
+ */
+class Netresearch_OPS_Model_Source_Cc_RecurringTypes
+{
+
+ public function toOptionArray()
+ {
+ $options = array();
+ $types = Mage::getModel('ops/config')->getAllRecurringCcTypes();
+ $translatedTypes = array();
+ foreach ($types as $type) {
+ $translatedTypes[Mage::helper('ops')->__($type)] = $type;
+ }
+ ksort($translatedTypes);
+ foreach ($translatedTypes as $label => $value) {
+ $options[] = array(
+ 'value' => $value,
+ 'label' => $label
+ );
+ }
+ return $options;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Cc/Types.php b/app/code/community/Netresearch/OPS/Model/Source/Cc/Types.php
new file mode 100644
index 0000000..0620a97
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Cc/Types.php
@@ -0,0 +1,52 @@
+getAllCcTypes();
+ $translatedTypes = array();
+ foreach ($types as $type) {
+ $translatedTypes[Mage::helper('ops')->__($type)] = $type;
+ }
+ ksort($translatedTypes);
+ foreach ($translatedTypes as $label=>$value) {
+ $options[] = array(
+ 'value' => $value,
+ 'label' => $label
+ );
+ }
+ return $options;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/DebitCard/AliasInterfaceEnabledTypes.php b/app/code/community/Netresearch/OPS/Model/Source/DebitCard/AliasInterfaceEnabledTypes.php
new file mode 100644
index 0000000..ef5ea2f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/DebitCard/AliasInterfaceEnabledTypes.php
@@ -0,0 +1,61 @@
+getAllDcTypes(),
+ $this->getAliasInterfaceCompatibleTypes()
+ );
+ foreach ($types as $type) {
+ $options[] = array(
+ 'value' => $type,
+ 'label' => Mage::helper('ops')->__($type)
+ );
+ }
+ return $options;
+ }
+
+ public function getAliasInterfaceCompatibleTypes()
+ {
+ return array(
+ 'Maestro',
+ 'MaestroUK',
+ 'MasterCard',
+ 'VISA',
+ );
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/DebitCard/Types.php b/app/code/community/Netresearch/OPS/Model/Source/DebitCard/Types.php
new file mode 100644
index 0000000..f02fdac
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/DebitCard/Types.php
@@ -0,0 +1,52 @@
+getAllDcTypes();
+ $translatedTypes = array();
+ foreach ($types as $type) {
+ $translatedTypes[Mage::helper('ops')->__($type)] = $type;
+ }
+ ksort($translatedTypes);
+ foreach ($translatedTypes as $label=>$value) {
+ $options[] = array(
+ 'value' => $value,
+ 'label' => $label
+ );
+ }
+ return $options;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/DirectDebit/Countries.php b/app/code/community/Netresearch/OPS/Model/Source/DirectDebit/Countries.php
new file mode 100644
index 0000000..cd09167
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/DirectDebit/Countries.php
@@ -0,0 +1,65 @@
+options) {
+ $this->options = Mage::getResourceModel('directory/country_collection')->loadData()->toOptionArray(false);
+ if (!$isMultiselect) {
+ array_unshift(
+ $this->options,
+ array(
+ 'value'=>'',
+ 'label'=> Mage::helper('adminhtml')->__('--Please Select--')
+ )
+ );
+ }
+ foreach ($this->options as $offset=>$option) {
+ if (!in_array($option['value'], $this->countries)) {
+ unset($this->options[$offset]);
+ }
+ }
+ }
+
+ return $this->options;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/DirectEbanking/Brands.php b/app/code/community/Netresearch/OPS/Model/Source/DirectEbanking/Brands.php
new file mode 100644
index 0000000..a469eb2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/DirectEbanking/Brands.php
@@ -0,0 +1,67 @@
+ 'DirectEbanking',
+ ),
+ array(
+ 'value' => 'DirectEbankingAT',
+ ),
+ array(
+ 'value' => 'DirectEbankingBE',
+ ),
+ array(
+ 'value' => 'DirectEbankingCH',
+ ),
+ array(
+ 'value' => 'DirectEbankingDE',
+ ),
+ array(
+ 'value' => 'DirectEbankingFR',
+ ),
+ array(
+ 'value' => 'DirectEbankingGB',
+ )
+);
+
+ /**
+ * @return array
+ */
+ public function toOptionArray()
+ {
+ foreach ($this->options as $key => $value) {
+ $this->options[$key]['label'] = Mage::helper('ops')->__($value['value']);
+ }
+ return $this->options;
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Kwixo/ProductCategories.php b/app/code/community/Netresearch/OPS/Model/Source/Kwixo/ProductCategories.php
new file mode 100644
index 0000000..3d16259
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Kwixo/ProductCategories.php
@@ -0,0 +1,127 @@
+ 1,
+ 'label' => Mage::helper('ops/data')->__('Food & gastronomy')
+ ),
+ array(
+ 'value' => 2,
+ 'label' => Mage::helper('ops/data')->__('Car & Motorbike')
+ ),
+ array(
+ 'value' => 3,
+ 'label' => Mage::helper('ops/data')->__('Culture & leisure')
+ ),
+ array(
+ 'value' => 4,
+ 'label' => Mage::helper('ops/data')->__('Home & garden')
+ ),
+ array(
+ 'value' => 5,
+ 'label' => Mage::helper('ops/data')->__('Appliances')
+ ),
+ array(
+ 'value' => 6,
+ 'label' => Mage::helper('ops/data')->__('Auctions and bulk purchases')
+ ),
+ array(
+ 'value' => 7,
+ 'label' => Mage::helper('ops/data')->__('Flowers & gifts')
+ ),
+ array(
+ 'value' => 8,
+ 'label' => Mage::helper('ops/data')->__('Computer & software')
+ ),
+ array(
+ 'value' => 9,
+ 'label' => Mage::helper('ops/data')->__('Health & beauty')
+ ),
+ array(
+ 'value' => 10,
+ 'label' => Mage::helper('ops/data')->__('Services for individuals')
+ ),
+ array(
+ 'value' => 11,
+ 'label' => Mage::helper('ops/data')->__('Services for professionals')
+ ),
+ array(
+ 'value' => 12,
+ 'label' => Mage::helper('ops/data')->__('Sports')
+ ),
+ array(
+ 'value' => 13,
+ 'label' => Mage::helper('ops/data')->__('Clothing & accessories')
+ ),
+ array(
+ 'value' => 14,
+ 'label' => Mage::helper('ops/data')->__('Travel & tourism')
+ ),
+ array(
+ 'value' => 15,
+ 'label' => Mage::helper('ops/data')->__('Hifi, photo & video')
+ ),
+ array(
+ 'value' => 16,
+ 'label' => Mage::helper('ops/data')->__('Telephony & communication')
+ ),
+ array(
+ 'value' => 17,
+ 'label' => Mage::helper('ops/data')->__('Jewelry & precious metals')
+ ),
+ array(
+ 'value' => 18,
+ 'label' => Mage::helper('ops/data')->__('Baby articles and accessories')
+ ),
+ array(
+ 'value' => 19,
+ 'label' => Mage::helper('ops/data')->__('Sound & light')
+ )
+ );
+ }
+
+ public function getValidKwixoCategoryIds()
+ {
+ $kwixoValues = array();
+ foreach ($this->toOptionArray() as $option) {
+ $kwixoValues[] = $option['value'];
+ }
+ return $kwixoValues;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Kwixo/ShipMethodType.php b/app/code/community/Netresearch/OPS/Model/Source/Kwixo/ShipMethodType.php
new file mode 100644
index 0000000..c5af638
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Kwixo/ShipMethodType.php
@@ -0,0 +1,94 @@
+ "",
+ 'label' => Mage::helper('ops/data')->__('--Please select--')
+ ),
+ array(
+ 'value' => self::PICK_UP_AT_MERCHANT,
+ 'label' => Mage::helper('ops/data')->__('Pick up at merchant')
+ ),
+ array(
+ 'value' => self::COLLECTION_POINT,
+ 'label' => Mage::helper('ops/data')->__(
+ 'Collection point (Kiala...)'
+ )
+ ),
+ array(
+ 'value' => self::COLLECT_AT_AIRPORT,
+ 'label' => Mage::helper('ops/data')->__(
+ 'Collect at airport, train station or travel agency'
+ )
+ ),
+ array(
+ 'value' => self::TRANSPORTER,
+ 'label' => Mage::helper('ops/data')->__(
+ 'Transporter (La Poste, UPS...)'
+ )
+ ),
+ array(
+ 'value' => self::DOWNLOAD,
+ 'label' => Mage::helper('ops/data')->__('Download')
+ )
+ );
+ }
+
+ public function getValidValues()
+ {
+ return array(
+ self::PICK_UP_AT_MERCHANT,
+ self::COLLECTION_POINT,
+ self::COLLECT_AT_AIRPORT,
+ self::TRANSPORTER,
+ self::DOWNLOAD
+ );
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Mode.php b/app/code/community/Netresearch/OPS/Model/Source/Mode.php
new file mode 100644
index 0000000..f1819d2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Mode.php
@@ -0,0 +1,31 @@
+ self::TEST, 'label' => Mage::helper('ops')->__(self::TEST)),
+ array('value' => self::PROD, 'label' => Mage::helper('ops')->__(self::PROD)),
+ array('value' => self::CUSTOM, 'label' => Mage::helper('ops')->__(self::CUSTOM)),
+ );
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/OrderReference.php b/app/code/community/Netresearch/OPS/Model/Source/OrderReference.php
new file mode 100644
index 0000000..6eac41e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/OrderReference.php
@@ -0,0 +1,50 @@
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID,
+ 'label' => Mage::helper('ops')->__('quote id')
+ ),
+ array(
+ 'value' => Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID,
+ 'label' => Mage::helper('ops')->__('order id')
+ ),
+ );
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Source/PaymentAction.php b/app/code/community/Netresearch/OPS/Model/Source/PaymentAction.php
new file mode 100644
index 0000000..5275376
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/PaymentAction.php
@@ -0,0 +1,50 @@
+ Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE,
+ 'label' => Mage::helper('ops')->__('Authorization')
+ ),
+ array(
+ 'value' => Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE,
+ 'label' => Mage::helper('ops')->__('Direct Sale')
+ ),
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Pmlist.php b/app/code/community/Netresearch/OPS/Model/Source/Pmlist.php
new file mode 100644
index 0000000..831fdd1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Pmlist.php
@@ -0,0 +1,54 @@
+ Netresearch_OPS_Model_Payment_Abstract::PMLIST_HORIZONTAL_LEFT,
+ 'label' => Mage::helper('ops')->__('Horizontally grouped logo with group name on left')
+ ),
+ array(
+ 'value' => Netresearch_OPS_Model_Payment_Abstract::PMLIST_HORIZONTAL,
+ 'label' => Mage::helper('ops')->__('Horizontally grouped logo with no group name')
+ ),
+ array(
+ 'value' => Netresearch_OPS_Model_Payment_Abstract::PMLIST_VERTICAL,
+ 'label' => Mage::helper('ops')->__('Verical list')
+ ),
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/Template.php b/app/code/community/Netresearch/OPS/Model/Source/Template.php
new file mode 100644
index 0000000..e163fcf
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/Template.php
@@ -0,0 +1,58 @@
+ Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_REDIRECT,
+ 'label' => Mage::helper('ops')->__('Ingenico ePayments - Redirect mode')
+ ),
+ array(
+ 'value' => Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_MAGENTO_INTERNAL,
+ 'label' => Mage::helper('ops')->__('Magento - internal shop template')
+ ),
+ array(
+ 'value' => Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_IFRAME,
+ 'label' => Mage::helper('ops')->__('Ingenico ePayments - iFrame mode')
+ ),
+ array(
+ 'value' => Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_TEMPLATE,
+ 'label' => Mage::helper('ops')->__('Ingenico ePayments - Dynamic template')
+ )
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Source/TemplateType.php b/app/code/community/Netresearch/OPS/Model/Source/TemplateType.php
new file mode 100644
index 0000000..193a4b2
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Source/TemplateType.php
@@ -0,0 +1,23 @@
+ self::URL, 'label' => Mage::helper('ops')->__(self::URL)),
+ array('value' => self::ID, 'label' => Mage::helper('ops')->__(self::ID))
+ );
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Status.php b/app/code/community/Netresearch/OPS/Model/Status.php
new file mode 100644
index 0000000..3df149c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Status.php
@@ -0,0 +1,301 @@
+
+ */
+?>
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Status_Update
+{
+
+ /** @var Netresearch_OPS_Model_Api_DirectLink $directLinkApi */
+ protected $directLinkApi = null;
+
+ protected $order = null;
+
+ protected $requestParams = array();
+
+ /** @var Netresearch_OPS_Model_Config $opsConfig */
+ protected $opsConfig = null;
+
+ protected $opsResponse = array();
+
+ protected $paymentHelper = null;
+
+ protected $directLinkHelper = null;
+
+ protected $messageContainer = null;
+
+ protected $dataHelper = null;
+
+ /**
+ * @param null $dataHelper
+ */
+ public function setDataHelper($dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Data
+ */
+ public function getDataHelper()
+ {
+ if (null == $this->dataHelper) {
+ $this->dataHelper = Mage::helper('ops/data');
+ }
+
+ return $this->dataHelper;
+ }
+ /**
+ * @param Mage_Core_Model_Session_Abstract $messageContainer
+ */
+ public function setMessageContainer(Mage_Core_Model_Session_Abstract $messageContainer)
+ {
+ $this->messageContainer = $messageContainer;
+ }
+
+ /**
+ * @return Mage_Core_Model_Session_Abstract
+ */
+ public function getMessageContainer()
+ {
+ if (null == $this->messageContainer) {
+ $this->messageContainer = Mage::getSingleton('adminhtml/session');
+ }
+ return $this->messageContainer;
+ }
+
+ /**
+ * @param Netresearch_OPS_Model_Config $opsConfig
+ */
+ public function setOpsConfig(Netresearch_OPS_Model_Config $opsConfig)
+ {
+ $this->opsConfig = $opsConfig;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Config
+ */
+ public function getOpsConfig()
+ {
+ if (null === $this->opsConfig) {
+ $this->opsConfig = Mage::getModel('ops/config');
+ }
+ return $this->opsConfig;
+ }
+
+ /**
+ * @param array $requestParams
+ */
+ public function setRequestParams($requestParams)
+ {
+ $this->requestParams = $requestParams;
+ }
+
+ /**
+ * @return array
+ */
+ public function getRequestParams()
+ {
+ return $this->requestParams;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Order $orderHelper
+ */
+ public function setOrderHelper(Netresearch_OPS_Helper_Order $orderHelper)
+ {
+ $this->orderHelper = $orderHelper;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Order
+ */
+ public function getOrderHelper()
+ {
+ if (null == $this->orderHelper) {
+ $this->orderHelper = Mage::helper('ops/order');
+ }
+
+ return $this->orderHelper;
+ }
+
+ /**
+ * @param array $opsResponse
+ */
+ public function setOpsResponse($opsResponse)
+ {
+ $this->opsResponse = $opsResponse;
+ }
+
+ /**
+ * @return array
+ */
+ public function getOpsResponse()
+ {
+ return $this->opsResponse;
+ }
+
+ /** @var Netresearch_OPS_Helper_Order $orderHelper */
+ protected $orderHelper = null;
+
+ /**
+ * @param Netresearch_OPS_Model_Api_DirectLink $directLinkApi
+ */
+ public function setDirectLinkApi(Netresearch_OPS_Model_Api_DirectLink $directLinkApi)
+ {
+ $this->directLinkApi = $directLinkApi;
+ }
+
+ /**
+ * @return Netresearch_OPS_Model_Api_DirectLink
+ */
+ public function getDirectLinkApi()
+ {
+ if (null === $this->directLinkApi) {
+ $this->directLinkApi = Mage::getModel('ops/api_directlink');
+ }
+ return $this->directLinkApi;
+ }
+
+ /**
+ * @param Mage_Sales_Model_Order $order
+ */
+ public function setOrder(Mage_Sales_Model_Order $order)
+ {
+ $this->order = $order;
+ }
+
+ /**
+ * @return Mage_Sales_Model_Order
+ */
+ public function getOrder()
+ {
+ return $this->order;
+ }
+
+ public function updateStatusFor(Mage_Sales_Model_Order $order)
+ {
+ if (false === ($order->getPayment()->getMethodInstance() instanceof Netresearch_OPS_Model_Payment_Abstract)) {
+ return $this;
+ }
+ $this->setOrder($order);
+ $this->buildParams($order->getPayment());
+
+ try {
+ $this->performRequest();
+ $this->updatePaymentStatus();
+ } catch (Mage_Core_Exception $e) {
+ $this->getMessageContainer()->addError($e->getMessage());
+ }
+ return $this;
+ }
+
+ protected function buildParams(Mage_Sales_Model_Order_Payment $payment)
+ {
+ // use PAYID if possible
+ if (0 < strlen(trim($payment->getAdditionalInformation('paymentId')))) {
+ $this->requestParams['PAYID'] = $payment->getAdditionalInformation('paymentId');
+
+ } else {
+ $useOrderId = true;
+ if ($this->canNotUseOrderId($payment)
+ ) {
+ $useOrderId = false;
+ }
+ $this->requestParams['ORDERID'] = $this->getOrderHelper()->getOpsOrderId($this->getOrder(), $useOrderId);
+ }
+ $this->addPayIdSub($payment);
+
+
+ return $this;
+ }
+
+ protected function performRequest()
+ {
+ $storeId = $this->getOrder()->getStoreId();
+ $url = $this->getOpsConfig()->getDirectLinkMaintenanceApiPath($storeId);
+ try {
+ $this->opsResponse = $this->getDirectLinkApi()->performRequest($this->getRequestParams(), $url, $storeId);
+ } catch (Mage_Core_Exception $e) {
+ $this->getMessageContainer()->addError($this->getDataHelper()->__($e->getMessage()));
+ return $this;
+ }
+ $this->opsResponse = array_change_key_case($this->opsResponse, CASE_UPPER);
+ // in further processing the amount is sometimes in upper and sometimes in lower case :(
+ if (array_key_exists('AMOUNT', $this->opsResponse)) {
+ $this->opsResponse['amount'] = $this->opsResponse['AMOUNT'];
+ }
+
+
+ return $this;
+ }
+
+ protected function updatePaymentStatus()
+ {
+ if (!array_key_exists('STATUS', $this->getOpsResponse())
+ || $this->opsResponse['STATUS'] == $this->getOrder()->getPayment()->getAdditionalInformation('status')
+ ) {
+ $this->getMessageContainer()->addNotice($this->getDataHelper()->__('No update available from Ingenico ePayments.'));
+ return $this;
+ }
+
+ if (false != strlen(trim($this->getOrder()->getPayment()->getAdditionalInformation('paymentId')))) {
+ Mage::getModel('ops/response_handler')->processResponse(
+ $this->getOpsResponse(),
+ $this->getOrder()->getPayment()->getMethodInstance()
+ );
+ } else {
+ // simulate initial request
+ $this->getPaymentHelper()->applyStateForOrder($this->getOrder(), $this->getOpsResponse());
+ }
+
+ $this->getPaymentHelper()->saveOpsStatusToPayment($this->getOrder()->getPayment(), $this->getOpsResponse());
+ $this->getMessageContainer()->addSuccess($this->getDataHelper()->__('Ingenico ePayments status successfully updated'));
+
+ return $this;
+ }
+
+ public function getPaymentHelper()
+ {
+ if (null == $this->paymentHelper) {
+ $this->paymentHelper = Mage::helper('ops/payment');
+ }
+
+ return $this->paymentHelper;
+ }
+
+ public function setPaymentHelper(Netresearch_OPS_Helper_Payment $paymentHelper)
+ {
+ $this->paymentHelper = $paymentHelper;
+ }
+
+ public function getDirectLinkHelper()
+ {
+ if (null == $this->directLinkHelper) {
+ $this->directLinkHelper = Mage::helper('ops/directlink');
+ }
+
+ return $this->directLinkHelper;
+ }
+
+ public function setDirectLinkHelper(Netresearch_OPS_Helper_Directlink $directLinkHelper)
+ {
+ $this->directLinkHelper = $directLinkHelper;
+ }
+
+ /**
+ * @param Mage_Sales_Model_Order_Payment $payment
+ * @return $this
+ */
+ protected function addPayIdSub(Mage_Sales_Model_Order_Payment $payment)
+ {
+ $lastTransaction = $payment->getLastTransId();
+ $lastTransactionParts = explode('/', $lastTransaction);
+ if ($lastTransaction && count($lastTransactionParts)>1) {
+ $this->requestParams['PAYIDSUB'] = $lastTransactionParts[1];
+ }
+ return $this;
+ }
+
+ protected function canNotUseOrderId(Mage_Sales_Model_Order_Payment $payment)
+ {
+ $methodInstance = $payment->getMethodInstance();
+
+ return ($methodInstance instanceof Netresearch_OPS_Model_Payment_Kwixo_Abstract)
+ || ($methodInstance instanceof Netresearch_OPS_Model_Payment_DirectDebit)
+ || ($methodInstance instanceof Netresearch_OPS_Model_Payment_Cc
+ && $methodInstance->hasBrandAliasInterfaceSupport($payment));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Subscription/Manager.php b/app/code/community/Netresearch/OPS/Model/Subscription/Manager.php
new file mode 100644
index 0000000..3c55c73
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Subscription/Manager.php
@@ -0,0 +1,306 @@
+
+ */
+?>
+dataHelper) {
+ $this->dataHelper = Mage::helper('ops');
+ }
+
+ return $this->dataHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Data $dataHelper
+ *
+ * @returns $this
+ */
+ public function setDataHelper($dataHelper)
+ {
+ $this->dataHelper = $dataHelper;
+
+ return $this;
+ }
+
+ /**
+ * @return Netresearch_OPS_Helper_Payment
+ */
+ public function getPaymentHelper()
+ {
+ if (null === $this->paymentHelper) {
+ $this->paymentHelper = Mage::helper('ops/payment');
+ }
+
+ return $this->paymentHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Payment $paymentHelper
+ *
+ * @returns $this
+ */
+ public function setPaymentHelper($paymentHelper)
+ {
+ $this->paymentHelper = $paymentHelper;
+
+ return $this;
+ }
+
+
+ /**
+ * @return Netresearch_OPS_Helper_Subscription
+ */
+ public function getSubscriptionHelper()
+ {
+ if (null === $this->subscriptionHelper) {
+ $this->subscriptionHelper = Mage::helper('ops/subscription');
+ }
+
+ return $this->subscriptionHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Subscription $subscriptionHelper
+ *
+ * @returns $this
+ */
+ public function setSubscriptionHelper($subscriptionHelper)
+ {
+ $this->subscriptionHelper = $subscriptionHelper;
+
+ return $this;
+ }
+
+
+ /**
+ * Process request from Ingenico ePayments automatic subscription payments and initial creations
+ *
+ *
+ * @param mixed[] $responseParams
+ * @param Mage_Sales_Model_Recurring_Profile $profile - only has to be provided during the initial setup of
+ * the subscription
+ * @param Mage_Sales_Model_Order $order
+ *
+ *
+ * @return Mage_Sales_Model_Order | false
+ */
+ public function processSubscriptionFeedback($responseParams, $profile = null, $order = null)
+ {
+ $createOrder = true;
+ $feedbackType = false;
+ $orderId = $responseParams['orderID'];
+ if (!is_array($responseParams)) {
+ Mage::throwException($this->getDataHelper()->__('No response array provided'));
+ }
+
+ if (null === $profile) {
+ $profile = $this->getSubscriptionHelper()->getProfileForSubscription($orderId);
+ }
+
+ if (array_key_exists('creation_status', $responseParams)) {
+ switch ($responseParams['creation_status']) {
+ case self::CREATION_SUCCEEDED:
+ $profile->setState(Mage_Sales_Model_Recurring_Profile::STATE_ACTIVE);
+ break;
+ default:
+ $profile->setState(Mage_Sales_Model_Recurring_Profile::STATE_UNKNOWN);
+ break;
+ }
+ $profile->setReferenceId($responseParams['subscription_id']);
+ $profile->setProfileVendorInfo(serialize($responseParams));
+ $profile->setAdditionalInfo(serialize($responseParams));
+ $feedbackType = Mage_Sales_Model_Recurring_Profile::PAYMENT_TYPE_INITIAL;
+ // do not create an order since it already got created
+ $createOrder = false;
+ }
+
+ if (!$feedbackType) {
+ if ($this->getSubscriptionHelper()->isTrialFeedback($orderId)) {
+ $feedbackType = Mage_Sales_Model_Recurring_Profile::PAYMENT_TYPE_TRIAL;
+ } else {
+ $feedbackType = Mage_Sales_Model_Recurring_Profile::PAYMENT_TYPE_REGULAR;
+ }
+ }
+
+ if ($createOrder && null === $order) {
+ return $this->createOrderFromFeedback($profile, $feedbackType, $responseParams);
+ } elseif (null != $order) {
+ return $this->processPaymentFeedback($responseParams, $profile, $order);
+ }
+
+ return $createOrder;
+ }
+
+ /**
+ * Creates an order for the given item type using the recurring profile model
+ *
+ * @see Mage_Sales_Model_Recurring_Profile::createOrder()
+ *
+ * @param Mage_Sales_Model_Recurring_Profile $profile
+ * @param string $feedbackType - @see Mage_Sales_Model_Recurring_Profile payment types
+ * @param string[] $responseParams
+ *
+ * @return Mage_Sales_Model_Order the created order
+ */
+ protected function createOrderFromFeedback($profile, $feedbackType, $responseParams)
+ {
+ // Just set the payment type, the recurring profile sets the correct amounts automatically
+ $orderItem = new Varien_Object();
+ $orderItem->setPaymentType($feedbackType);
+ if ($feedbackType == Mage_Sales_Model_Recurring_Profile::PAYMENT_TYPE_TRIAL) {
+ $orderItemInfo = new Varien_Object($profile->getOrderItemInfo());
+ $calculator = Mage::getModel('tax/calculation');
+ $tax = $calculator->calcTaxAmount(
+ $profile->getTrialBillingAmount(),
+ $orderItemInfo->getTaxPercent(), true, true
+ );
+ $price = $profile->getTrialBillingAmount() - $tax;
+ $orderItem->setPrice($price)
+ ->setTaxAmount($tax);
+ }
+
+ $order = $profile->createOrder($orderItem);
+ $billingAddressInfo = $profile->getBillingAddressInfo();
+ $order->setQuoteId($billingAddressInfo['quote_id']);
+
+ $order = $this->processPaymentFeedback($responseParams, $profile, $order);
+
+ return $order;
+ }
+
+ /**
+ * Creates an order for the initial fee. It also fixes the missing data for the order item, so a capture can be
+ * properly processed and an invoice created.
+ *
+ * @param Mage_Payment_Model_Recurring_Profile $profile
+ *
+ * @return Mage_Sales_Model_Order
+ */
+ public function createInitialOrder(Mage_Payment_Model_Recurring_Profile $profile)
+ {
+ /** @var $profile Mage_Sales_Model_Recurring_Profile */
+ $item = new Varien_Object();
+ $orderItemInfo = new Varien_Object($profile->getOrderItemInfo());
+ $calculator = Mage::getModel('tax/calculation');
+ $taxAmount = $calculator->calcTaxAmount(
+ $profile->getInitAmount(), $orderItemInfo->getTaxPercent(), true,
+ true
+ );
+ $amountWithoutTax = $profile->getInitAmount() - $taxAmount;
+ $item->setPaymentType(Mage_Sales_Model_Recurring_Profile::PAYMENT_TYPE_INITIAL)
+ ->setPrice($amountWithoutTax)
+ ->setTaxAmount($taxAmount);
+
+ $order = $profile->createOrder($item);
+ $order->setQuoteId($profile->getQuote()->getId());
+
+ /** @var $item Mage_Sales_Model_Order_Item */
+ list($item) = $order->getAllItems();
+ $item->setData('base_discount_amount', 0)
+ ->setData('base_discount_calculation_price', $profile->getInitAmount())
+ ->setData('base_hidden_tax_amount', 0)
+ ->setData('base_original_price', $profile->getInitAmount())
+ ->setData('base_price_incl_tax', $profile->getInitAmount())
+ ->setData('base_row_tax', $taxAmount)
+ ->setData('base_row_total_incl_tax', $profile->getInitAmount())
+ ->setData('base_tax_amount', $taxAmount)
+ ->setData('base_taxable_amount', $profile->getInitAmount())
+ ->setData('calculation_price', $amountWithoutTax)
+ ->setData('converted_price', $amountWithoutTax)
+ ->setData('discount_calculation_price', $profile->getInitAmount())
+ ->setData('price_incl_tax', $profile->getInitAmount())
+ ->setData('row_tax', $taxAmount)
+ ->setData('row_total_incl_tax', $profile->getInitAmount())
+ ->setData('taxable_amount', $profile->getInitAmount());
+
+ $itemData = $item->getData();
+ $item->addData($profile->getOrderItemInfo());
+ $item->addData($itemData);
+ $item->setId(null);
+ $order->getItemsCollection()->removeItemByKey(0);
+ $order->addItem($item);
+ $order->save();
+
+ return $order;
+ }
+
+ /**
+ * Takes the responseparameters and applies the corresponding action (capture/authorize) on the order payment.
+ * Also updates the Ingenico ePayments information on the payment.
+ *
+ * @param string[] $responseParams
+ * @param Mage_Sales_Model_Recurring_Profile $profile
+ * @param Mage_Sales_Model_Order $order
+ *
+ * @return Mage_Sales_Model_Order $order - updated order
+ */
+ protected function processPaymentFeedback($responseParams, $profile, $order)
+ {
+ $payment = $order->getPayment();
+ foreach ($responseParams as $key => $value) {
+ $payment->setTransactionAdditionalInfo($key, $value);
+ }
+ $payment->setTransactionId($responseParams['PAYID'])
+ ->setCurrencyCode($responseParams['currency'])
+ ->setIsTransactionClosed(0);
+ $order->save();
+ $profile->addOrderRelation($order->getId());
+ if ($this->getPaymentHelper()->isPaymentAuthorizeType($responseParams['STATUS'])) {
+ $payment->registerAuthorizationNotification($responseParams['amount']);
+ } elseif ($this->getPaymentHelper()->isPaymentCaptureType($responseParams['STATUS'])) {
+ $payment->registerCaptureNotification($responseParams['amount']);
+ } elseif ($responseParams['STATUS']
+ == Netresearch_OPS_Model_Payment_Abstract::OPS_WAITING_FOR_IDENTIFICATION
+ ) {
+ // handle 3ds payment - only relevant for initial order creation
+ $payment->setIsTransactionPending(1);
+ $payment->registerCaptureNotification($responseParams['amount'], true);
+ }
+ $order->save();
+ $this->getPaymentHelper()->applyStateForOrder($order, $responseParams);
+
+ return $order;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Encoding.php b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Encoding.php
new file mode 100644
index 0000000..6ccc221
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Encoding.php
@@ -0,0 +1,46 @@
+
+ */
+class Netresearch_OPS_Model_System_Config_Backend_Encoding
+{
+
+ /**
+ * Options getter
+ *
+ * @return array
+ */
+ public function toOptionArray()
+ {
+ return array(
+ array('value' => 'utf-8', 'label' => Mage::helper('ops')->__('UTF-8')),
+ array('value' => 'other', 'label' => Mage::helper('ops')->__('Other')),
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Flex/Methods.php b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Flex/Methods.php
new file mode 100644
index 0000000..05d8710
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Flex/Methods.php
@@ -0,0 +1,67 @@
+
+ */
+
+class Netresearch_OPS_Model_System_Config_Backend_Flex_Methods
+ extends Mage_Adminhtml_Model_System_Config_Backend_Serialized_Array
+{
+ protected $_eventPrefix = 'ops_config_backend_flex_methods';
+
+ /**
+ * additional validation for unique brands
+ *
+ * @override
+ * @throws Mage_Core_Exception if the brands are not unique -> validation failed
+ * @return Netresearch_Ops_Model_System_Config_Backend_Intersolve_Brands
+ */
+ public function save()
+ {
+ $methods = $this->getValue();
+ if (is_array($methods) && count($methods) > 1) {
+ $alreadyProcessedMethods = array();
+ foreach ($methods as $method) {
+
+ if (is_array($method)
+ && array_key_exists('pm', $method)
+ && array_key_exists('brand', $method)
+ ) {
+ if (empty($method['title'])||empty($method['pm'])) {
+ Mage::throwException("Can not save empty title or PM fields");
+ }
+
+
+ if (in_array($method['pm'].'_'.$method['brand'], $alreadyProcessedMethods)) {
+ Mage::throwException("PM and Brand combination must be unique");
+ }
+ $alreadyProcessedMethods[] = $method['pm'].'_'.$method['brand'];
+ }
+ }
+ }
+ return parent::save();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/System/Config/Backend/HashMethods.php b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/HashMethods.php
new file mode 100644
index 0000000..c9ff3eb
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/HashMethods.php
@@ -0,0 +1,48 @@
+
+ */
+
+class Netresearch_Ops_Model_System_Config_Backend_HashMethods
+ extends Mage_Adminhtml_Model_System_Config_Backend_Serialized_Array
+{
+ /**
+ * Options getter
+ *
+ * @return array
+ */
+ public function toOptionArray()
+ {
+ return array(
+ array('value' => 'sha1', 'label'=>Mage::helper('ops')->__('SHA-1')),
+ array('value' => 'sha256', 'label'=>Mage::helper('ops')->__('SHA-256')),
+ array('value' => 'sha512', 'label'=>Mage::helper('ops')->__('SHA-512'))
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Intersolve/Brands.php b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Intersolve/Brands.php
new file mode 100644
index 0000000..6d3ed3b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/Intersolve/Brands.php
@@ -0,0 +1,60 @@
+
+ */
+
+class Netresearch_Ops_Model_System_Config_Backend_Intersolve_Brands
+ extends Mage_Adminhtml_Model_System_Config_Backend_Serialized_Array
+{
+ protected $_eventPrefix = 'ops_config_backend_intersolve_brands';
+
+ /**
+ * additional validation for unique brands
+ *
+ * @override
+ * @throws Mage_Core_Exception if the brands are not unique -> validation failed
+ * @return Netresearch_Ops_Model_System_Config_Backend_Intersolve_Brands
+ */
+ public function save()
+ {
+ $brands = $this->getValue();
+ if (is_array($brands) && count($brands) > 1) {
+ $alreadyProcessedBrands = array();
+ foreach ($brands as $brand) {
+ if (is_array($brand) && array_key_exists('brand', $brand)) {
+ if (in_array($brand['brand'], $alreadyProcessedBrands)) {
+ Mage::throwException("Brands must be unique");
+ }
+ $alreadyProcessedBrands[] = $brand['brand'];
+ }
+ }
+ }
+ return parent::save();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/System/Config/Backend/PaymentLogo.php b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/PaymentLogo.php
new file mode 100644
index 0000000..b5ce370
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/System/Config/Backend/PaymentLogo.php
@@ -0,0 +1,47 @@
+
+ */
+class Netresearch_Ops_Model_System_Config_Backend_PaymentLogo
+{
+
+ /**
+ * Options getter
+ *
+ * @return array
+ */
+ public function toOptionArray()
+ {
+ return array(
+ array('value' => 'left', 'label' => Mage::helper('ops')->__('Left')),
+ array('value' => 'right', 'label' => Mage::helper('ops')->__('Right')),
+ array('value' => 'hidden', 'label' => Mage::helper('ops')->__('Non Visible')),
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Model/System/Config/Mode.php b/app/code/community/Netresearch/OPS/Model/System/Config/Mode.php
new file mode 100644
index 0000000..ae3cbad
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/System/Config/Mode.php
@@ -0,0 +1,40 @@
+getValue() != Netresearch_OPS_Model_Source_Mode::CUSTOM && $this->isValueChanged()) {
+ $xmlConfig = Mage::getConfig()->loadModulesConfiguration('config.xml');
+ foreach ($this->getUrlPaths() as $path) {
+ $default = $xmlConfig->getNode('default/'.$path);
+ $newValue = preg_replace('/\/ncol\/\w+/', '/ncol/'.$this->getValue(), $default);
+ Mage::getConfig()->saveConfig($path, $newValue, $this->getScope(), $this->getScopeId());
+
+ }
+ }
+
+ return parent::_afterSave();
+ }
+
+ protected function getUrlPaths()
+ {
+ return array(
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'ops_gateway',
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'ops_alias_gateway',
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'frontend_gateway',
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'directlink_gateway',
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'directlink_gateway_order',
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'directlink_maintenance_api'
+ );
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/System/Config/Template.php b/app/code/community/Netresearch/OPS/Model/System/Config/Template.php
new file mode 100644
index 0000000..72613be
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/System/Config/Template.php
@@ -0,0 +1,63 @@
+getConfig()->getPayPageTemplate();
+ $paypageInfo = Mage::helper('ops')->__(
+ 'With this setting the customer will be redirected to the Ingenico ePayments paypage with the look and feel of your shop. ' .
+ ' The template used can be seen here: '
+ );
+ $paypageInfo .= "" . $paypageUrl . " ";
+
+ $result = "
";
+ $result .= "
+ ";
+
+ return $result;
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Model/Validator/CompositeInterface.php b/app/code/community/Netresearch/OPS/Model/Validator/CompositeInterface.php
new file mode 100644
index 0000000..46b0672
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Validator/CompositeInterface.php
@@ -0,0 +1,12 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+ interface Netresearch_OPS_Model_Validator_CompositeInterface
+{
+ public function addValidator(Zend_Validate_Interface $validator);
+
+ }
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Validator/Kwixo/Shipping/Setting.php b/app/code/community/Netresearch/OPS/Model/Validator/Kwixo/Shipping/Setting.php
new file mode 100644
index 0000000..02e3ba7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Validator/Kwixo/Shipping/Setting.php
@@ -0,0 +1,95 @@
+
+ * @category Netresearch
+ * @package ${MODULENAME}
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Validator_Kwixo_Shipping_Setting
+{
+
+ protected $messages = array();
+
+ public function isValid(array $data)
+ {
+ $result = false;
+ $methodCodes = array_keys(Mage::getSingleton('shipping/config')->getAllCarriers());
+ if (0 < count($data)) {
+ $result = true;
+ foreach ($data as $code => $row) {
+ if (!in_array($code, $methodCodes)) continue;
+ $result = $this->validateRow($code, $row) && $result;
+ }
+ }
+ return $result;
+ }
+
+ public function getMessages()
+ {
+ return $this->messages;
+ }
+
+ protected function validateRow($code, $row)
+ {
+ $shippingTypeResult = $this->validateShippingType($code, $row);
+ $shippingSpeedResult = $this->validateShippingSpeed($code, $row);
+ $shippingDetailsResult = $this->validateShippingDetails($code, $row);
+ return $shippingTypeResult && $shippingSpeedResult && $shippingDetailsResult;
+ }
+
+ private function validateShippingType($code, $row)
+ {
+ $validValues = Mage::getModel('ops/source_kwixo_shipMethodType')
+ ->getValidValues();
+
+ if (array_key_exists('kwixo_shipping_type', $row)
+ && Zend_Validate::is(
+ $row['kwixo_shipping_type'], 'Digits'
+ )
+ && 0 < $row['kwixo_shipping_type']
+ && in_array((int)$row['kwixo_shipping_type'], $validValues)
+
+ ) {
+ return true;
+ }
+ $this->messages[$code]['kwixo_shipping_type_error']
+ = 'invalid shipping type provided';
+
+ return false;
+ }
+
+ protected function validateShippingSpeed($code, $row)
+ {
+ if (array_key_exists('kwixo_shipping_speed', $row)
+ && Zend_Validate::is(
+ $row['kwixo_shipping_speed'], 'Digits'
+ )
+ && 0 < $row['kwixo_shipping_speed']
+ ) {
+ return true;
+ }
+ $this->messages[$code]['kwixo_shipping_speed_error']
+ = 'invalid shipping speed provided';
+
+ return false;
+ }
+
+ protected function validateShippingDetails($code, $row)
+ {
+ if (array_key_exists('kwixo_shipping_details', $row)
+ && Zend_Validate::is(
+ $row['kwixo_shipping_details'], 'StringLength',
+ array('min' => 0, 'max' => 50)
+ )
+ ) {
+ return true;
+ }
+ $this->messages[$code]['kwixo_shipping_details_error']
+ = 'invalid shipping details provided';
+
+ return false;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Factory.php b/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Factory.php
new file mode 100644
index 0000000..9c2cf5c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Factory.php
@@ -0,0 +1,63 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Model_Validator_Parameter_Factory extends Mage_Core_Model_Abstract
+{
+
+ const TYPE_REQUEST_PARAMS_VALIDATION = 'request_validation';
+
+ /**
+ * @var Netresearch_OPS_Model_Validator_Parameter_Validator
+ */
+ protected $validator = null;
+
+ /**
+ * @var Netresearch_OPS_Model_Config
+ */
+ protected $config = null;
+
+ /**
+ * sets the necessary dependencies for this class
+ */
+ public function _construct()
+ {
+ parent::_construct();
+ $this->validator = Mage::getModel('ops/validator_parameter_validator');
+ $this->config = Mage::getModel('ops/config');
+ }
+
+ /**
+ * creates validator for given type
+ *
+ * @param $type - the requested type
+ *
+ * @return Netresearch_OPS_Model_Validator_Parameter_Validator
+ */
+ public function getValidatorFor($type)
+ {
+ if ($type == self::TYPE_REQUEST_PARAMS_VALIDATION) {
+ $this->createRequestParamsValidator();
+ }
+
+ return $this->validator;
+ }
+
+ /**
+ * configures the validator for validation of the request parameter
+ *
+ * @return $this
+ */
+ protected function createRequestParamsValidator()
+ {
+ $validator = Mage::getModel('ops/validator_parameter_length');
+ $validator->setFieldLengths($this->config->getParameterLengths());
+ $this->validator->addValidator($validator);
+
+ return $this;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Length.php b/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Length.php
new file mode 100644
index 0000000..0c78b51
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Length.php
@@ -0,0 +1,96 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Validator_Parameter_Length implements Zend_Validate_Interface
+{
+
+ protected $messages = array();
+
+ protected $fieldLengths = array();
+
+ /**
+ * @param array $fieldLengths - the fieldLengths which are assumed as valid
+ */
+ public function setFieldLengths(array $fieldLengths)
+ {
+ $this->fieldLengths = $fieldLengths;
+ }
+
+ /**
+ * gets the current configuration of the field lengths
+ *
+ * @return array
+ */
+ public function getFieldLengths()
+ {
+ return $this->fieldLengths;
+ }
+
+ /**
+ * checks if the given data matching the given string lengths
+ *
+ * @param mixed $dataToValidate
+ *
+ * @return bool
+ */
+ public function isValid($dataToValidate)
+ {
+ $validationResult = true;
+ if (is_array($dataToValidate) && 0 < count($dataToValidate)) {
+ foreach ($dataToValidate as $key => $value) {
+ $maxLength = $this->getFieldLengthFor($key);
+ if ($value === null) {
+ $value = '';
+ }
+ if (0 < $maxLength) {
+ if (
+ false == Zend_Validate::is(
+ utf8_encode($value),
+ 'StringLength',
+ array('max' => $maxLength, 'encoding' => 'utf-8')
+ )
+ ) {
+ $this->messages[$key] = Mage::helper('ops/data')->__('Value exceeds %d characters', $maxLength);
+ $validationResult = false;
+ }
+ }
+ }
+ }
+
+ return $validationResult;
+ }
+
+ /**
+ * gets the messages
+ *
+ * @return array
+ */
+ public function getMessages()
+ {
+ return $this->messages;
+ }
+
+ /**
+ * gets the valid string length for a given value
+ *
+ * @param $paramName
+ *
+ * @return int -1 if not found, the corresponding value otherwise
+ */
+ protected function getFieldLengthFor($paramName)
+ {
+ $value = -1;
+ if (array_key_exists($paramName, $this->fieldLengths)) {
+ $value = $this->fieldLengths[$paramName];
+ }
+
+ return $value;
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Validator.php b/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Validator.php
new file mode 100644
index 0000000..f8a8959
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Model/Validator/Parameter/Validator.php
@@ -0,0 +1,56 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Model_Validator_Parameter_Validator
+ implements Netresearch_OPS_Model_Validator_CompositeInterface, Zend_Validate_Interface
+{
+
+ protected $validators = array();
+
+ protected $messages = array();
+
+ /**
+ * adds a validator
+ *
+ * @param Zend_Validate_Interface $validator
+ */
+ public function addValidator(Zend_Validate_Interface $validator)
+ {
+ $this->validators[] = $validator;
+ }
+
+ /**
+ * @param $dataToValidate
+ *
+ * @return bool - indicates whether the data are valid or not
+ */
+ public function isValid($dataToValidate)
+ {
+ $isValid = true;
+ foreach ($this->validators as $validator) {
+ /** @var Zend_Validate_Interface $validator */
+ $isValid = $isValid && $validator->isValid($dataToValidate);
+ if (false === $validator->isValid($dataToValidate)) {
+ $this->messages = array_merge($this->messages, $validator->getMessages());
+ }
+ }
+
+ return $isValid;
+ }
+
+ public function getMessages()
+ {
+ return $this->messages;
+ }
+
+ public function getValidators()
+ {
+ return $this->validators;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Customer/Renderer/StateTest.php b/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Customer/Renderer/StateTest.php
new file mode 100644
index 0000000..3ec5ed9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Customer/Renderer/StateTest.php
@@ -0,0 +1,23 @@
+setIndex('state');
+ $row = new Varien_Object();
+ $row->setData(array('state' => Netresearch_OPS_Model_Alias_State::ACTIVE));
+ $block = Mage::app()->getLayout()->getBlockSingleton(
+ 'ops/adminhtml_customer_renderer_state'
+ );
+ $block->setColumn($column);
+ $this->assertEquals(
+ Mage::helper('ops/data')->__(
+ Netresearch_OPS_Model_Alias_State::ACTIVE
+ ), $block->render($row)
+ );
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Kwixo/Shipping/EditTest.php b/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Kwixo/Shipping/EditTest.php
new file mode 100644
index 0000000..dc448fb
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Kwixo/Shipping/EditTest.php
@@ -0,0 +1,81 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Block_Adminhtml_Kwixo_Shipping_EditTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+
+ public function setUp()
+ {
+ $sessionMock = $this->getModelMock(
+ 'core/session', array('init', 'save', 'getSessionIdForHost')
+ );
+
+ $this->replaceByMock('model', 'core/session', $sessionMock);
+ }
+
+ public function testGetFormActionUrl()
+ {
+
+ $widgetContainer = new Mage_Adminhtml_Block_Widget_Form_Container();
+ $block
+ = new Netresearch_OPS_Block_Adminhtml_Kwixo_Shipping_Edit();
+ $this->assertEquals(
+ $widgetContainer->getUrl('adminhtml/kwixoshipping/save', array()),
+ $block->getFormActionUrl()
+ );
+ }
+
+ public function testGetShippingMethods()
+ {
+ $shippingConfigMock = $this->getModelMock(
+ 'shipping/config', array('getAllCarriers')
+ );
+ $shippingConfigMock->expects($this->any())
+ ->method('getAllCarriers')
+ ->will(
+ $this->returnValue(
+ array('dhl' => 'dhl', 'hermes' => 'hermes', 'ips' => 'ips')
+ )
+ );
+ $this->replaceByMock('model', 'shipping/config', $shippingConfigMock);
+
+ $block = new Netresearch_OPS_Block_Adminhtml_Kwixo_Shipping_Edit();
+ $result = $block->getShippingMethods();
+ $this->assertEquals(3, count($result));
+ $this->assertEquals($result[0]['code'], 'dhl');
+ $this->assertEquals($result[1]['code'], 'hermes');
+ $this->assertEquals($result[1]['label'], 'hermes');
+ $this->assertEquals($result[2]['code'], 'ips');
+ $this->assertEquals($result[2]['label'], 'ips');
+
+ $block->setData(
+ 'postData', array('dhl' => array('error' => 'sample error'))
+ );
+ $result = $block->getShippingMethods();
+ $this->assertEquals($result[0]['values']['error'], 'sample error');
+ }
+
+ public function testGetKwixoShippingTypes()
+ {
+ $block = new Netresearch_OPS_Block_Adminhtml_Kwixo_Shipping_Edit();
+ $expectedResult = Mage::getModel('ops/source_kwixo_shipMethodType')
+ ->toOptionArray();
+ $this->assertEquals($expectedResult, $block->getKwixoShippingTypes());
+ }
+
+
+ public function testGetFormKey()
+ {
+ $block = new Netresearch_OPS_Block_Adminhtml_Kwixo_Shipping_Edit();
+ $expectedResult = Mage::getSingleton('core/session')->getFormKey();
+ $this->assertEquals($expectedResult, $block->getFormKey());
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Sales/Order/Creditmemo/Totals/CheckboxTest.php b/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Sales/Order/Creditmemo/Totals/CheckboxTest.php
new file mode 100644
index 0000000..a359734
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Adminhtml/Sales/Order/Creditmemo/Totals/CheckboxTest.php
@@ -0,0 +1,11 @@
+getLayout()->getBlockSingleton('ops/adminhtml_sales_order_creditmemo_totals_checkbox');
+ $this->assertEquals('ops/sales/order/creditmemo/totals/checkbox.phtml', $block->getTemplate());
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Alias/ListTest.php b/app/code/community/Netresearch/OPS/Test/Block/Alias/ListTest.php
new file mode 100644
index 0000000..3828926
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Alias/ListTest.php
@@ -0,0 +1,77 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Test_Block_Alias_ListTest
+ *
+ * @author Thomas Birke
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Block_Alias_ListTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+ private $block;
+
+ public function setUp()
+ {
+ parent::setup();
+ $this->block = Mage::app()->getLayout()->getBlockSingleton('ops/alias_list');
+ }
+
+ public function testGetMethodName()
+ {
+ $this->assertEquals('', $this->block->getMethodName('something_stupid'));
+
+ Mage::app()->getStore()->setConfig('payment/ops_cc/title', 'OPS Credit Card');
+ $this->assertEquals(
+ 'OPS Credit Card',
+ $this->block->getMethodName('ops_cc')
+ );
+ }
+
+ public function testGetAliasDeleteUrl()
+ {
+// array('_secure' => Mage::app()->getFrontController()->getRequest()->isSecure());
+ $this->mockSessions();
+ $aliasId = 1;
+ // previous behaviour until OGNB-229: Mage::getUrl('ops/customer/deleteAlias/id/' . $aliasId)
+ $this->assertEquals(Mage::getUrl('ops/customer/deleteAlias/id/' . $aliasId), $this->block->getAliasDeleteUrl($aliasId));
+
+ // new since OGNB-229: passed aliasId as array param
+ $this->assertEquals(Mage::getUrl('ops/customer/deleteAlias/', array('id' => $aliasId)), $this->block->getAliasDeleteUrl($aliasId));
+
+ $_SERVER['HTTPS'] = 'on';
+ $this->assertEquals(
+ Mage::getUrl(
+ 'ops/customer/deleteAlias/',
+ array(
+ '_secure' => true,
+ 'id' => $aliasId)
+ ),
+ $this->block->getAliasDeleteUrl($aliasId)
+ );
+ }
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest.php b/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest.php
new file mode 100644
index 0000000..526aa25
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest.php
@@ -0,0 +1,75 @@
+
+ * @copyright 2016 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+
+/**
+ * Netresearch_OPS_Test_Block_Checkout_DeviceFingerprintingTest
+ *
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @author Christoph Aßmann
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+class Netresearch_OPS_Test_Block_Checkout_DeviceFingerprintingTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+ protected function setUp()
+ {
+ $sessionMock = $this->getModelMock('core/session', array('init'));
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+ }
+
+ /**
+ * @test
+ * @loadFixture
+ */
+ public function fingerPrintingEnabled()
+ {
+ /** @var Netresearch_OPS_Block_Checkout_DeviceFingerprinting $block */
+ $block = Mage::app()->getLayout()->createBlock('ops/checkout_deviceFingerprinting');
+
+ $html = $block->toHtml();
+ $this->assertNotEmpty($html);
+
+ $url = $block->getConsentUrl();
+ $this->assertContains('ops/device/', $url);
+ }
+
+ /**
+ * @test
+ * @loadFixture
+ */
+ public function fingerPrintingDisabled()
+ {
+ /** @var Netresearch_OPS_Block_Checkout_DeviceFingerprinting $block */
+ $block = Mage::app()->getLayout()->createBlock('ops/checkout_deviceFingerprinting');
+ $html = $block->toHtml();
+ $this->assertEmpty($html);
+
+ $url = $block->getConsentUrl();
+ $this->assertContains('ops/device/', $url);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingDisabled.yaml b/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingDisabled.yaml
new file mode 100644
index 0000000..0a0ea75
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingDisabled.yaml
@@ -0,0 +1,3 @@
+config:
+ default/dev/template/allow_symlink: 1
+ default/payment_services/ops/device_fingerprinting: 0
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingEnabled.yaml b/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingEnabled.yaml
new file mode 100644
index 0000000..abe96fc
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Checkout/DeviceFingerprintingTest/fixtures/fingerPrintingEnabled.yaml
@@ -0,0 +1,3 @@
+config:
+ default/dev/template/allow_symlink: 1
+ default/payment_services/ops/device_fingerprinting: 1
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/CcTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/CcTest.php
new file mode 100644
index 0000000..cfa06cf
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/CcTest.php
@@ -0,0 +1,459 @@
+_block = Mage::app()->getLayout()->getBlockSingleton('ops/form_cc');
+ $this->_block->setMethod(Mage::getModel('ops/payment_cc'));
+ $this->mockSessions();
+ }
+
+ public function testGetAliasBrands()
+ {
+
+ $aliasBrands = array(
+ 'American Express',
+ 'Diners Club',
+ 'MaestroUK',
+ 'MasterCard',
+ 'VISA',
+ );
+
+ $ccAliasInterfaceEnabledTypesMock = $this->getModelMock(
+ 'ops/source_cc_aliasInterfaceEnabledTypes', array('getAliasInterfaceCompatibleTypes')
+ );
+ $ccAliasInterfaceEnabledTypesMock->expects($this->any())
+ ->method('getAliasInterfaceCompatibleTypes')
+ ->will($this->returnValue($aliasBrands));
+ $this->replaceByMock('model', 'ops/source_cc_aliasInterfaceEnabledTypes', $ccAliasInterfaceEnabledTypesMock);
+ /** @var Netresearch_OPS_Block_Form_Cc $ccForm */
+ $ccForm = Mage::app()->getLayout()->getBlockSingleton('ops/form_cc');
+ $ccAliases = $ccForm->getAliasBrands();
+ $this->assertEquals($aliasBrands, $ccAliases);
+ }
+
+
+ public function testTemplate()
+ {
+ //Frontend case
+ $modelMock = $this->getModelMock('ops/config', array('isFrontendEnvironment'));
+ $modelMock->expects($this->any())
+ ->method('isFrontendEnvironment')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/config', $modelMock);
+ $ccForm = new Netresearch_OPS_Block_Form_Cc();
+ $this->assertEquals(Netresearch_OPS_Block_Form_Cc::FRONTEND_TEMPLATE, $ccForm->getTemplate());
+
+ //Backend case
+ $modelMock = $this->getModelMock('ops/config', array('isFrontendEnvironment'));
+ $modelMock->expects($this->any())
+ ->method('isFrontendEnvironment')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('model', 'ops/config', $modelMock);
+ $ccForm = new Netresearch_OPS_Block_Form_Cc();
+ $this->assertEquals(Netresearch_OPS_Block_Form_Cc::FRONTEND_TEMPLATE, $ccForm->getTemplate());
+ }
+
+ public function testGetCcBrands()
+ {
+ $blockMock = $this->getBlockMock('ops/form_cc', array('getMethod'));
+ $method = new Varien_Object();
+ $method->setCode('ops_cc');
+ $blockMock->expects($this->any())
+ ->method('getMethod')
+ ->will($this->returnValue($method));
+ $this->replaceByMock('block', 'ops/form_cc', $blockMock);
+
+
+ $this->assertInternalType('array', $blockMock->getCcBrands());
+ }
+
+ public function testIsAliasPMEnabled()
+ {
+ $model = Mage::getModel('ops/config');
+ $this->assertEquals(
+ $model->isAliasManagerEnabled('ops_cc'), $this->_block->isAliasPMEnabled()
+ );
+ }
+
+ public function testGetStoredAliasDataForCustomer()
+ {
+
+ $reflectionClass = new ReflectionClass(get_class($this->_block));
+ $method = $reflectionClass->getMethod("getStoredAliasDataForCustomer");
+ $method->setAccessible(true);
+ $this->assertNull($method->invoke($this->_block, 0, 'bla'));
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasForCustomer')
+ );
+ $blockMock->expects($this->once())
+ ->method('getStoredAliasForCustomer')
+ ->will($this->returnValue(array()));
+ $reflectionClass = new ReflectionClass(get_class($blockMock));
+ $method = $reflectionClass->getMethod("getStoredAliasDataForCustomer");
+ $method->setAccessible(true);
+ $this->assertNull($method->invoke($blockMock, 0, 'bla'));
+
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasForCustomer')
+ );
+ $blockMock->expects($this->once())
+ ->method('getStoredAliasForCustomer')
+ ->will($this->returnValue(array(0 => new Varien_Object(array('bla' => 'foo')))));
+ $reflectionClass = new ReflectionClass(get_class($blockMock));
+ $method = $reflectionClass->getMethod("getStoredAliasDataForCustomer");
+ $method->setAccessible(true);
+ $this->assertEquals(
+ 'foo', $method->invoke($blockMock, 0, 'bla')
+ );
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasForCustomer')
+ );
+ $blockMock->expects($this->once())
+ ->method('getStoredAliasForCustomer')
+ ->will($this->returnValue(array(0 => new Varien_Object(array('bla' => 'foo')))));
+ $reflectionClass = new ReflectionClass(get_class($blockMock));
+ $method = $reflectionClass->getMethod("getStoredAliasDataForCustomer");
+ $method->setAccessible(true);
+ $this->assertNull($method->invoke($blockMock, 0, 'foo'));
+
+ }
+
+ public function testGetAliasCardNumber()
+ {
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasForCustomer')
+ );
+ $blockMock->expects($this->any())
+ ->method('getStoredAliasForCustomer')
+ ->will(
+ $this->returnValue(
+ array(
+ 0 => new Varien_Object(
+ array(
+ 'pseudo_account_or_cc_no' => 'xxxxxxxxxxxx1111',
+ 'brand' => 'visa'
+ )
+ )
+ )
+ )
+ );
+ $this->assertEquals('XXXX XXXX XXXX 1111', $blockMock->getAliasCardNumber(0));
+ }
+
+ /**
+ * @loadFixture aliases.yaml
+ */
+ public function testGetStoredAliasForCustomer()
+ {
+
+ $reflectionClass = new ReflectionClass(get_class($this->_block));
+ $method = $reflectionClass->getMethod("getStoredAliasForCustomer");
+ $method->setAccessible(true);
+ $this->assertEquals(0, count($method->invoke($this->_block)));
+
+
+ $configMock = $this->getModelMock('ops/config', array('isAliasManagerEnabled'));
+ $configMock->expects($this->any())
+ ->method('isAliasManagerEnabled')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $aliases = Mage::getModel('ops/alias')
+ ->getCollection()
+ ->addFieldToFilter('customer_id', 1)
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::ACTIVE)
+ ->setOrder('created_at', Varien_Data_Collection::SORT_ORDER_DESC);
+ $alias = $aliases->getFirstItem();
+ $aliasHelperMock = $this->getHelperMock('ops/alias', array('getAliasesForAddresses'));
+ $aliasHelperMock->expects($this->once())
+ ->method('getAliasesForAddresses')
+ ->will($this->returnValue($aliases));
+ $this->replaceByMock('helper', 'ops/alias', $aliasHelperMock);
+
+ $customerMock = $this->getHelperMock('customer/data', array('isLoggedIn'));
+ $customerMock->expects($this->once())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'customer/data', $customerMock);
+
+ $fakeCustomer = new Varien_Object();
+ $fakeCustomer->setId(1);
+
+ $fakeQuote = new Varien_Object();
+ $fakeQuote->setCustomer($fakeCustomer);
+
+
+ $blockMock = $this->getBlockMock('ops/form_cc', array('getQuote', 'getMethodCode'));
+ $blockMock->expects($this->once())
+ ->method('getQuote')
+ ->will($this->returnValue($fakeQuote));
+ $blockMock->expects($this->any())
+ ->method('getMethodCode')
+ ->will($this->returnValue('ops_cc'));
+ $this->replaceByMock('block', 'ops/form_cc', $blockMock);
+
+ $reflectionClass = new ReflectionClass(get_class($blockMock));
+ $method = $reflectionClass->getMethod("getStoredAliasForCustomer");
+ $method->setAccessible(true);
+ $aliases = $method->invoke($blockMock);
+ $this->assertEquals($alias->getData(), $aliases[1]->getData());
+
+ }
+
+
+ public function testGetExpirationDatePart()
+ {
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasForCustomer')
+ );
+ $blockMock->expects($this->any())
+ ->method('getStoredAliasForCustomer')
+ ->will($this->returnValue(array(0 => new Varien_Object(array('expiration_date' => '0416')))));
+ $this->assertEquals('04', $blockMock->getExpirationDatePart(0, 'month'));
+ $this->assertEquals('16', $blockMock->getExpirationDatePart(0, 'year'));
+ }
+
+ public function testGetCardHolderName()
+ {
+ $configMock = $this->getModelMock('ops/config', array('isAliasManagerEnabled'));
+ $configMock->expects($this->any())
+ ->method('isAliasManagerEnabled')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $this->assertNull($block = $this->_block->getCardHolderName(2));
+
+ $configMock = $this->getModelMock('ops/config', array('isAliasManagerEnabled'));
+ $configMock->expects($this->any())
+ ->method('isAliasManagerEnabled')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasDataForCustomer', 'getStoredAlias')
+ );
+
+ $blockMock->expects($this->any())
+ ->method('getStoredAliasDataForCustomer')
+ ->will($this->returnValue('Hubertus von Fürstenberg'));
+
+ $blockMock->expects($this->any())
+ ->method('getStoredAlias')
+ ->will($this->returnValue('4711'));
+ $this->assertEquals('Hubertus von Fürstenberg', $blockMock->getCardHolderName(2));
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasDataForCustomer', 'getStoredAlias', 'getMethodCode')
+ );
+ $blockMock->expects($this->any())
+ ->method('getMethodCode')
+ ->will($this->returnValue('ops_cc'));
+ $blockMock->expects($this->once())
+ ->method('getStoredAliasDataForCustomer')
+ ->will($this->returnValue(null));
+
+ $blockMock->expects($this->any())
+ ->method('getStoredAlias')
+ ->will($this->returnValue('4711'));
+
+ $customerHelperMock = $this->getHelperMock('customer/data', array('isLoggedIn', 'getCustomerName'));
+ $customerHelperMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(true));
+ $customerHelperMock->expects($this->any())
+ ->method('getCustomerName')
+ ->will($this->returnValue('Hubertus zu Fürstenberg'));
+ $this->replaceByMock('helper', 'customer/data', $customerHelperMock);
+
+
+ $this->assertEquals('Hubertus zu Fürstenberg', $blockMock->getCardHolderName(2));
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasDataForCustomer', 'getStoredAlias', 'getMethodCode')
+ );
+ $blockMock->expects($this->any())
+ ->method('getMethodCode')
+ ->will($this->returnValue('ops_cc'));
+ $blockMock->expects($this->once())
+ ->method('getStoredAliasDataForCustomer')
+ ->will($this->returnValue(''));
+
+ $blockMock->expects($this->any())
+ ->method('getStoredAlias')
+ ->will($this->returnValue('4711'));
+
+ $this->assertEquals('Hubertus zu Fürstenberg', $blockMock->getCardHolderName(2));
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasDataForCustomer', 'getStoredAlias')
+ );
+ $blockMock->expects($this->once())
+ ->method('getStoredAliasDataForCustomer')
+ ->will($this->returnValue(null));
+
+ $blockMock->expects($this->any())
+ ->method('getStoredAlias')
+ ->will($this->returnValue('4711'));
+
+ $customerHelperMock = $this->getHelperMock('customer/data', array('isLoggedIn'));
+ $customerHelperMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'customer/data', $customerHelperMock);
+
+ $this->assertNull($blockMock->getCardHolderName(2));
+
+
+ }
+
+ public function testGetStoredAliasBrandWithInlineBrand()
+ {
+ /** @var Netresearch_OPS_Block_Form_Cc $blockMock */
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasForCustomer', 'getMethodCode')
+ );
+ $blockMock->expects($this->any())
+ ->method('getStoredAliasForCustomer')
+ ->will(
+ $this->returnValue(
+ array(0 => new Varien_Object(
+ array(
+ 'pseudo_account_or_cc_no' => 'xxxxxxxxxxxx1111',
+ 'brand' => 'VISA'
+ )
+ ))
+ )
+ );
+ $blockMock->expects($this->any())
+ ->method('getMethodCode')
+ ->will($this->returnValue('ops_cc'));
+
+ $modelMock = $this->getModelMock(
+ 'ops/config', array('getInlinePaymentCcTypes')
+ );
+ $modelMock->expects($this->any())
+ ->method('getInlinePaymentCcTypes')
+ ->will(
+ $this->returnValue(
+ array(
+ 'VISA'
+ )
+ )
+ );
+
+ $this->assertEquals('VISA', $blockMock->getStoredAliasBrand(0));
+ }
+
+
+ public function testGetStoredAliasBrand()
+ {
+ /** @var Netresearch_OPS_Block_Form_Cc $blockMock */
+
+ $blockMock = $this->getBlockMock(
+ 'ops/form_cc', array('getStoredAliasForCustomer', 'getMethodCode')
+ );
+ $blockMock->expects($this->any())
+ ->method('getStoredAliasForCustomer')
+ ->will(
+ $this->returnValue(
+ array(new Varien_Object(
+ array(
+ 'pseudo_account_or_cc_no' => 'xxxxxxxxxxxx1111',
+ 'brand' => 'VISA'
+ )
+ ))
+ )
+ );
+ $blockMock->expects($this->any())
+ ->method('getMethodCode')
+ ->will($this->returnValue('ops_cc'));
+
+ $modelMock = $this->getModelMock(
+ 'ops/config', array('getInlinePaymentCcTypes')
+ );
+ $modelMock->expects($this->any())
+ ->method('getInlinePaymentCcTypes')
+ ->will(
+ $this->returnValue(
+ array(
+ 'FOO'
+ )
+ )
+ );
+
+ $this->replaceByMock('model', 'ops/config', $modelMock);
+
+ $this->assertEquals('VISA', $blockMock->getStoredAliasBrand(0));
+ }
+
+ public function testIsAliasInfoBlockEnabled()
+ {
+ $configMock = $this->getModelMock('ops/config', array('isAliasPMEnabled', 'isAliasInfoBlockEnabled'));
+ $configMock->expects($this->any())
+ ->method('isAliasPMEnabled')
+ ->will($this->returnValue(false));
+ $configMock->expects($this->any())
+ ->method('isAliasInfoBlockEnabled')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $this->assertFalse(Mage::app()->getLayout()->getBlockSingleton('ops/form_cc')->isAliasInfoBlockEnabled());
+
+ $configMock = $this->getModelMock('ops/config', array('isAliasPMEnabled', 'isAliasInfoBlockEnabled'));
+ $configMock->expects($this->any())
+ ->method('isAliasPMEnabled')
+ ->will($this->returnValue(false));
+ $configMock->expects($this->any())
+ ->method('isAliasInfoBlockEnabled')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $this->assertFalse(Mage::app()->getLayout()->getBlockSingleton('ops/form_cc')->isAliasInfoBlockEnabled());
+
+ $configMock = $this->getModelMock('ops/config', array('isAliasPMEnabled', 'isAliasInfoBlockEnabled'));
+ $configMock->expects($this->any())
+ ->method('isAliasPMEnabled')
+ ->will($this->returnValue(true));
+ $configMock->expects($this->any())
+ ->method('isAliasInfoBlockEnabled')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $this->assertFalse(Mage::app()->getLayout()->getBlockSingleton('ops/form_cc')->isAliasInfoBlockEnabled());
+
+ $configMock = $this->getModelMock('ops/config', array('isAliasPMEnabled', 'isAliasInfoBlockEnabled'));
+ $configMock->expects($this->any())
+ ->method('isAliasPMEnabled')
+ ->will($this->returnValue(true));
+ $configMock->expects($this->any())
+ ->method('isAliasInfoBlockEnabled')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $this->assertFalse(Mage::app()->getLayout()->getBlockSingleton('ops/form_cc')->isAliasInfoBlockEnabled());
+ }
+
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor()// This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()// This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/CcTest/fixtures/aliases.yaml b/app/code/community/Netresearch/OPS/Test/Block/Form/CcTest/fixtures/aliases.yaml
new file mode 100644
index 0000000..829dae0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/CcTest/fixtures/aliases.yaml
@@ -0,0 +1,92 @@
+tables:
+ ops/alias:
+ - id: 1
+ customer_id: 1
+ alias: 4711
+ brand: 'VISA'
+ billing_address_hash: '0815'
+ shipping_address_hash: '2342'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0116'
+ payment_method: 'ops_cd'
+ state: 'active'
+ store_id: 0
+ created_at: '2000-01-01 00:00:01'
+
+ - id: 2
+ customer_id: 1
+ alias: 4712
+ brand: 'VISA'
+ billing_address_hash: '0816'
+ shipping_address_hash: '2342'
+ pseudo_account_or_cc_no: 'xxxx1112'
+ expiration_date: '0116'
+ payment_method: 'ops_cc'
+ state: 'active'
+ store_id: 0
+ created_at: '1970-01-01 00:00:01'
+
+ - id: 3
+ customer_id: 1
+ alias: 4713
+ brand: 'VISA'
+ billing_address_hash: '0817'
+ shipping_address_hash: '0817'
+ pseudo_account_or_cc_no: 'xxxx1113'
+ expiration_date: '0116'
+ payment_method: 'ops_cc'
+ state: 'pending'
+ store_id: 0
+ created_at: '1970-01-01 00:00:02'
+
+ - id: 4
+ customer_id: 2
+ alias: 4711
+ brand: 'VISA'
+ billing_address_hash: '1508'
+ shipping_address_hash: '4223'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0117'
+ payment_method: 'ops_cc'
+ state: 'active'
+ store_id: 0
+ created_at: '1970-01-01 00:00:02'
+
+ - id: 5
+ customer_id: 1
+ alias: 4711
+ brand: 'VISA'
+ billing_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ shipping_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0117'
+ payment_method: 'ops_cc'
+ state: 'active'
+ store_id: 0
+ created_at: '1970-01-01 00:00:02'
+
+ - id: 6
+ customer_id: 1
+ alias: 4714
+ brand: 'VISA'
+ billing_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ shipping_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0116'
+ payment_method: 'ops_cd'
+ state: 'pending'
+ store_id: 0
+ created_at: '2000-11-01 00:00:01'
+
+ - id: 7
+ customer_id: 23
+ alias: 4714
+ brand: 'VISA'
+ billing_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ shipping_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0116'
+ payment_method: 'ops_cd'
+ state: 'active'
+ store_id: 0
+ created_at: '2000-11-01 00:00:01'
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/DirectDebitTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/DirectDebitTest.php
new file mode 100644
index 0000000..5a6a3e5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/DirectDebitTest.php
@@ -0,0 +1,51 @@
+getModelMock(
+ 'ops/config', array('isFrontendEnvironment')
+ );
+ $modelMock->expects($this->any())
+ ->method('isFrontendEnvironment')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/config', $modelMock);
+ $ccForm = new Netresearch_OPS_Block_Form_DirectDebit();
+ $this->assertEquals(
+ Netresearch_OPS_Block_Form_DirectDebit::TEMPLATE,
+ $ccForm->getTemplate()
+ );
+
+ //Backend case
+ $modelMock = $this->getModelMock(
+ 'ops/config', array('isFrontendEnvironment')
+ );
+ $modelMock->expects($this->any())
+ ->method('isFrontendEnvironment')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('model', 'ops/config', $modelMock);
+ $ccForm = new Netresearch_OPS_Block_Form_DirectDebit();
+ $this->assertEquals(
+ Netresearch_OPS_Block_Form_DirectDebit::TEMPLATE,
+ $ccForm->getTemplate()
+ );
+ }
+
+ public function testDirectDebitCountryIds()
+ {
+ $fakeConfig = new Varien_Object();
+ $fakeConfig->setDirectDebitCountryIds("AT, DE, NL");
+ $blockMock = $this->getBlockMock(
+ 'ops/form_directDebit', array('getconfig')
+ );
+ $blockMock->expects($this->once())
+ ->method('getConfig')
+ ->will($this->returnValue($fakeConfig));
+ $this->assertEquals(
+ explode(',', 'AT, DE, NL'), $blockMock->getDirectDebitCountryIds()
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/Field/MethodTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/Field/MethodTest.php
new file mode 100644
index 0000000..8414c8a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/Field/MethodTest.php
@@ -0,0 +1,42 @@
+
+ */
+?>
+getLayout()->createBlock('ops/system_config_form_field_method');
+ $this->assertTrue($block instanceof Netresearch_OPS_Block_System_Config_Form_Field_Method);
+
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/FlexTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/FlexTest.php
new file mode 100644
index 0000000..3062049
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/FlexTest.php
@@ -0,0 +1,89 @@
+
+ */
+?>
+setCurrentStore(0);
+ Mage::getConfig()->saveConfig('payment/ops_flex/methods', serialize($this->getMethodArray()));
+
+ /** @var Netresearch_OPS_Block_Form_Flex $block */
+ $block = Mage::app()->getLayout()->createBlock('ops/form_flex');
+
+ $block->setMethod(Mage::getModel('ops/payment_flex'));
+
+ $this->assertTrue(is_array($block->getFlexMethods()));
+ $this->assertEquals(1, count($block->getFlexMethods()));
+ }
+
+ private function getMethodArray()
+ {
+ return array(
+ array(
+ 'title' => 'foo',
+ 'brand' => 'bar',
+ 'pm' => 'zzz'
+ )
+ );
+ }
+
+
+ public function testGetDefaultOptionTitle()
+ {
+ Mage::app()->setCurrentStore(0);
+ Mage::getConfig()->saveConfig('payment/ops_flex/default_title', 'flex');
+ Mage::getConfig()->cleanCache();
+
+ /** @var Netresearch_OPS_Block_Form_Flex $block */
+ $block = Mage::app()->getLayout()->createBlock('ops/form_flex');
+
+ $block->setMethod(Mage::getModel('ops/payment_flex'));
+
+ $this->assertEquals('flex', $block->getDefaultOptionTitle());
+ }
+
+ public function testIsDefaultOptionActive()
+ {
+ Mage::app()->setCurrentStore(0);
+ Mage::getConfig()->saveConfig('payment/ops_flex/default', true);
+ Mage::getConfig()->cleanCache();
+
+ /** @var Netresearch_OPS_Block_Form_Flex $block */
+ $block = Mage::app()->getLayout()->createBlock('ops/form_flex');
+
+ $block->setMethod(Mage::getModel('ops/payment_flex'));
+
+ $this->assertTrue($block->isDefaultOptionActive());
+
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/Ideal.php b/app/code/community/Netresearch/OPS/Test/Block/Form/Ideal.php
new file mode 100644
index 0000000..7593d84
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/Ideal.php
@@ -0,0 +1,12 @@
+getIDealIssuers();
+ $block = Mage::app()->getLayout()->createBlock('ops/form_Ideal');
+ $this->assertEquals($issuers, $block->getIssuers());
+
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/InterSolveTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/InterSolveTest.php
new file mode 100644
index 0000000..bee340d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/InterSolveTest.php
@@ -0,0 +1,52 @@
+
+ */
+?>
+saveConfig(
+ 'payment/ops_interSolve/brands', serialize($this->getBrandArray())
+ );
+ Mage::getConfig()->cleanCache();
+
+ $block = Mage::app()->getLayout()->createBlock('ops/form_interSolve');
+ $this->assertEquals($this->getBrandArray(), $block->getInterSolveBrands());
+ }
+
+ private function getBrandArray()
+ {
+ return array(
+ array('brand' => 'foo', 'title' => 'bar')
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ApresReceptionTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ApresReceptionTest.php
new file mode 100644
index 0000000..8c77b80
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ApresReceptionTest.php
@@ -0,0 +1,29 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Test_Block_Form_Kwixo_ApresReceptionTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $block = null;
+
+ public function setUp()
+ {
+ $this->block = new Netresearch_OPS_Block_Form_Kwixo_ApresReception();
+ }
+
+ public function testGetTemplate()
+ {
+ $this->assertEquals('ops/form/kwixo/apres_reception.phtml', $this->block->getTemplate());
+ }
+
+ public function testGetPmLogo()
+ {
+ $this->assertEquals('images/ops/kwixo/apres_reception.jpg', $this->block->getPmLogo());
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ComptantTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ComptantTest.php
new file mode 100644
index 0000000..59cd62d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/ComptantTest.php
@@ -0,0 +1,30 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Block_Form_Kwixo_ComptantTest extends EcomDev_PHPUnit_Test_Case
+{
+ protected $block = null;
+
+ public function setUp()
+ {
+ $this->block = new Netresearch_OPS_Block_Form_Kwixo_Comptant();
+ }
+
+ public function testGetTemplate()
+ {
+ $this->assertEquals('ops/form/kwixo/comptant.phtml', $this->block->getTemplate());
+ }
+
+ public function testGetPmLogo()
+ {
+ $this->assertEquals('images/ops/kwixo/comptant.jpg', $this->block->getPmLogo());
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/CreditTest.php b/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/CreditTest.php
new file mode 100644
index 0000000..b4f6cf4
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Form/Kwixo/CreditTest.php
@@ -0,0 +1,34 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+
+
+class Netresearch_OPS_Test_Block_Form_Kwixo_CreditTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $block = null;
+
+ public function setUp()
+ {
+ $this->block = new Netresearch_OPS_Block_Form_Kwixo_Credit();
+ }
+
+ public function testGetTemplate()
+ {
+ $block = new Netresearch_OPS_Block_Form_Kwixo_Credit();
+ $this->assertEquals('ops/form/kwixo/credit.phtml', $block->getTemplate());
+ }
+
+ public function testGetPmLogo()
+ {
+ $this->assertEquals('images/ops/kwixo/credit.jpg', $this->block->getPmLogo());
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/FormTest.php b/app/code/community/Netresearch/OPS/Test/Block/FormTest.php
new file mode 100644
index 0000000..d89d416
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/FormTest.php
@@ -0,0 +1,106 @@
+_block = Mage::app()->getLayout()->getBlockSingleton('ops/form');
+ }
+
+ public function testIsUserRegistering()
+ {
+ $dataHelperMock = $this->getHelperMock('ops/data', array('checkIfUserIsRegistering'));
+ $dataHelperMock->expects($this->any())
+ ->method('checkIfUserIsRegistering')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+
+ $block = new Netresearch_OPS_Block_Form();
+ $this->assertFalse($block->isUserRegistering());
+ }
+
+ public function testIsUserNotRegistering()
+ {
+ $dataHelperMock = $this->getHelperMock('ops/data', array('checkIfUserIsNotRegistering'));
+ $dataHelperMock->expects($this->any())
+ ->method('checkIfUserIsNotRegistering')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+
+ $block = new Netresearch_OPS_Block_Form();
+ $this->assertFalse($block->isUserNotRegistering());
+ }
+
+ public function testGetPmLogo()
+ {
+ $this->assertEquals(null, $this->_block->getPmLogo());
+ }
+
+ public function getMethodLabelAfterHtmlSuccess()
+ {
+ $method = new Varien_Object();
+ $method->setData('code', 'ops_cc');
+
+ $blockMock = $this->getBlockMock('ops/form', array('getMethod'));
+
+ $blockMock->expects($this->any())
+ ->method('getMethod')
+ ->will($this->returnValue($method));
+ $this->replaceByMock('block', 'ops/form', $blockMock);
+
+ $formBlock = Mage::app()->getLayout()->createBlock('ops/form');
+
+ $result = $formBlock->getMethodLabelAfterHtml();
+
+ $this->assertContains('cc.jpg', $result);
+ $this->assertContains(' left', $result);
+
+ $result = $formBlock->getMethodLabelAfterHtml();
+
+ $this->assertContains('store_one', $result);
+ }
+
+ public function getMethodLabelAfterHtmlHidden()
+ {
+ $method = new Varien_Object();
+ $method->setData('code', 'ops_dc');
+
+ $blockMock = $this->getBlockMock('ops/form', array('getMethod'));
+
+ $blockMock->expects($this->any())
+ ->method('getMethod')
+ ->will($this->returnValue($method));
+ $this->replaceByMock('block', 'ops/form', $blockMock);
+
+ $formBlock = Mage::app()->getLayout()->createBlock('ops/form');
+
+ $result = $formBlock->getMethodLabelAfterHtml();
+
+ $this->assertEmpty($result);
+ }
+
+ public function getMethodLabelAfterHtmlFail()
+ {
+ $method = new Varien_Object();
+ $method->setData('code', 'ops_iDEAL');
+
+ $blockMock = $this->getBlockMock('ops/form', array('getMethod'));
+
+ $blockMock->expects($this->any())
+ ->method('getMethod')
+ ->will($this->returnValue($method));
+ $this->replaceByMock('block', 'ops/form', $blockMock);
+
+ $formBlock = Mage::app()->getLayout()->createBlock('ops/form');
+
+ $result = $formBlock->getMethodLabelAfterHtml();
+
+ $this->assertContains('ops_iDEAL.jpg', $result);
+ $this->assertContains('skin/frontend', $result);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/FormTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Block/FormTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Block/FormTest/fixtures/FormTest.yaml b/app/code/community/Netresearch/OPS/Test/Block/FormTest/fixtures/FormTest.yaml
new file mode 100644
index 0000000..c8abbc1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/FormTest/fixtures/FormTest.yaml
@@ -0,0 +1,22 @@
+scope:
+ store: # Initializes store views
+# Store 1
+ - store_id: 1
+ website_id: 1
+ group_id: 1
+ code: store_one
+ name: Store One
+ is_active: 1
+# Store 2
+ - store_id: 2
+ website_id: 1
+ group_id: 1
+ code: store_two
+ name: Store Two
+ is_active: 1
+
+config:
+ default/payment/ops_dc/position: hidden
+ default/payment/ops_cc/position: left
+ default/payment/ops_cc/image: default/cc.jpg
+ stores/store_one/payment/ops_cc/image: store_one/cc.jpg
diff --git a/app/code/community/Netresearch/OPS/Test/Block/FrauddetectionTest.php b/app/code/community/Netresearch/OPS/Test/Block/FrauddetectionTest.php
new file mode 100644
index 0000000..7d7345f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/FrauddetectionTest.php
@@ -0,0 +1,65 @@
+store = Mage::app()->getStore(0)->load(0);
+ $this->store->resetConfig();
+ }
+
+ public function testToHtml()
+ {
+ $block = Mage::app()->getLayout()->getBlockSingleton('ops/frauddetection');
+ $this->assertEquals(null, $block->toHtml());
+
+ $configMock = $this->getModelMock('ops/config', array('getDeviceFingerPrinting'));
+ $configMock->expects($this->once())
+ ->method('getDeviceFingerPrinting')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->setMethods(array('getData'))
+ ->getMock();
+ $sessionMock->expects($this->once())
+ ->method('getData')
+ ->with(Netresearch_OPS_Model_Payment_Abstract::FINGERPRINT_CONSENT_SESSION_KEY)
+ ->will($this->returnValue(true));
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ // for some reason the html is not rendered in the tests
+ $this->assertNotNull($block->toHtml());
+ }
+
+
+ public function testGetTrackingCodeAid()
+ {
+ $block = Mage::app()->getLayout()->getBlockSingleton('ops/frauddetection');
+ $this->assertEquals('10376', $block->getTrackingCodeAid());
+ }
+
+
+ public function testGetTrackingSid()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $quote->setReservedOrderId('123456');
+ $quote->getStoreId(0);
+ Mage::app(0)->getStore(0)->setConfig(Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'PSPID', 'abc');
+
+ $block = Mage::app()->getLayout()->getBlockSingleton('ops/frauddetection');
+ $modelMock = $this->getModelMock('checkout/type_onepage', array('getQuote'));
+ $modelMock->expects($this->once())
+ ->method('getQuote')
+ ->will($this->returnValue($quote));
+ $this->replaceByMock('singleton', 'checkout/type_onepage', $modelMock);
+ $this->assertEquals(md5(Mage::getModel('ops/config')->getPSPID() . '#123456'), $block->getTrackingSid());
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/Info/FlexTest.php b/app/code/community/Netresearch/OPS/Test/Block/Info/FlexTest.php
new file mode 100644
index 0000000..8036877
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/Info/FlexTest.php
@@ -0,0 +1,50 @@
+
+ */
+?>
+setAdditionalInformation(Netresearch_OPS_Model_Payment_Flex::INFO_KEY_TITLE, 'FLEX');
+
+ /** @var Netresearch_OPS_Block_Info_Flex $block */
+ $block = Mage::app()->getLayout()->createBlock('ops/info_flex');
+ $method = Mage::getModel('ops/payment_flex');
+ $method->setData('info_instance', $payment);
+ $payment->setMethodInstance($method);
+ $block->setInfo($payment);
+
+ $this->assertEquals('FLEX', $block->getFlexTitle());
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/PlaceFormShaTest.php b/app/code/community/Netresearch/OPS/Test/Block/PlaceFormShaTest.php
new file mode 100644
index 0000000..5985eab
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/PlaceFormShaTest.php
@@ -0,0 +1,81 @@
+_helper = new Netresearch_OPS_Helper_Payment();
+ $this->_shaKey = 'qu4rkkuchen12345';
+ }
+
+ public function testShaGenerationWithTestData()
+ {
+ $params = array(
+ 'AMOUNT' => '2129',
+ 'CIVILITY' => 'Herr',
+ 'CURRENCY' => 'EUR',
+ 'ECOM_BILLTO_POSTAL_NAME_FIRST' => 'John',
+ 'ECOM_BILLTO_POSTAL_NAME_LAST' => 'Doe',
+ 'ECOM_SHIPTO_DOB' => '09/10/1940',
+ 'EMAIL' => 'john@doe.com',
+ 'ITEMID1' => 'article1',
+ 'ITEMNAME1' => 'coffee',
+ 'ITEMPRICE1' => '3.00',
+ 'ITEMQUANT1' => '4',
+ 'ITEMVAT1' => '0.57',
+ 'LANGUAGE' => 'de_DE',
+ 'ORDERID' => 'order123',
+ 'ORDERSHIPCOST' => '100',
+ 'ORDERSHIPTAX' => '6',
+ 'OWNERADDRESS' => 'test street',
+ 'OWNERCTY' => 'DE',
+ 'OWNERTELNO' => '+49 111 222 33 444',
+ 'OWNERTOWN' => 'Berlin',
+ 'OWNERZIP' => '10000',
+ 'PM' => 'Open Invoice DE',
+ 'PSPID' => 'NRMAGbillpay1',
+ );
+ $expected = '695103f8891dfc80ea46369203925b898a381334';
+ $shaSign = $this->_helper->getSHASign($params, $this->_shaKey, 0);
+ $result = $this->_helper->shaCrypt($shaSign);
+ $this->assertEquals($expected, $result);
+ }
+
+ public function testShaGenerationWithSpecialChars()
+ {
+ $params = array(
+ 'PSPID' => 'NRMAGbillpay1',
+ 'AMOUNT' => '560',
+ 'ORDERID' => 'TBI72',
+ 'CURRENCY' => 'EUR',
+ 'OWNERCTY' => 'DE',
+ 'ITEMVAT1' => '0.10',
+ 'LANGUAGE' => 'de_DE',
+ 'PM' => 'Open Invoice DE',
+ 'CIVILITY' => 'Herr',
+ 'EMAIL' => 'thomas.kappel@netresearch.de',
+ 'ORDERSHIPCOST' => '500',
+ 'ORDERSHIPTAX' => '0',
+ 'ECOM_BILLTO_POSTAL_NAME_FIRST' => 'Karla',
+ 'ECOM_BILLTO_POSTAL_NAME_LAST' => 'Kolumna',
+ 'OWNERTELNO' => '64065460',
+ 'ITEMPRICE1' => '0.60',
+ 'ECOM_SHIPTO_DOB' => '09/10/1940',
+ 'OWNERADDRESS' => 'Tierparkallee 2',
+ 'OWNERTOWN' => 'Leipzig',
+ 'ITEMID1' => '26',
+ 'ITEMNAME1' => 'Club Mate',
+ 'ITEMQUANT1' => '1',
+ 'OWNERZIP' => '04229',
+ );
+ $expected = 'baf6099446e3bf93ecf26e622032e7db2139839c';
+ $shaSign = $this->_helper->getSHASign($params, $this->_shaKey, 0);
+ $result = $this->_helper->shaCrypt($shaSign);
+ $this->assertEquals($expected, $result);
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Block/PlaceformTest.php b/app/code/community/Netresearch/OPS/Test/Block/PlaceformTest.php
new file mode 100644
index 0000000..35cc863
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/PlaceformTest.php
@@ -0,0 +1,92 @@
+mockSessions();
+
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_openInvoiceDe');
+ $order->setPayment($payment);
+
+ //$block = Mage::app()->getLayout()->getBlockSingleton('ops/placeform');
+ $blockMock = $this->getBlockMock('ops/placeform', array('getQuestion', '_getOrder'));
+ $blockMock->expects($this->any())
+ ->method('getQuestion')
+ ->will($this->returnValue('How much is the fish?'));
+
+
+ $blockMock->expects($this->any())
+ ->method('_getOrder')
+ ->will($this->returnValue($order));
+
+
+ $action = $blockMock->getFormAction();
+ $this->assertEquals(Mage::getUrl('*/*/*', array('_secure' => Mage::app()->getFrontController()->getRequest()->isSecure())), $action);
+
+ // check explicitly for https
+ $_SERVER['HTTPS'] = 'on';
+ $action = $blockMock->getFormAction();
+ $this->assertEquals(Mage::getUrl('*/*/*', array('_secure' =>true)), $action);
+
+ $blockMock = $this->getBlockMock('ops/placeform', array('getQuestion', '_getOrder'));
+ $blockMock->expects($this->any())
+ ->method('getQuestion')
+ ->will($this->returnValue(null));
+
+ $blockMock->expects($this->any())
+ ->method('_getOrder')
+ ->will($this->returnValue($order));
+
+
+
+ $action = $blockMock->getFormAction();
+ $this->assertEquals($blockMock->getConfig()->getFrontendGatewayPath(), $action);
+ }
+
+ public function testIsKwixoPaymentMethodTrue()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_kwixoApresReception');
+ $order->setPayment($payment);
+
+ $blockMock = $this->getBlockMock('ops/placeform', array('_getOrder'));
+ $blockMock->expects($this->any())
+ ->method('_getOrder')
+ ->will($this->returnValue($order));
+
+ $this->assertTrue($blockMock->isKwixoPaymentMethod());
+
+ }
+
+ public function testIsKwixoPaymentMethodFalse()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_cc');
+ $order->setPayment($payment);
+
+ $blockMock = $this->getBlockMock('ops/placeform', array('_getOrder'));
+ $blockMock->expects($this->any())
+ ->method('_getOrder')
+ ->will($this->returnValue($order));
+
+ $this->assertFalse($blockMock->isKwixoPaymentMethod());
+
+ }
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/RetryPayment/MethodsTest.php b/app/code/community/Netresearch/OPS/Test/Block/RetryPayment/MethodsTest.php
new file mode 100644
index 0000000..4d1f085
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/RetryPayment/MethodsTest.php
@@ -0,0 +1,86 @@
+
+ */
+class Netresearch_OPS_Test_Block_RetryPayment_MethodsTest extends EcomDev_PHPUnit_Test_Case
+{
+ /**
+ * @test
+ */
+ public function getMethods()
+ {
+ $this->mockSessions();
+
+ /** @var Netresearch_OPS_Block_RetryPayment_Methods $retryBlockMock */
+ $retryBlockMock = $this->getBlockMock('ops/retryPayment_methods', array('_canUseMethod'));
+ $retryBlockMock->expects($this->any())
+ ->method('_canUseMethod')
+ ->will($this->returnValue(true));
+
+ $method = Mage::getModel('ops/payment_ops_cc');
+ $retryBlockMock->setMethods(array($method));
+
+ $paymentMethodMock = $this->getModelMock('ops/payment_abstract', array('isApplicableToQuote'));
+ $paymentMethodMock->expects($this->any())
+ ->method('isApplicableToQuote')
+ ->will($this->returnValue(true));
+
+ $paymentHelperMock = $this->getHelperMock('payment', array('getStoreMethods'));
+ $paymentHelperMock->expects($this->any())
+ ->method('getStoreMethods')
+ ->will($this->returnValue(array($paymentMethodMock)));
+ $this->replaceByMock('helper', 'payment', $paymentHelperMock);
+
+ $result = $retryBlockMock->getMethods();
+
+ $this->assertInternalType('array', $result);
+ $this->assertEquals(1, count($result));
+
+ }
+
+ /**
+ * Helper Function to remove Session Errors
+ */
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('admin/session')
+ ->disableOriginalConstructor()// This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'admin/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor()// This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()// This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/RetryPaymentTest.php b/app/code/community/Netresearch/OPS/Test/Block/RetryPaymentTest.php
new file mode 100644
index 0000000..3e7ff44
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/RetryPaymentTest.php
@@ -0,0 +1,94 @@
+
+ */
+class Netresearch_OPS_Test_Block_RetryPaymentTest extends EcomDev_PHPUnit_Test_Case
+{
+ /**
+ * @test
+ */
+ public function getFormAction()
+ {
+ $this->mockSessions();
+ $retryBlock = new Netresearch_OPS_Block_RetryPayment();
+
+ $result = $retryBlock->getFormAction();
+
+ $this->assertInternalType('string', $result);
+ $this->assertContains('http', $result);
+
+ }
+
+ /**
+ * @test
+ */
+ public function getCancelUrl()
+ {
+ $this->mockSessions();
+ $retryBlock = new Netresearch_OPS_Block_RetryPayment();
+
+ $result = $retryBlock->getCancelUrl();
+
+ $this->assertInternalType('string', $result);
+ $this->assertContains('http', $result);
+
+ }
+
+ /**
+ * @test
+ */
+ public function getOrderId()
+ {
+ $this->mockSessions();
+ $retryBlock = new Netresearch_OPS_Block_RetryPayment();
+ $orderId = '100000023';
+
+ Mage::app()->getRequest()->setParam('orderID', $orderId);
+
+ $result = $retryBlock->getOrderId();
+
+ $this->assertContains($orderId, $result);
+
+ }
+
+ /**
+ * Helper Function to remove Session Errors
+ */
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor()// This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()// This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/System/Config/Form/Field/ImageTest.php b/app/code/community/Netresearch/OPS/Test/Block/System/Config/Form/Field/ImageTest.php
new file mode 100644
index 0000000..590545e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/System/Config/Form/Field/ImageTest.php
@@ -0,0 +1,73 @@
+
+ * @copyright 2016 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+
+/**
+ * Netresearch_OPS_Test_Block_System_Config_ImageTest
+ *
+ * @category OPS
+ * @package Netresearch_OPS
+ * @author Benjamin Heuer
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+class Netresearch_OPS_Test_Block_System_Config_Form_Field_ImageTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+ /**
+ * @test
+ */
+ public function getElementHtml()
+ {
+ $blockMock =
+ $this->getBlockMock('ops/system_config_form_field_image', array('getHtmlId', '_getDeleteCheckbox'), false,
+ array(), '', false
+ );
+
+ $blockMock->expects($this->any())
+ ->method('getHtmlId')
+ ->will($this->returnValue('112'));
+ $blockMock->expects($this->any())
+ ->method('_getDeleteCheckbox')
+ ->will($this->returnValue(''));
+
+ /** @var Netresearch_OPS_Block_System_Config_Form_Field_Image $imageBlock */
+ $blockMock->setData('name', 'groups[ops_cc][fields][image][value]');
+
+ $result = $blockMock->getElementHtml();
+
+ $this->assertInternalType('string', $result);
+ $this->assertContains('ops/logos/ops_cc.png', $result);
+
+ /* Fill the Block with an Url */
+ $simpleXmlElement = new Varien_Simplexml_Element('ingenico/test ');
+ $blockMock->setData('value', 'default/img.png');
+ $blockMock->setData('field_config', $simpleXmlElement);
+ $result = $blockMock->getElementHtml();
+ $this->assertInternalType('string', $result);
+ $this->assertContains('ingenico/test', $result);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Block/System/Config/KwixoconfigurationTest.php b/app/code/community/Netresearch/OPS/Test/Block/System/Config/KwixoconfigurationTest.php
new file mode 100644
index 0000000..f57a43a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/System/Config/KwixoconfigurationTest.php
@@ -0,0 +1,24 @@
+
+ * @category Netresearch
+ * @package ${MODULENAME}
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Block_System_Config_KwixoconfigurationTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+
+ public function testRender()
+ {
+ $element = new Varien_Data_Form_Element_Text();
+ $element->setLegend('I am legend');
+ $block = new Netresearch_OPS_Block_System_Config_Kwixoconfiguration();
+ $block->render($element);
+ $this->assertEquals('I am legend', $block->getData('fieldset_label'));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Block/System/Config/ModeTest.php b/app/code/community/Netresearch/OPS/Test/Block/System/Config/ModeTest.php
new file mode 100644
index 0000000..618d24d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Block/System/Config/ModeTest.php
@@ -0,0 +1,21 @@
+setForm(new Varien_Object());
+ $block = new Netresearch_OPS_Block_System_Config_Mode();
+ $html = $block->render($element);
+ $this->assertTrue(preg_match('/");
+
+ $params = array('Alias_AliasId' => '4711', 'Card_CVC' => '123', 'Alias_OrderId' => '0');
+ $this->dispatch($routeToDispatch, $params);
+ $result = $this->getResponse()->getOutputBody();
+ $this->assertEquals($result, "");
+
+
+
+ }
+
+ public function testAcceptAliasActionException()
+ {
+ $routeToDispatch = $this->prepareAliasControllerTest();
+
+ $this->dispatch($routeToDispatch, array('Alias_OrderId' => '0'));
+ $result = $this->getResponse()->getOutputBody();
+ $this->assertEquals($result, "");
+ }
+
+
+ /**
+ * @loadFixture orders.yaml
+ */
+ public function testGenerateHashAction()
+ {
+
+ $fakeQuote = Mage::getModel('sales/order')->load(11);
+ $quoteMock = $this->getModelMock('sales/quote', array('load', 'save'));
+ $quoteMock->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($fakeQuote));
+ $this->replaceByMock('model', 'sales/quote', $quoteMock);
+ $params = array(
+ 'alias' => 4711,
+ 'storeId' => 1
+ );
+
+ $configHelperMock = $this->getModelMock('ops/config', array('getAliasAcceptUrl', 'getAliasExceptionUrl'));
+ $configHelperMock->expects($this->any())
+ ->method('getAliasAcceptUrl')
+ ->with(1)
+ ->will($this->returnValue(1));
+ $configHelperMock->expects($this->any())
+ ->method('getAliasExceptionUrl')
+ ->with(1)
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'ops/config', $configHelperMock);
+
+ $this->dispatch('ops/alias/generateHash', $params);
+ $result = Mage::helper('core')->jsonDecode($this->getResponse()->getOutputBody());
+ $this->assertArrayHasKey('hash', $result);
+
+ $params = array(
+ 'alias' => 4712,
+ 'storeId' => 0
+ );
+
+ $configHelperMock = $this->getModelMock('ops/config', array('getAliasAcceptUrl', 'getAliasExceptionUrl'));
+ $configHelperMock->expects($this->any())
+ ->method('getAliasAcceptUrl')
+ ->with(0)
+ ->will($this->returnValue(1));
+ $configHelperMock->expects($this->any())
+ ->method('getAliasExceptionUrl')
+ ->with(0)
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'ops/config', $configHelperMock);
+
+ $this->dispatch('ops/alias/generateHash', $params);
+ $result = Mage::helper('core')->jsonDecode($this->getResponse()->getOutputBody());
+ $this->assertArrayHasKey('hash', $result);
+
+ $params = array(
+ 'alias' => 4713,
+ 'storeId' => 1,
+ 'isAdmin' => 1,
+ 'brand' => 'visa'
+ );
+
+ $configHelperMock = $this->getModelMock('ops/config', array('getAliasAcceptUrl', 'getAliasExecptionUrl'));
+ $configHelperMock->expects($this->any())
+ ->method('getAliasAcceptUrl')
+ ->with(0)
+ ->will($this->returnValue(1));
+ $configHelperMock->expects($this->any())
+ ->method('getAliasExceptionUrl')
+ ->with(0)
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'ops/config', $configHelperMock);
+
+ $this->dispatch('ops/alias/generateHash', $params);
+ $result = Mage::helper('core')->jsonDecode($this->getResponse()->getOutputBody());
+ $this->assertArrayHasKey('hash', $result);
+
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Controller/AliasControllerTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Controller/AliasControllerTest/fixtures/orders.yaml
new file mode 100644
index 0000000..30ca933
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Controller/AliasControllerTest/fixtures/orders.yaml
@@ -0,0 +1,595 @@
+tables:
+ sales/order:
+ - entity_id: 11
+ increment_id: 100000011
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 23
+
+ - entity_id: 12
+ increment_id: 100000012
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 24
+
+ - entity_id: 13
+ increment_id: 100000013
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'processing'
+ status: 'processing'
+ quote_id: 25
+
+ - entity_id: 14
+ increment_id: 100000014
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 26
+
+ - entity_id: 15
+ increment_id: 100000015
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 200.00
+ currency: '$'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+ - entity_id: 16
+ increment_id: 100000016
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 28
+
+ - entity_id: 17
+ increment_id: 100000017
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 29
+
+ - entity_id: 18
+ increment_id: 100000018
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 30
+
+ - entity_id: 19
+ increment_id: 100000019
+ shipping_address_id: 50
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 43
+
+ - entity_id: 20
+ increment_id: 100000020
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 42#
+
+ - entity_id: 21
+ increment_id: 100000021
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 22
+ increment_id: 100000022
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 23
+ increment_id: 100000023
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 24
+ increment_id: 100000024
+ store_id: 1
+ shipping_address_id: 46
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 24
+ increment_id: 100000024
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 25
+ increment_id: 100000025
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 26
+ increment_id: 100000026
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 27
+ increment_id: 100000027
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 28
+ increment_id: 100000028
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 29
+ increment_id: 100000029
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 30
+ increment_id: 100000030
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ sales/quote:
+ - entity_id: 1
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ - entity_id: 2
+ base_grand_total: 119.00
+ grand_total: 200.00
+ currency: '$'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ - entity_id: 10
+ store_id: 0
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 11
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 23
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 12
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ sales/quote_payment:
+ - payment_id: 1
+ quote_id: 10
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 2
+ quote_id: 11
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ quote_id: 11
+
+ - payment_id: 3
+ quote_id: 10
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ additional_information: a:7:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:3:"cvc";s:3:"123";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 4
+ quote_id: 12
+ updated_at: '1970-01-01'
+ method: 'ops_paypal'
+ additional_information: a:7:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:3:"cvc";s:3:"123";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ sales/order_payment:
+ - entity_id: 1
+ parent_id: 11
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_bankTransfer'
+
+ - entity_id: 2
+ parent_id: 12
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:1:"5";}
+
+ - entity_id: 3
+ parent_id: 13
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:1:"0";}
+
+ - entity_id: 4
+ parent_id: 14
+ additional_information: a:2:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";}
+
+ - entity_id: 5
+ parent_id: 15
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFD";}
+ method: 'ops_cc'
+
+ - entity_id: 6
+ parent_id: 16
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFS";}
+
+ - entity_id: 7
+ parent_id: 17
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFS";s:9:"canRefund";b:0;}
+
+ - entity_id: 8
+ parent_id: 18
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFD";s:9:"canRefund";b:1;}
+
+ - entity_id: 9
+ parent_id: 19
+ method: 'ops_openInvoiceDe'
+
+ - entity_id: 11
+ parent_id: 20
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 12
+ parent_id: 21
+ additional_information: a:4:{s:2:"PM";s:16:"Direct Debits DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+ method: 'ops_directDebit'
+
+ - entity_id: 13
+ parent_id: 22
+ additional_information: a:4:{s:2:"PM";s:16:"Direct Debits NL";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 14
+ parent_id: 23
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 42
+ parent_id: 20
+
+ - entity_id: 15
+ parent_id: 24
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_cc'
+
+ - entity_id: 16
+ parent_id: 25
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_cc'
+
+ - entity_id: 17
+ parent_id: 26
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_paypal'
+
+ - entity_id: 18
+ parent_id: 27
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoApresReception'
+
+ - entity_id: 19
+ parent_id: 28
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoComptant'
+
+ - entity_id: 20
+ parent_id: 29
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoCredit'
+
+ - entity_id: 21
+ parent_id: 30
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'checkmo'
+
+ sales/shipment:
+ - entity_id: 1
+ increment_id: 100000077
+ order_id: 11
+ shipping_address_id: 42
+
+ - entity_id: 2
+ increment_id: 100000078
+ order_id: 12
+ shipping_address_id: 43
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 11
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 11
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 44
+ parent_id: 12
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 45
+ parent_id: 12
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 46
+ parent_id: 24
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 47
+ parent_id: 27
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_shipping: 1
+
+ - entity_id: 48
+ parent_id: 28
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 49
+ parent_id: 19
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 50
+ parent_id: 19
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ sales/order_item:
+ - item_id: 11
+ order_id: 11
+ qty_ordered: 2.0000
+ qty_shipped: 2.0000
+ sku: 4711
+ name: 'some great test item'
+ price: 19.99
+ tax_amount: 1.99
+
+ - item_id: 12
+ order_id: 11
+ qty_ordered: 2.0000
+ qty_shipped: 2.0000
+ sku: 4711
+ name: 'some great test item 2'
+ price: 19.99
+ tax_amount: 1.99
+
diff --git a/app/code/community/Netresearch/OPS/Test/Controller/ApiControllerTest.php b/app/code/community/Netresearch/OPS/Test/Controller/ApiControllerTest.php
new file mode 100644
index 0000000..85093da
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Controller/ApiControllerTest.php
@@ -0,0 +1,165 @@
+getHelperMock(
+ 'ops/payment', array('applyStateForOrder', 'shaCryptValidation')
+ );
+ $paymentHelperMock->expects($this->any())
+ ->method('applyStateForOrder')
+ ->will($this->returnValue($returnStatus));
+
+ $paymentHelperMock->expects($this->any())
+ ->method('shaCryptValidation')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+ $fakePayment = new Varien_Object();
+ $fakePayment->setMethodInstance(Mage::getModel('ops/payment_cc'));
+
+ $fakeOrder = new Varien_Object();
+ $fakeOrder->setPayment($fakePayment);
+ $fakeOrder->setId(1);
+ if ($setStoreId) {
+ $fakeOrder->setStoreId(1);
+ }
+ $orderHelperMock = $this->getHelperMock('ops/order', array('getOrder'));
+ $orderHelperMock->expects($this->any())
+ ->method('getOrder')
+ ->will($this->returnValue($fakeOrder));
+ $this->replaceByMock('helper', 'ops/order', $orderHelperMock);
+ }
+
+ private function getRequestParams()
+ {
+ return array(
+ 'orderID' => 1,
+ 'SHASIGN' => '12344',
+ );
+ }
+
+ public function testRedirectToSuccessRoute()
+ {
+ $this->setUpHelperMock(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT
+ );
+ $modelMock = $this->getModelMock('core/store', array('getId'));
+ $modelMock->expects($this->any())
+ ->method('getId()')
+ ->will($this->returnValue(null));
+ $this->replaceByMock('model', 'core/store', $modelMock);
+ $this->dispatch('ops/api/postBack', $this->getRequestParams());
+ $this->assertRedirectTo(
+ Mage::getModel('ops/config')->getAcceptRedirectRoute(),
+ array('_query' => $this->getRequestParams(), '_store' => 1)
+ );
+
+ }
+
+ public function testRedirectToSuccessRouteWithOrderId()
+ {
+ $this->setUpHelperMock(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT
+ );
+ $modelMock = $this->getModelMock('core/store', array('getId'));
+ $modelMock->expects($this->any())
+ ->method('getId()')
+ ->will($this->returnValue(null));
+ $requestParams = $this->getRequestParams();
+ $requestParams['orderID'] = '#1000001';
+ $this->dispatch('ops/api/postBack', $requestParams);
+ $this->assertRedirectTo(
+ Mage::getModel('ops/config')->getAcceptRedirectRoute(),
+ array('_query' => $requestParams, '_store' => 1)
+ );
+
+ }
+
+ public function testRedirectToCancelRoute()
+ {
+ $this->setUpHelperMock(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_CANCEL
+ );
+ $modelMock = $this->getModelMock('core/store', array('getId'));
+ $modelMock->expects($this->any())
+ ->method('getId()')
+ ->will($this->returnValue(null));
+ $this->dispatch('ops/api/postBack', $this->getRequestParams());
+ $this->assertRedirectTo(
+ Mage::getModel('ops/config')->getCancelRedirectRoute(),
+ array('_query' => $this->getRequestParams(), '_store' => 1)
+ );
+ }
+
+ public function testRedirectToDeclineRoute()
+ {
+ $this->setUpHelperMock(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_DECLINE
+ );
+ $modelMock = $this->getModelMock('core/store', array('getId'));
+ $modelMock->expects($this->any())
+ ->method('getId()')
+ ->will($this->returnValue(null));
+ $this->dispatch('ops/api/postBack', $this->getRequestParams());
+ $this->assertRedirectTo(
+ Mage::getModel('ops/config')->getDeclineRedirectRoute(),
+ array('_query' => $this->getRequestParams(), '_store' => 1)
+ );
+ }
+
+ public function testRedirectToExceptionRoute()
+ {
+ $this->setUpHelperMock(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_EXCEPTION
+ );
+ $modelMock = $this->getModelMock('core/store', array('getId'));
+ $modelMock->expects($this->any())
+ ->method('getId()')
+ ->will($this->returnValue(null));
+ $this->dispatch('ops/api/postBack', $this->getRequestParams());
+ $this->assertRedirectTo(
+ Mage::getModel('ops/config')->getExceptionRedirectRoute(),
+ array('_query' => $this->getRequestParams(), '_store' => 1)
+ );
+ }
+
+ public function testExceptionReturnsStatus500()
+ {
+ $this->setUpHelperMock(
+ 'INVALID_STATUS'
+ );
+ $modelMock = $this->getModelMock('core/store', array('getId'));
+ $modelMock->expects($this->any())
+ ->method('getId()')
+ ->will($this->returnValue(null));
+ $this->dispatch('ops/api/postBack', $this->getRequestParams());
+ $this->assertResponseHttpCode(500);
+ $this->getResponse();
+ }
+
+
+ public function testRedirectIfStoreIdDoesNotMatch()
+ {
+ $this->setUpHelperMock(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ false
+ );
+ $modelMock = $this->getModelMock('core/store', array('getId'));
+ $modelMock->expects($this->any())
+ ->method('getId()')
+ ->will($this->returnValue(9999));
+ $this->replaceByMock('model', 'core/store', $modelMock);
+ $this->dispatch('ops/api/postBack', $this->getRequestParams());
+ $this->assertRedirectTo(
+ 'ops/payment/accept', array('_query' => $this->getRequestParams(), '_store' => 1)
+ );
+
+
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Controller/DeviceControllerTest.php b/app/code/community/Netresearch/OPS/Test/Controller/DeviceControllerTest.php
new file mode 100644
index 0000000..c2086a0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Controller/DeviceControllerTest.php
@@ -0,0 +1,66 @@
+
+ */
+?>
+ true, '_store' => 1);
+ $this->dispatch('ops/device/toggleConsent', $params);
+ $this->assertResponseBodyJson();
+ $this->assertResponseBodyJsonMatch(array('consent' => false));
+
+ Mage::app()->getStore(1)->setConfig(Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'device_fingerprinting', 1);
+ $this->dispatch('ops/device/toggleConsent', $params);
+ $this->assertResponseBodyJson();
+ $this->assertResponseBodyJsonMatch(array('consent' => true));
+ }
+
+ public function testConsentAction()
+ {
+ $this->dispatch('ops/device/consent');
+ $this->assertResponseBodyJson();
+ $this->assertResponseBodyJsonMatch(array('consent' => false));
+
+ $params = array('consent' => true, '_store' => 1);
+ Mage::app()->getStore(1)->setConfig(Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH.'device_fingerprinting', 1);
+ $this->dispatch('ops/device/toggleConsent', $params);
+ $this->assertResponseBodyJson();
+ $this->assertResponseBodyJsonMatch(array('consent' => true));
+
+ $this->dispatch('ops/device/consent');
+ $this->assertResponseBodyJson();
+ $this->assertResponseBodyJsonMatch(array('consent' => true));
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest.php b/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest.php
new file mode 100644
index 0000000..58fbb07
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest.php
@@ -0,0 +1,413 @@
+
+ * @author André Herrn
+ * @author Paul Siedler
+ */
+class Netresearch_OPS_Test_Controller_PaymentControllerTest
+ extends EcomDev_PHPUnit_Test_Case_Controller
+{
+ public function setUp()
+ {
+ parent::setUp();
+ $helperMock = $this->getHelperMock(
+ 'ops/payment', array(
+ 'shaCryptValidation',
+ 'cancelOrder',
+ 'declineOrder',
+ 'handleException',
+ 'getSHAInSet',
+ 'refillCart'
+ )
+ );
+ $helperMock->expects($this->any())
+ ->method('shaCryptValidation')
+ ->will($this->returnValue(true));
+
+ $this->replaceByMock('helper', 'ops/payment', $helperMock);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testAcceptAction()
+ {
+ $params = array(
+ 'orderID' => '#100000011'
+ );
+ $this->dispatch('ops/payment/accept', $params);
+ $this->assertRedirectTo('checkout/onepage/success');
+
+ $params = array(
+ 'orderID' => '23'
+ );
+ $this->dispatch('ops/payment/accept', $params);
+ $this->assertRedirectTo('checkout/onepage/success');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testExceptionAction()
+ {
+ $msg = 'Your order has been registered, but your payment is still marked as pending.';
+ $msg.= ' Please have patience until the final status is known.';
+
+ $orderId = '11';
+ $quoteId = '23';
+ $incrementId = '#100000011';
+
+
+ // assert order increment id parameter handling
+ $params = array('orderID' => $incrementId);
+
+ $this->dispatch('ops/payment/exception', $params);
+ $this->assertRedirectTo('checkout/onepage/success');
+ $this->assertEquals($orderId, Mage::getSingleton('checkout/session')->getLastOrderId());
+
+ $message = Mage::getSingleton('checkout/session')->getMessages()->getLastAddedMessage();
+ $this->assertEquals('error', $message->getType());
+ $this->assertEquals($msg, $message->getText());
+
+
+ // assert entity id parameter handling
+ $params = array('orderID' => $quoteId);
+
+ $this->dispatch('ops/payment/exception', $params);
+ $this->assertRedirectTo('checkout/onepage/success');
+ $this->assertEquals($orderId, Mage::getSingleton('checkout/session')->getLastOrderId());
+
+ $message = Mage::getSingleton('checkout/session')->getMessages()->getLastAddedMessage();
+ $this->assertEquals('error', $message->getType());
+ $this->assertEquals($msg, $message->getText());
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testDeclineAction()
+ {
+ $routeToDispatch = 'ops/payment/decline';
+ $params = array();
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/onepage');
+
+
+ $params = array(
+ 'orderID' => '#100000011'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/onepage');
+
+ $params = array(
+ 'orderID' => '23'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/onepage');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testCancelAction()
+ {
+ $routeToDispatch = 'ops/payment/cancel';
+
+ $params = array(
+ 'orderID' => '#100000011'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/cart');
+
+ $params = array(
+ 'orderID' => '23'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/cart');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testContinueAction()
+ {
+ $routeToDispatch = 'ops/payment/continue';
+ $params = array();
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/cart');
+
+
+ $params = array(
+ 'orderID' => '#100000011'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/cart');
+
+ $params = array(
+ 'orderID' => '23'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('checkout/cart');
+
+ $params = array(
+ 'orderID' => '#100000011',
+ 'redirect' => 'catalog'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('/');
+
+ $params = array(
+ 'orderID' => '23',
+ 'redirect' => 'catalog'
+ );
+ $this->dispatch($routeToDispatch, $params);
+ $this->assertRedirectTo('/');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testRepayActionWithInvalidHash()
+ {
+ // test 1: hash not valid
+ $order = Mage::getModel('sales/order')->load(11);
+ $opsOrderId = Mage::helper('ops/order')->getOpsOrderId($order);
+
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('shaCryptValidation'));
+ $paymentHelperMock->expects($this->any())
+ ->method('shaCryptValidation')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+
+ $params = array('orderID' => $opsOrderId, 'SHASIGN' => 'foo');
+ $this->dispatch('ops/payment/retry', $params);
+ $this->assertRedirectTo('/');
+ $message = Mage::getSingleton('core/session')->getMessages()->getLastAddedMessage();
+ $this->assertNotNull($message);
+ $this->assertEquals($message->getText(), 'Hash not valid');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testRepayActionWithInvalidOrder()
+ {
+
+ // test 1: hash valid, order can not be retried
+ // orderID 100000012 - status 5
+ $order = Mage::getModel('sales/order')->load(12);
+ $opsOrderId = Mage::helper('ops/order')->getOpsOrderId($order);
+
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('shaCryptValidation'));
+ $paymentHelperMock->expects($this->any())
+ ->method('shaCryptValidation')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+ $orderHelperMock = $this->getHelperMock('ops/order', array('getOrder'));
+ $orderHelperMock->expects($this->any())
+ ->method('getOrder')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('helper', 'ops/order', $orderHelperMock);
+
+ $params = array('orderID' => $opsOrderId, 'SHASIGN' => 'foo');
+ $this->dispatch('ops/payment/retry', $params);
+
+ $this->assertRedirectTo('/');
+
+ $message = Mage::getSingleton('core/session')->getMessages()->getLastAddedMessage();
+ $this->assertNotNull($message);
+ $this->assertEquals(
+ $message->getText(), 'Not possible to reenter the payment details for order ' . $order->getIncrementId()
+ );
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testRepayActionWithSuccess()
+ {
+ // test 31: order is fine
+ // orderID 100000011
+
+ $order = Mage::getModel('sales/order')->load(11);
+ $opsOrderId = Mage::helper('ops/order')->getOpsOrderId($order);
+
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('shaCryptValidation'));
+ $paymentHelperMock->expects($this->any())
+ ->method('shaCryptValidation')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+ $this->dispatch('ops/payment/retry', $paymentHelperMock->validateOrderForReuse($opsOrderId,1));
+
+ $this->assertLayoutLoaded();
+ $this->assertLayoutHandleLoaded('ops_payment_retry');
+ }
+
+ /**
+ * @test
+ */
+ public function placeformActionWithoutSuccess()
+ {
+ $this->dispatch('ops/payment/placeForm');
+ $this->assertRedirectTo('checkout/cart');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @test
+ */
+ public function placeformActionWithSuccess()
+ {
+ $quoteModelMock = $this->getModelMock('sales/quote', array('save'));
+ $quoteModelMock->expects($this->any())
+ ->method('save')
+ ->will($this->returnSelf());
+
+ $checkoutSessionMock = $this->getModelMock('checkout/session', array('getLastRealOrderId', 'getQuote'));
+ $checkoutSessionMock->expects($this->any())
+ ->method('getLastRealOrderId')
+ ->will($this->returnValue(100000013));
+ $checkoutSessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($quoteModelMock));
+ $this->replaceByMock('singleton', 'checkout/session', $checkoutSessionMock);
+
+ $this->dispatch('ops/payment/placeForm');
+
+ $this->assertLayoutLoaded();
+ $this->assertLayoutHandleLoaded('ops_payment_placeform');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @test
+ */
+ public function updatePaymentAndPlaceFormActionWithException()
+ {
+ $orderId = 100000013;
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order');
+ $order->loadByIncrementId($orderId);
+
+ $orderHelperMock = $this->getHelperMock('ops/order', array('getOrder'));
+ $orderHelperMock->expects($this->any())
+ ->method('getOrder')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('helper', 'ops/order', $orderHelperMock);
+
+
+ $this->dispatch('ops/payment/updatePaymentAndPlaceForm', array('orderID' => $orderId));
+ $this->assertRedirectTo('checkout/cart');
+
+ /** @var Mage_Core_Model_Session $test */
+ $test = Mage::getSingleton('core/session');
+ $messages = $test->getMessages()->count();
+ $this->assertEquals(1, $messages);
+ $test->getMessages()->clear();
+ }
+
+ /**
+ * @loadFixture orders.yaml
+ * @test
+ */
+ public function updatePaymentAndPlaceFormActionWithSuccess()
+ {
+ $orderId = '#100000013';
+ $params = array(
+ 'orderID' => $orderId,
+ 'payment' => array(
+ 'method' => 'ops_iDeal',
+ 'ops_iDeal' => array('info' => 'foo', 'info2' => 'bar')
+ )
+ );
+
+ Mage::app()->getRequest()->setParams($params);
+ Mage::getConfig()->setNode('stores/default/payment/ops_iDeal/active', 1);
+ $this->mockSession('checkout/session', array());
+
+ $this->dispatch('ops/payment/updatePaymentAndPlaceForm');
+
+ $this->assertRedirectToUrlContains('placeForm');
+
+ /** @var Mage_Core_Model_Session $test */
+ $test = Mage::getSingleton('core/session');
+ $messages = $test->getMessages()->count();
+ $this->assertEquals(0, $messages);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @test
+ */
+ public function updatePaymentAndPlaceFormActionWithSuccessForDirectDebit()
+ {
+ $this->markTestIncomplete("DirectDebit needs a general rework - INGRC-34");
+
+ $orderId = 100000014;
+ Mage::app()->getRequest()->setParam('orderID', $orderId);
+ Mage::app()->getRequest()->setParam('payment', array('method' => 'ops_directDebit'));
+
+ /** @var Mage_Sales_Model_Order $orderModelMock */
+ $orderModelMock = $this->getModelMock('sales/order', array('save', 'place'));
+ $orderModelMock->expects($this->any())
+ ->method('save')
+ ->will($this->returnSelf());
+ $orderModelMock->expects($this->any())
+ ->method('place')
+ ->will($this->returnSelf());
+
+ $orderHelperMock = $this->getHelperMock('ops/order', array('getOrder'));
+ $orderHelperMock->expects($this->any())
+ ->method('getOrder')
+ ->will($this->returnValue($orderModelMock->loadByIncrementId($orderId)));
+ $this->replaceByMock('helper', 'ops/order', $orderHelperMock);
+
+ $quoteModelMock = $this->getModelMock('sales/quote', array('save'));
+ $quoteModelMock->expects($this->any())
+ ->method('save')
+ ->will($this->returnSelf());
+ $this->replaceByMock('model', 'sales/quote', $quoteModelMock);
+
+ $quotePaymentModelMock = $this->getModelMock('sales/quote_payment', array('save'));
+ $quotePaymentModelMock->expects($this->any())
+ ->method('save')
+ ->will($this->returnSelf());
+ $this->replaceByMock('model', 'sales/quote_payment', $quotePaymentModelMock);
+
+ $this->dispatch('ops/payment/updatePaymentAndPlaceForm');
+ $this->assertRedirectToUrlContains('onepage/success');
+
+ /** @var Mage_Core_Model_Session $test */
+ $test = Mage::getSingleton('core/session');
+ $messages = $test->getMessages()->count();
+ $this->assertEquals(0, $messages);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest/fixtures/orders.yaml
new file mode 100644
index 0000000..0766b5b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Controller/PaymentControllerTest/fixtures/orders.yaml
@@ -0,0 +1,26 @@
+tables:
+ core/config_data:
+ - config_id: 500
+ path: 'payment/ops_iDeal/active'
+ value: 1
+
+ sales/order:
+ - entity_id: 13
+ increment_id: 100000013
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'processing'
+ status: 'processing'
+ quote_id: 25
+ store_id: 0
+
+ sales/order_payment:
+ - entity_id: 3
+ parent_id: 13
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:1:"0";}
+ method: 'ops_bankTransfer'
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/AddressTest.php b/app/code/community/Netresearch/OPS/Test/Helper/AddressTest.php
new file mode 100644
index 0000000..6fe0451
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/AddressTest.php
@@ -0,0 +1,22 @@
+splitStreet($street);
+ $expected = $this->expected('auto')->getData();
+
+ $this->assertEquals($expected, $split);
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/AddressTest/expectations/splitStreet.yaml b/app/code/community/Netresearch/OPS/Test/Helper/AddressTest/expectations/splitStreet.yaml
new file mode 100644
index 0000000..8c81c10
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/AddressTest/expectations/splitStreet.yaml
@@ -0,0 +1,209 @@
+thunstrasse_39:
+ street_name: "Thunstraße"
+ street_number: "39"
+ supplement: ""
+nonnenstrasse:
+ street_name: "Nonnenstraße"
+ street_number: ""
+ supplement: ""
+tulpenweg:
+ street_name: "Tulpenweg"
+ street_number: ""
+ supplement: ""
+tulpenweg_:
+ street_name: "Tulpenweg"
+ street_number: ""
+ supplement: ""
+nonnenstrasse_11c:
+ street_name: "Nonnenstraße"
+ street_number: "11c"
+ supplement: ""
+nonnenstrasse11c:
+ street_name: "Nonnenstraße11c"
+ street_number: ""
+ supplement: ""
+nonnenstrasse_44_46:
+ street_name: "Nonnenstraße"
+ street_number: "44-46"
+ supplement: ""
+nonnenstrasse_44_46_haus_c:
+ street_name: "Nonnenstraße"
+ street_number: "44-46"
+ supplement: "Haus C"
+leipziger_strasse_117_zimmer_321:
+ street_name: "Leipziger Straße"
+ street_number: "117"
+ supplement: "Zimmer 321"
+lilienweg_14:
+ street_name: "Lilienweg"
+ street_number: "14"
+ supplement: ""
+lilienweg_4:
+ street_name: "Lilienweg"
+ street_number: "4"
+ supplement: ""
+richard_strauss_strasse_4:
+ street_name: "Richard Strauß Straße"
+ street_number: "4"
+ supplement: ""
+mittelstrasse_6:
+ street_name: "Mittelstrasse"
+ street_number: "6"
+ supplement: ""
+hauptstr_6:
+ street_name: "Hauptstr."
+ street_number: "6"
+ supplement: ""
+alte_dorfstraße_4:
+ street_name: "Alte Dorfstraße"
+ street_number: "4"
+ supplement: ""
+alfons_mitnacht_str_5:
+ street_name: "Alfons-Mitnacht Str."
+ street_number: "5"
+ supplement: ""
+seilerweg_5:
+ street_name: "Seilerweg"
+ street_number: "5"
+ supplement: ""
+aegirsvej_4:
+ street_name: "Ægirsvej"
+ street_number: "4"
+ supplement: ""
+hilgartshausener_hauptstrasse_49:
+ street_name: "Hilgartshausener Hauptstraße"
+ street_number: "49"
+ supplement: ""
+erich_weinert_strasse_87:
+ street_name: "erich-weinert-strasse"
+ street_number: "87"
+ supplement: ""
+m4_8:
+ street_name: "M4"
+ street_number: "8"
+ supplement: ""
+strasse_1:
+ street_name: "1.Straße"
+ street_number: ""
+ supplement: ""
+wiesencenter_bayreuther_strasse_108_2_stock:
+ street_name: "Bayreuther Str."
+ street_number: "108"
+ supplement: "Wiesentcenter 2. Stock"
+neue_strasse_28_1_stock:
+ street_name: "Neue Straße"
+ street_number: "28"
+ supplement: "1.Stock"
+kirchengasse_7_1_stock_zi_4:
+ street_name: "Kirchengasse"
+ street_number: "7"
+ supplement: "1. Stock Zi.Nr. 4"
+pallaswiesenstr_57_App_235:
+ street_name: "Pallaswiesenstr."
+ street_number: "57"
+ supplement: "App. 235"
+neue_str_55_whg_3:
+ street_name: "Neue Str."
+ street_number: "55"
+ supplement: "Whg. 3"
+apenrader_str_16_whg_3:
+ street_name: "Apenrader Str."
+ street_number: "16"
+ supplement: "Whg. 3"
+d_6_2:
+ street_name: "D 6"
+ street_number: "2"
+ supplement: ""
+r4_7:
+ street_name: "R4"
+ street_number: "7"
+ supplement: ""
+lieblgasse_2_41_7_21:
+ street_name: "Lieblgasse"
+ street_number: "2/41/7/21"
+ supplement: ""
+1752_oto_iwatsukiku:
+ street_name: "Oto"
+ street_number: "1752"
+ supplement: "Iwatsukiku"
+3940_radio_road_unit_110:
+ street_name: "Radio Road"
+ street_number: "3940"
+ supplement: "Unit 110"
+1101_madison_st_600:
+ street_name: "Madison St"
+ street_number: "1101"
+ supplement: "# 600"
+1523_6th_ave:
+ street_name: "6th Ave"
+ street_number: "1523"
+ supplement: ""
+81_quai_charles_de_gaulle:
+ street_name: "quai Charles de Gaulle"
+ street_number: "81"
+ supplement: ""
+nafarroa_kalea_9:
+ street_name: "Nafarroa Kalea"
+ street_number: "9"
+ supplement: ""
+av_libertad_53:
+ street_name: "Av. Libertad"
+ street_number: "53"
+ supplement: ""
+vanzada_errepidea_1:
+ street_name: "vanzada Errepidea"
+ street_number: "1"
+ supplement: ""
+88_century_blvd_pudong:
+ street_name: "Century Blvd"
+ street_number: "88"
+ supplement: "Pudong"
+mannerheimintie_13A2:
+ street_name: "Mannerheimintie"
+ street_number: "13A2"
+ supplement: ""
+mannerheimintie_13_A2:
+ street_name: "Mannerheimintie"
+ street_number: "13 A2"
+ supplement: ""
+mannerheimintie_13_A_2:
+ street_name: "Mannerheimintie"
+ street_number: "13 A 2"
+ supplement: ""
+7_place_de_l_hotel_de_ville:
+ street_name: "place de l'Hôtel de Ville"
+ street_number: "7"
+ supplement: ""
+488_west_57_street:
+ street_name: "West 57 Street"
+ street_number: "488"
+ supplement: ""
+574_e_10th_street:
+ street_name: "E 10th Street"
+ street_number: "574"
+ supplement: ""
+neuhof_13_15:
+ street_name: "Neuhof"
+ street_number: "13 / 15"
+ supplement: ""
+no_133_shangdong_st:
+ street_name: "Shangdong St."
+ street_number: "133"
+ supplement: ""
+56_route_de_geneve:
+ street_name: "route de Genève"
+ street_number: "56"
+ supplement: ""
+no_59_yangfangdian_xi:
+ street_name: "Yangfangdian Xi"
+ street_number: "59"
+ supplement: ""
+514_3_daechi_dong:
+ street_name: "Daechi-Dong"
+ street_number: "514-3"
+ supplement: ""
+san_millan_3_10:
+ street_name: "San Millán"
+ street_number: "3-10"
+ supplement: ""
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/AddressTest/providers/splitStreet.yaml b/app/code/community/Netresearch/OPS/Test/Helper/AddressTest/providers/splitStreet.yaml
new file mode 100644
index 0000000..1e511ff
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/AddressTest/providers/splitStreet.yaml
@@ -0,0 +1,105 @@
+thunstrasse_39:
+ - "Thunstraße 39"
+nonnenstrasse:
+ - "Nonnenstraße"
+tulpenweg:
+ - "Tulpenweg"
+tulpenweg_:
+ - "Tulpenweg"
+nonnenstrasse_11c:
+ - "Nonnenstraße 11c"
+nonnenstrasse11c:
+ - "Nonnenstraße11c"
+nonnenstrasse_44_46:
+ - "Nonnenstraße 44-46"
+nonnenstrasse_44_46_haus_c:
+ - "Nonnenstraße 44-46 Haus C"
+leipziger_strasse_117_zimmer_321:
+ - "Leipziger Straße 117, Zimmer 321"
+lilienweg_14:
+ - "Lilienweg 14"
+lilienweg_4:
+ - "Lilienweg 4"
+richard_strauss_strasse_4:
+ - "Richard Strauß Straße 4"
+mittelstrasse_6:
+ - "Mittelstrasse 6"
+hauptstr_6:
+ - "Hauptstr. 6"
+alte_dorfstraße_4:
+ - "Alte Dorfstraße 4"
+alfons_mitnacht_str_5:
+ - "Alfons-Mitnacht Str. 5"
+seilerweg_5:
+ - "Seilerweg 5"
+aegirsvej_4:
+ - "Ægirsvej 4"
+hilgartshausener_hauptstrasse_49:
+ - "Hilgartshausener Hauptstraße 49"
+erich_weinert_strasse_87:
+ - "erich-weinert-strasse 87"
+m4_8:
+ - "M4 8"
+strasse_1:
+ - "1.Straße"
+wiesencenter_bayreuther_strasse_108_2_stock:
+ - "Wiesentcenter, Bayreuther Str. 108, 2. Stock"
+neue_strasse_28_1_stock:
+ - "Neue Straße 28 / 1.Stock"
+kirchengasse_7_1_stock_zi_4:
+ - "Kirchengasse 7, 1. Stock Zi.Nr. 4"
+pallaswiesenstr_57_App_235:
+ - "Pallaswiesenstr. 57 App. 235"
+neue_str_55_whg_3:
+ - "Neue Str. 55, Whg. 3"
+apenrader_str_16_whg_3:
+ - "Apenrader Str. 16 / Whg. 3"
+d_6_2:
+ - "D 6, 2"
+r4_7:
+ - "R4, 7"
+lieblgasse_2_41_7_21:
+ - "Lieblgasse 2/41/7/21"
+1752_oto_iwatsukiku:
+ - "1752 Oto, Iwatsukiku"
+3940_radio_road_unit_110:
+ - "3940 Radio Road, Unit 110"
+1101_madison_st_600:
+ - "1101 Madison St # 600"
+1523_6th_ave:
+ - "1523 6th Ave"
+81_quai_charles_de_gaulle:
+ - "81, quai Charles de Gaulle"
+nafarroa_kalea_9:
+ - "Nafarroa Kalea 9"
+av_libertad_53:
+ - "Av. Libertad 53"
+vanzada_errepidea_1:
+ - "vanzada Errepidea 1"
+88_century_blvd_pudong:
+ - "88 Century Blvd, Pudong"
+mannerheimintie_13A2:
+ - "Mannerheimintie 13A2"
+mannerheimintie_13_A2:
+ - "Mannerheimintie 13 A2"
+mannerheimintie_13_A_2:
+ - "Mannerheimintie 13 A 2"
+7_place_de_l_hotel_de_ville:
+ - "7, place de l'Hôtel de Ville"
+488_west_57_street:
+ - "488 West 57 Street"
+574_e_10th_street:
+ - "574 E 10th Street"
+neuhof_13_15:
+ - "Neuhof 13 / 15"
+no_133_shangdong_st:
+ - "No. 133 Shangdong St."
+56_route_de_geneve:
+ - "56, route de Genève"
+no_59_yangfangdian_xi:
+ - "No. 59 Yangfangdian Xi"
+514_3_daechi_dong:
+ - "514-3, Daechi-Dong"
+san_millan_3_10:
+ - "San Millán, 3-10"
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/AliasTest.php b/app/code/community/Netresearch/OPS/Test/Helper/AliasTest.php
new file mode 100644
index 0000000..e6df1e6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/AliasTest.php
@@ -0,0 +1,763 @@
+_helper = Mage::helper('ops/alias');
+ $this->store = Mage::app()->getStore(0)->load(0);
+ $this->mockSessions();
+ }
+
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'checkout/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+
+ protected function mockCheckoutOnepage($method)
+ {
+ $onepage = $this->getModelMock('checkout/type_onepage', array('getCheckoutMethod'));
+ $onepage->expects($this->any())
+ ->method('getCheckoutMehtod')
+ ->will($this->returnValue($method));
+ $this->replaceByMock('singleton', 'checkout/type_onepage', $onepage);
+ }
+
+
+
+ public function testGetOpsCode()
+ {
+ $this->assertEquals(null, Mage::helper('ops/alias')->getOpsCode());
+ }
+
+ public function testGetOpsBrand()
+ {
+ $this->assertEquals(null, Mage::helper('ops/alias')->getOpsBrand());
+ }
+
+ public function testSaveAliasIfCustomerIsNotLoggedIn()
+ {
+ $this->mockCheckoutOnepage(Mage_Checkout_Model_Type_Onepage::METHOD_GUEST);
+ $quote = Mage::getModel('sales/quote');
+ $this->assertEquals(
+ null,
+ $this->_helper->saveAlias(
+ array(
+ 'OrderID' => 4711,
+ 'StorePermanently' => 'N'
+ )
+ )
+ );
+ }
+
+ public function testSaveAliasIfCustomerIsLoggedIn()
+ {
+ $this->mockCheckoutOnepage(Mage_Checkout_Model_Type_Onepage::METHOD_CUSTOMER);
+ /** @var Mage_Sales_Model_Quote $quote */
+ $quote = $this->getModelMock('sales/quote', array('save'));
+ $this->replaceByMock('model', 'sales/quote', $quote);
+ $quote->setBillingAddress($this->getAddressData());
+ $quote->setShippingAddress($this->getAddressData());
+ $quote->setId(4711);
+ $customer = Mage::getModel('customer/customer');
+ $customer->setId(1);
+ $aliasData['Alias_OrderId'] = 4711;
+ $aliasData['Alias_AliasId'] = 4711;
+ $aliasData['Card_Brand'] = 'Visa';
+ $aliasData['Card_CardNumber'] = 'xxxx0815';
+ $aliasData['Card_ExpiryDate'] = '1212';
+ $aliasData['Card_CardHolderName'] = 'Foo Baar';
+ $aliasData['Alias_StorePermanently'] = 'Y';
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->setMethod('CreditCard');
+ $payment->setAdditionalInformation(array('saveOpsAlias' => '1'));
+// $quote->setCustomer($customer);
+ $quote->setPayment($payment);
+
+ $quoteMock = $this->getModelMock(
+ 'sales/quote', array('load', 'getPayment', 'getCustomer')
+ );
+ $quoteMock->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($quoteMock));
+ $quoteMock->expects($this->any())
+ ->method('getPayment')
+ ->will($this->returnValue($payment));
+ $quoteMock->expects($this->any())
+ ->method('getCustomer')
+ ->will($this->returnValue($customer));
+ $this->replaceByMock('model', 'sales/quote', $quoteMock);
+ $alias = $this->_helper->saveAlias($aliasData);
+ $this->assertEquals('4711', $alias->getAlias());
+ $this->assertEquals('Visa', $alias->getBrand());
+ $this->assertEquals('xxxx0815', $alias->getPseudoAccountOrCcNo());
+ $this->assertEquals('1212', $alias->getExpirationDate());
+ $this->assertEquals(
+ 'da39a3ee5e6b4b0d3255bfef95601890afd80709',
+ $alias->getBillingAddressHash()
+ );
+ $this->assertEquals(
+ 'da39a3ee5e6b4b0d3255bfef95601890afd80709',
+ $alias->getShippingAddressHash()
+ );
+ $this->assertEquals('CreditCard', $alias->getPaymentMethod());
+ $this->assertEquals(1, $alias->getCustomerId());
+
+ $oldAliasId = $alias->getId();
+ $alias = $this->_helper->saveAlias($aliasData, $quote);
+ $this->assertEquals($oldAliasId, $alias->getId());
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSaveAliasUpdate()
+ {
+ $this->mockCheckoutOnepage(Mage_Checkout_Model_Type_Onepage::METHOD_CUSTOMER);
+ $quote = $this->getModelMock('sales/quote', array('save'));
+ $this->replaceByMock('model', 'sales/quote', $quote);
+ $quote->setBillingAddress($this->getAddressData());
+ $quote->setShippingAddress($this->getAddressData());
+ $quote->setId(4711);
+ $customer = new Varien_Object();
+ $customer->setId(1);
+ $aliasData['Alias_OrderId'] = 4711;
+ $aliasData['Alias_AliasId'] = 4711;
+ $aliasData['Card_Brand'] = 'Visa';
+ $aliasData['Card_CardNumber'] = 'xxxx0815';
+ $aliasData['Card_ExpiryDate'] = '1212';
+ $aliasData['Card_CardHolderName'] = 'Foo Baar';
+ $aliasData['Alias_StorePermanently'] = 'Y';
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->setMethod('CreditCard');
+ $payment->setAdditionalInformation(array('saveOpsAlias' => '1'));
+// $quote->setCustomer($customer);
+ $quote->setPayment($payment);
+
+ $quoteMock = $this->getModelMock(
+ 'sales/quote', array('load', 'getPayment', 'getCustomer')
+ );
+ $quoteMock->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($quoteMock));
+ $quoteMock->expects($this->any())
+ ->method('getPayment')
+ ->will($this->returnValue($payment));
+ $quoteMock->expects($this->any())
+ ->method('getCustomer')
+ ->will($this->returnValue($customer));
+ $this->replaceByMock('model', 'sales/quote', $quoteMock);
+ $oldAlias = $this->_helper->saveAlias($aliasData);
+ $oldAlias->setState(Netresearch_OPS_Model_Alias_State::ACTIVE);
+ $oldAlias->save();
+
+ $aliasData['Alias_OrderId'] = 4711;
+ $aliasData['Alias_AliasId'] = 4711;
+ $aliasData['Card_Brand'] = 'Mastercard';
+ $aliasData['Card_CardNumber'] = 'xxxx01111';
+ $aliasData['Card_ExpiryDate'] = '1213';
+ $aliasData['Card_CardHolderName'] = 'Max Power';
+ $aliasData['Alias_StorePermanently'] = 'Y';
+
+ $updatedAlias = $this->_helper->saveAlias($aliasData);
+
+
+
+ $this->assertEquals(4711, $updatedAlias->getAlias());
+ $this->assertEquals('Mastercard', $updatedAlias->getBrand());
+ $this->assertEquals('xxxx01111', $updatedAlias->getPseudoAccountOrCcNo());
+ $this->assertEquals('1213', $updatedAlias->getExpirationDate());
+ $this->assertEquals('Max Power', $updatedAlias->getCardHolder());
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSaveNewAliasFromQuote()
+ {
+ $reflection_class = new ReflectionClass("Netresearch_OPS_Helper_Alias");
+ $method = $reflection_class->getMethod("saveNewAliasFromQuote");
+ $method->setAccessible(true);
+
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $aliasData = array(
+ 'Alias_AliasId' => 'TestAlias',
+ 'Card_ExpiryDate' => '12.12.0012',
+ 'Card_Brand' => 'Visa',
+ 'Card_CardNumber' => '12345678',
+ 'Card_CardHolderName' => 'Foo',
+ 'Alias_StorePermanently' => 'Y'
+ );
+ $aliasHelper = Mage::helper('ops/alias');
+ $alias = $method->invoke($aliasHelper, $quote, $aliasData);
+ $this->assertEquals('TestAlias', $alias->getAlias());
+ $this->assertEquals('12.12.0012', $alias->getExpirationDate());
+ $this->assertEquals('Foo', $alias->getCardHolder());
+ $this->assertEquals(Netresearch_OPS_Model_Alias_State::PENDING, $alias->getState());
+
+ $aliasData = array(
+ 'Alias_AliasId' => 'TestAlias',
+ 'Card_ExpiryDate' => '12.12.0012',
+ 'Card_Brand' => 'Visa',
+ 'Card_CardNumber' => '12345678',
+ 'Alias_StorePermanently' => 'Y'
+ );
+ $aliasHelper = Mage::helper('ops/alias');
+ $alias = $method->invoke($aliasHelper, $quote, $aliasData);
+ $this->assertEquals('TestAlias', $alias->getAlias());
+ $this->assertEquals('12.12.0012', $alias->getExpirationDate());
+ $this->assertEquals('Foo', $alias->getCardHolder());
+ $this->assertEquals(Netresearch_OPS_Model_Alias_State::PENDING, $alias->getState());
+
+ $aliasData = array(
+ 'Alias_AliasId' => 'TestAlias',
+ 'Card_ExpiryDate' => '12.12.0012',
+ 'Card_Brand' => 'Visa',
+ 'Card_CardNumber' => '12345678',
+ 'Card_CardHolderName' => '',
+ 'Alias_StorePermanently' => 'Y'
+ );
+ $aliasHelper = Mage::helper('ops/alias');
+ $alias = $method->invoke($aliasHelper, $quote, $aliasData);
+ $this->assertEquals('TestAlias', $alias->getAlias());
+ $this->assertEquals('12.12.0012', $alias->getExpirationDate());
+ $this->assertEquals('', $alias->getCardHolder());
+ $this->assertEquals(Netresearch_OPS_Model_Alias_State::PENDING, $alias->getState());
+ }
+
+
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSaveNewAliasFromOrder()
+ {
+ $reflection_class = new ReflectionClass("Netresearch_OPS_Helper_Alias");
+ $method = $reflection_class->getMethod("saveNewAliasFromOrder");
+ $method->setAccessible(true);
+
+ $order = Mage::getModel('sales/order')->load(11);
+
+
+
+ $aliasData = array(
+ 'alias' => 'TestAlias',
+ 'brand' => 'Visa',
+ 'cardno' => '12345678',
+ 'cn' => 'Foo',
+ 'Alias_StorePermanently' => 'Y',
+ 'ed' => '12.12.0012'
+ );
+
+
+ $aliasHelper = Mage::helper('ops/alias');
+ $alias = $method->invoke($aliasHelper, $order, $aliasData);
+ $this->assertEquals('TestAlias', $alias->getAlias());
+ $this->assertEquals('12.12.0012', $alias->getExpirationDate());
+ $this->assertEquals('Foo', $alias->getCardHolder());
+ $this->assertEquals(Netresearch_OPS_Model_Alias_State::ACTIVE, $alias->getState());
+
+ $aliasData = array(
+ 'alias' => 'TestAlias',
+ 'brand' => 'Visa',
+ 'cardno' => '12345678',
+ 'Alias_StorePermanently' => 'Y',
+ 'ed' => '12.12.0012',
+ 'cn' => null
+ );
+ $aliasHelper = Mage::helper('ops/alias');
+ $alias = $method->invoke($aliasHelper, $order, $aliasData);
+ $this->assertEquals('TestAlias', $alias->getAlias());
+ $this->assertEquals('12.12.0012', $alias->getExpirationDate());
+ $this->assertNull($alias->getCardHolder());
+ $this->assertEquals(Netresearch_OPS_Model_Alias_State::ACTIVE, $alias->getState());
+
+ $aliasData = array(
+ 'alias' => 'TestAlias',
+ 'brand' => 'Visa',
+ 'cardno' => '12345678',
+ 'Alias_StorePermanently' => 'Y',
+ 'ed' => '12.12.0012',
+ 'cn' => ''
+ );
+ $aliasHelper = Mage::helper('ops/alias');
+ $alias = $method->invoke($aliasHelper, $order, $aliasData);
+ $this->assertEquals('TestAlias', $alias->getAlias());
+ $this->assertEquals('12.12.0012', $alias->getExpirationDate());
+ $this->assertEquals('', $alias->getCardHolder());
+ $this->assertEquals(Netresearch_OPS_Model_Alias_State::ACTIVE, $alias->getState());
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testDeleteAlias()
+ {
+ $reflection_class = new ReflectionClass("Netresearch_OPS_Helper_Alias");
+ $method = $reflection_class->getMethod("deleteAlias");
+ $method->setAccessible(true);
+ $aliasModel = Mage::getModel('ops/alias');
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $quote->setBillingAddress($this->getAddressData());
+ $quote->setShippingAddress($this->getAddressData());
+ $customer = Mage::getModel('customer/customer');
+ $customer->setId(1);
+
+ $quote->setCustomer($customer);
+
+ $customerId = $quote->getCustomer()->getId();
+ $aliasesForCustomer = $aliasCollection = $aliasModel->getCollection()
+ ->addFieldToFilter('customer_id', $customerId)
+ ->load();
+ $oldAliasSize = count($aliasesForCustomer);
+
+ $aliasData = array(
+ 'Alias_AliasId' => '4711',
+ 'Card_ExpiryDate' => '0117',
+ 'Card_Brand' => 'Visa',
+ 'Card_CardNumber' => 'xxxx1111'
+ );
+ $aliasHelper = Mage::helper('ops/alias');
+ $method->invoke($aliasHelper, $quote, $aliasData);
+ $newAliasForCustomer = $aliasCollection = $aliasModel->getCollection()
+ ->addFieldToFilter('customer_id', $customerId)
+ ->load();
+ $newAliasSize = count($newAliasForCustomer);
+ $this->assertGreaterThan($newAliasSize, $oldAliasSize);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testDeleteAliasDoesNotDeleteAliasIfAddressDoesNotMatch()
+ {
+ $reflection_class = new ReflectionClass("Netresearch_OPS_Helper_Alias");
+ $method = $reflection_class->getMethod("deleteAlias");
+ $method->setAccessible(true);
+ $aliasModel = Mage::getModel('ops/alias');
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $customer = Mage::getModel('customer/customer');
+ $customer->setId(1);
+
+ $quote->setCustomer($customer);
+
+ $customerId = $quote->getCustomer()->getId();
+ $aliasesForCustomer = $aliasCollection = $aliasModel->getCollection()
+ ->addFieldToFilter('customer_id', $customerId)
+ ->load();
+ $oldAliasSize = count($aliasesForCustomer);
+
+ $aliasData = array(
+ 'Alias_AliasId' => '4711',
+ 'Card_ExpiryDate' => '0117',
+ 'Card_Brand' => 'Visa',
+ 'Card_CardNumber' => 'xxxx1111'
+ );
+ $aliasHelper = Mage::helper('ops/alias');
+ $method->invoke($aliasHelper, $quote, $aliasData);
+ $newAliasForCustomer = $aliasCollection = $aliasModel->getCollection()
+ ->addFieldToFilter('customer_id', $customerId)
+ ->load();
+ $newAliasSize = count($newAliasForCustomer);
+ $this->assertEquals($newAliasSize, $oldAliasSize);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testGetAliasesForCustomer()
+ {
+ $quote = Mage::getModel('sales/quote')->load(10);
+
+ $aliasesCollection = $this->_helper->getAliasesForCustomer(1);
+ $this->assertEquals(5, count($aliasesCollection));
+
+ $aliasesCollection = $this->_helper->getAliasesForCustomer(2);
+ $this->assertEquals(1, count($aliasesCollection));
+
+ $aliasesCollection = $this->_helper->getAliasesForCustomer(3);
+ $this->assertEquals(0, count($aliasesCollection));
+
+ $aliasesCollection = $this->_helper->getAliasesForCustomer(
+ null, $quote
+ );
+ $this->assertEquals(0, count($aliasesCollection));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ */
+ public function testIsAliasValidForAddresses()
+ {
+ $billingAddress = Mage::getModel('sales/quote_address');
+ $shippingAddress = Mage::getModel('sales/quote_address');
+ $this->assertFalse(
+ $this->_helper->isAliasValidForAddresses(
+ 1, '4711', $shippingAddress, $billingAddress
+ )
+ );
+
+ $billingAddress = $this->getAddressData();
+ $shippingAddress = $this->getAddressData();
+
+ $this->assertTrue(
+ $this->_helper->isAliasValidForAddresses(
+ 1, '4711', $shippingAddress, $billingAddress
+ )
+ );
+
+ $this->assertFalse(
+ $this->_helper->isAliasValidForAddresses(
+ 2, '4711', $shippingAddress, $billingAddress
+ )
+ );
+ }
+
+ protected function getAddressData()
+ {
+ $address = new Mage_Sales_Model_Quote_Address();
+ $address->setFirstname('foo');
+ $address->setLastname('bert');
+ $address->setStreet1('bla street 1');
+ $address->setZipcode('4711');
+ $address->setCity('Cologne');
+ $address->setCountry_id(1);
+ return $address;
+ }
+
+ public function testGenerateAddressHash()
+ {
+ $address = $this->getAddressData();
+ $this->assertEquals(
+ '1b9ecdf409e240717f04b7155712658ab09116bb',
+ $this->_helper->generateAddressHash($address)
+ );
+ $address->setData('street', array('wuseldusel', 'foo'));
+ $this->assertEquals(
+ '260a9287b2964d3674f49f589d5e5fd7143041cf',
+ $this->_helper->generateAddressHash($address)
+ );
+ }
+
+ public function testFormatAliasCardNo()
+ {
+ $helper = Mage::helper('ops/alias');
+ $cardNo = 'xxxxxxxxxxxx1111';
+ $cardType = 'VISA';
+ $this->assertEquals(
+ 'XXXX XXXX XXXX 1111',
+ $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+
+ $cardNo = 'xxxxxxxxxxxx9999';
+ $cardType = 'MasterCard';
+ $this->assertEquals(
+ 'XXXX XXXX XXXX 9999',
+ $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+
+ $cardNo = '3750-xxxxxx-03';
+ $cardType = 'american express';
+ $this->assertEquals(
+ '3750 XXXXXX 03', $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+
+ $cardNo = '3750-xxxxxx-03';
+ $cardType = 'DINERS CLUB';
+ $this->assertEquals(
+ '3750 XXXXXX 03', $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+
+
+ $cardNo = '675941-XXXXXXXX-08';
+ $cardType = 'MaestroUK';
+ $this->assertEquals(
+ '675941 XXXXXXXX 08', $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+
+ $cardNo = '675956-XXXXXXXX-54';
+ $cardType = 'MaestroUK';
+ $this->assertEquals(
+ '675956 XXXXXXXX 54', $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+
+ $cardNo = '564182-XXXXXXXX-69';
+ $cardType = 'MaestroUK';
+ $this->assertEquals(
+ '564182 XXXXXXXX 69', $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+
+ $cardNo = '3750-xxxxxx-03';
+ $cardType = 'PostFinance Card';
+ $this->assertEquals(
+ '3750-XXXXXX-03', $helper->formatAliasCardNo($cardType, $cardNo)
+ );
+ }
+
+ /**
+ *
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ */
+ public function testSetAliasToPayment()
+ {
+ $params = array();
+ $quote = Mage::getModel('sales/quote')->load(11);
+ $helper = Mage::helper('ops/alias');
+ $helper->setAliasToPayment($quote->getPayment(), $params);
+ $payment = $quote->getPayment();
+ $this->assertArrayNotHasKey('alias', $payment->getAdditionalInformation());
+ $this->assertArrayNotHasKey('cvc', $payment->getAdditionalInformation());
+
+ $params = array(
+ 'alias_aliasid' => '4711'
+ );
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $helper = Mage::helper('ops/alias');
+ $helper->setAliasToPayment($quote->getPayment(), $params);
+ $payment = $quote->getPayment();
+
+ $this->assertArrayHasKey('alias', $payment->getAdditionalInformation());
+ $this->assertEquals('4711', $payment->getAdditionalInformation('alias'));
+ $this->assertArrayNotHasKey('cvc', $payment->getAdditionalInformation());
+
+ $params = array(
+ 'alias_aliasid' => '4712',
+ 'card_cvc' => '123'
+ );
+
+ $dataHelperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $dataHelperMock->expects($this->any())
+ ->method('isAdminSession')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $helper = Mage::helper('ops/alias');
+ $helper->setAliasToPayment($quote->getPayment(), $params);
+ $payment = $quote->getPayment();
+ $this->assertEquals('4712', $payment->getAdditionalInformation('alias'));
+ $this->assertArrayHasKey('cvc', $payment->getAdditionalInformation());
+ $this->assertEquals('123', $payment->getAdditionalInformation('cvc'));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSetCardHolder()
+ {
+ $reflection_class = new ReflectionClass("Netresearch_OPS_Helper_Alias");
+ $method = $reflection_class->getMethod('setCardHolderToAlias');
+ $method->setAccessible(true);
+
+ $helperObject = Mage::helper('ops/alias');
+
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $quote->setBillingAddress($this->getAddressData());
+ $quote->setShippingAddress($this->getAddressData());
+
+ $oldAlias = Mage::getModel('ops/alias')->load(7);
+ $aliasData = array(
+ 'alias_aliasid' => '4712',
+ 'card_cvc' => '123',
+ 'Card_CardHolderName' => 'Max Muster'
+ );
+
+ $method->invoke($helperObject, $quote, $aliasData);
+ $updatedAlias = Mage::getModel('ops/alias')->load(7);
+ $this->assertEquals($aliasData['Card_CardHolderName'], $updatedAlias->getCardHolder());
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSetAliasActive()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $quote->setBillingAddress($this->getAddressData());
+ $quote->setShippingAddress($this->getAddressData());
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->setAdditionalInformation('alias', '4714');
+ $payment->setAdditionalInformation('userIsRegistering', false);
+ $orderPayment = $this->getModelMock('sales/order_payment', array('save'));
+ $orderPayment->setAdditionalInformation('alias', '4714');
+ $orderPayment->setAdditionalInformation('userIsRegistering', false);
+ $quote->setPayment($payment);
+ $order->setPayment($orderPayment);
+ $customer = Mage::getModel('customer/customer');
+ $customer->setId(1);
+ $quote->setCustomer($customer);
+ $billingAddressHash = Mage::helper('ops/alias')->generateAddressHash($quote->getBillingAddress());
+ $shippingAddressHash = Mage::helper('ops/alias')->generateAddressHash($quote->getShippingAddress());
+ $aliasesToDelete = Mage::getModel('ops/alias')
+ ->getCollection()
+ ->addFieldToFilter('customer_id', $quote->getCustomer()->getId())
+ ->addFieldToFilter('billing_address_hash', $billingAddressHash)
+ ->addFieldToFilter('shipping_address_hash', $shippingAddressHash)
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::ACTIVE);
+ $oldAlias = $aliasesToDelete->getFirstItem();
+ $helperMock = $this->getHelperMock('ops/alias', array('cleanUpAdditionalInformation'));
+ $helperMock->setAliasActive($quote, $order);
+ $aliasesToUpdate = Mage::getModel('ops/alias')
+ ->getCollection()
+ ->addFieldToFilter('customer_id', $quote->getCustomer()->getId())
+ ->addFieldToFilter('billing_address_hash', $billingAddressHash)
+ ->addFieldToFilter('shipping_address_hash', $shippingAddressHash)
+ ->addFieldToFilter('alias', '4714')
+ ->addFieldToFilter('state', Netresearch_OPS_Model_Alias_State::ACTIVE)
+ ->setOrder('created_at', Varien_Data_Collection::SORT_ORDER_DESC);
+ $newAlias = $aliasesToUpdate->getFirstItem();
+
+ $testAlias = Mage::getModel('ops/alias')->load($oldAlias->getId());
+ $this->assertEquals(null, $testAlias->getId());
+ $this->assertEquals('active', $newAlias->getState());
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSetAliasActiveWhenUserRegisters()
+ {
+ $order = $this->getModelMock('sales/order', array('getPayment'));
+ $quote = $this->getModelMock('sales/quote', array('getPayment'));
+ $quote->setBillingAddress($this->getAddressData());
+ $quote->setShippingAddress($this->getAddressData());
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->setAdditionalInformation('alias', '4714');
+ $payment->setAdditionalInformation('userIsRegistering', true);
+ $orderPayment = $this->getModelMock('sales/order_payment', array('save'));
+ $orderPayment->setAdditionalInformation('alias', '4714');
+ $orderPayment->setAdditionalInformation('userIsRegistering', true);
+ $quote->expects($this->any())
+ ->method('getPayment')
+ ->will($this->returnValue($payment));
+
+ $order->expects($this->any())
+ ->method('getPayment')
+ ->will($this->returnValue($orderPayment));
+ $customer = Mage::getModel('customer/customer');
+ $customer->setId(1);
+ $quote->setCustomer($customer);
+ $helperMock = $this->getHelperMock('ops/alias', array('cleanUpAdditionalInformation', 'setAliasToActiveAfterUserRegisters'));
+ $helperMock->expects($this->once())
+ ->method('setAliasToActiveAfterUserRegisters')
+ ->with($order, $quote);
+
+ $helperMock->setAliasActive($quote, $order);
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSetAliasToActiveAfterUserRegisters()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->setCustomerId(123);
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $quote->setBillingAddress($this->getAddressData());
+ $quote->setShippingAddress($this->getAddressData());
+ $quote->getPayment()->setAdditionalInformation('alias', '4714');
+ $quote->getPayment()->setAdditionalInformation('opsAliasId', '11111');
+ $quote->getPayment()->setAdditionalInformation('userIsRegistering', true);
+ $quote->setCheckoutMethod(Mage_Sales_Model_Quote::CHECKOUT_METHOD_REGISTER);
+ $quote->setStoreId(null);
+ $billingAddressHash = Mage::helper('ops/alias')->generateAddressHash($quote->getBillingAddress());
+ $shippingAddressHash = Mage::helper('ops/alias')->generateAddressHash($quote->getShippingAddress());
+
+ $oldAlias = Mage::getModel('ops/alias')->getCollection()
+ ->addFieldToFilter('alias', $quote->getPayment()->getAdditionalInformation('alias'))
+ ->addFieldToFilter('billing_address_hash', $billingAddressHash)
+ ->addFieldToFilter('shipping_address_hash', $shippingAddressHash)
+ ->getFirstItem();
+
+ Mage::helper('ops/alias')->setAliasToActiveAfterUserRegisters($order, $quote);
+ $testAlias = Mage::getModel('ops/alias')->load($oldAlias->getId());
+ $this->assertEquals(Netresearch_OPS_Model_Alias_State::ACTIVE, $testAlias->getState());
+ $this->assertEquals(123, $testAlias->getCustomerId());
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/aliases.yaml
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testCleanUpAdditionalInformation()
+ {
+ $quote = Mage::getModel('sales/quote')->load(11);
+ $payment = $quote->getPayment();
+ $payment->setAdditionalInformation('cvc', 'cvctest');
+ $payment->setAdditionalInformation('storedOPSId', 'storedOPSIdTest');
+
+
+
+ $this->assertTrue(array_key_exists('cvc', $payment->getAdditionalInformation()));
+ $this->assertTrue(array_key_exists('storedOPSId', $payment->getAdditionalInformation()));
+
+ Mage::helper('ops/alias')->cleanUpAdditionalInformation($payment);
+
+ $this->assertTrue(is_array($payment->getAdditionalInformation()));
+ $this->assertFalse(array_key_exists('cvc', $payment->getAdditionalInformation()));
+ $this->assertFalse(array_key_exists('storedOPSId', $payment->getAdditionalInformation()));
+
+ $quote = Mage::getModel('sales/quote')->load(11);
+ $payment = $quote->getPayment();
+ $payment->setAdditionalInformation('cvc', 'cvctest');
+ $payment->setAdditionalInformation('storedOPSId', 'storedOPSIdTest');
+
+
+
+ $this->assertTrue(array_key_exists('cvc', $payment->getAdditionalInformation()));
+ $this->assertTrue(array_key_exists('storedOPSId', $payment->getAdditionalInformation()));
+
+ Mage::helper('ops/alias')->cleanUpAdditionalInformation($payment, true);
+
+ $this->assertTrue(is_array($payment->getAdditionalInformation()));
+ $this->assertFalse(array_key_exists('cvc', $payment->getAdditionalInformation()));
+ $this->assertTrue(array_key_exists('storedOPSId', $payment->getAdditionalInformation()));
+ }
+
+ /**
+ */
+ public function testCleanUpAdditionalInformationWithSave()
+ {
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->expects($this->once())
+ ->method('save');
+
+ Mage::helper('ops/alias')->cleanUpAdditionalInformation($payment, true, true);
+
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/AliasTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/AliasTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/ApiTest.php b/app/code/community/Netresearch/OPS/Test/Helper/ApiTest.php
new file mode 100644
index 0000000..14047d9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/ApiTest.php
@@ -0,0 +1,52 @@
+getAcceptRedirectRoute();
+ $this->assertEquals(
+ $successRoute, $helper->getRedirectRouteFromStatus(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT
+ )
+ );
+
+ $cancelRoute = $configModel->getCancelRedirectRoute();
+ $this->assertEquals(
+ $cancelRoute, $helper->getRedirectRouteFromStatus(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_CANCEL
+ )
+ );
+
+ $declineRoute = $configModel->getDeclineRedirectRoute();
+ $this->assertEquals(
+ $declineRoute, $helper->getRedirectRouteFromStatus(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_DECLINE
+ )
+ );
+
+ $exceptionRoute = $configModel->getExceptionRedirectRoute();
+ $this->assertEquals(
+ $exceptionRoute, $helper->getRedirectRouteFromStatus(
+ Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_EXCEPTION
+ )
+ );
+
+ try {
+ $helper->getRedirectRouteFromStatus('');
+ } catch (Exception $e) {
+ $this->assertEquals('invalid status provided', $e->getMessage());
+ }
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/DataTest.php b/app/code/community/Netresearch/OPS/Test/Helper/DataTest.php
new file mode 100644
index 0000000..d54cdcc
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/DataTest.php
@@ -0,0 +1,170 @@
+helper = Mage::helper('ops');
+ $this->store = Mage::app()->getStore(0)->load(0);
+ }
+
+ /**
+ * @test
+ */
+ public function getModuleVersionString()
+ {
+ $path = 'modules/Netresearch_OPS/version';
+
+ Mage::getConfig()->setNode($path, '12.03.01');
+ $this->assertSame('OGmg120301', $this->helper->getModuleVersionString());
+
+ Mage::getConfig()->setNode($path, '12.06.12+383');
+ $this->assertSame('OGmg120612', $this->helper->getModuleVersionString());
+
+ Mage::getConfig()->setNode($path, '12.09.12-beta2+808');
+ $this->assertSame('OGmg120912', $this->helper->getModuleVersionString());
+
+ $this->store->resetConfig();
+ }
+
+ public function testCheckIfUserIsRegistering()
+ {
+ $quote = new Varien_Object();
+ $quote->setCheckoutMethod(Mage_Sales_Model_Quote::CHECKOUT_METHOD_REGISTER);
+ $sessionMock = $this->getModelMock('checkout/session', array('getQuote', 'init', 'save'));
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($quote));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+
+ $this->assertTrue(Mage::helper('ops/data')->checkIfUserIsRegistering());
+
+ $quote->setCheckoutMethod(Mage_Sales_Model_Quote::CHECKOUT_METHOD_LOGIN_IN);
+ $this->assertTrue(Mage::helper('ops/data')->checkIfUserIsRegistering());
+
+ $quote->setCheckoutMethod(Mage_Sales_Model_Quote::CHECKOUT_METHOD_GUEST);
+ $this->assertFalse(Mage::helper('ops/data')->checkIfUserIsRegistering());
+
+ }
+
+ public function testCheckIfUserIsNotRegistering()
+ {
+ $quote = new Varien_Object();
+ $quote->setCheckoutMethod(Mage_Sales_Model_Quote::CHECKOUT_METHOD_REGISTER);
+ $sessionMock = $this->getModelMock('checkout/session', array('getQuote', 'init', 'save'));
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($quote));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+ $this->assertTrue(Mage::helper('ops/data')->checkIfUserIsNotRegistering());
+
+ $quote->setCheckoutMethod(Mage_Sales_Model_Quote::CHECKOUT_METHOD_LOGIN_IN);
+ $this->assertFalse(Mage::helper('ops/data')->checkIfUserIsNotRegistering());
+
+ $quote->setCheckoutMethod(Mage_Sales_Model_Quote::CHECKOUT_METHOD_GUEST);
+ $this->assertFalse(Mage::helper('ops/data')->checkIfUserIsNotRegistering());
+ }
+
+ public function testClearMsg()
+ {
+ $helper = Mage::helper('ops/data');
+ $testArray = array('cvc' => '1', 'CVC' => '2', 'test' => 'me');
+ $testArray = $helper->clearMsg($testArray);
+ $this->assertFalse(array_key_exists('cvc', $testArray));
+ $this->assertFalse(array_key_exists('CVC', $testArray));
+ $this->assertTrue(array_key_exists('test', $testArray));
+ $testString = '{"CVC":"123"}';
+ $this->assertFalse(strpos($helper->clearMsg($testString), 'CVC'));
+ $testString = '{"CVC":"123","CN":"Some Name"}';
+ $this->assertFalse(strpos($helper->clearMsg($testString), 'CVC'));
+ $testString = '{"cvc":"123","CN":"Some Name"}';
+ $this->assertFalse(strpos($helper->clearMsg($testString), 'cvc'));
+ $this->assertTrue(false !== strpos($helper->clearMsg($testString), 'CN'));
+
+ $testString = 'a:3:{s:5:"Alias";s:14:"10290855992990";s:3:"CVC";s:3:"777";s:2:"CN";s:13:"Homer Simpson";}';
+ $this->assertFalse(strpos($helper->clearMsg($testString), 'CVC'));
+ $this->assertTrue(false !== strpos($helper->clearMsg($testString), 'Homer'));
+ }
+
+ /**
+ * @test
+ */
+ public function sendNoMail()
+ {
+ $documentMock = $this->getMockBuilder('Mage_Sales_Model_Order_Shipment')
+ ->setMethods(array('getEmailSent'))
+ ->getMock();
+ $documentMock
+ ->expects($this->never())
+ ->method('getEmailSent');
+
+ Mage::helper('ops/data')->sendTransactionalEmail($documentMock);
+ }
+
+ /**
+ * @test
+ */
+ public function sendOrderEmail()
+ {
+ $orderMock = $this->getModelMock(
+ 'sales/order', array(
+ 'getEmailSent', 'getCanSendNewEmailFlag', 'sendNewOrderEmail'
+ )
+ );
+ $orderMock
+ ->expects($this->exactly(3))
+ ->method('getEmailSent')
+ ->willReturnOnConsecutiveCalls(true, false, false);
+ $orderMock
+ ->expects($this->exactly(2))
+ ->method('getCanSendNewEmailFlag')
+ ->willReturnOnConsecutiveCalls(false, true);
+ $orderMock
+ ->expects($this->once())
+ ->method('sendNewOrderEmail');
+ $this->replaceByMock('model', 'sales/order', $orderMock);
+
+ $order = Mage::getModel('sales/order');
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ }
+
+ /**
+ * @test
+ */
+ public function sendInvoiceEmail()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getSendInvoice'));
+ $configMock
+ ->expects($this->exactly(2))
+ ->method('getSendInvoice')
+ ->willReturnOnConsecutiveCalls(false, true);
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $invoiceMock = $this->getModelMock(
+ 'sales/order_invoice', array(
+ 'getEmailSent', 'sendEmail'
+ )
+ );
+ $invoiceMock
+ ->expects($this->exactly(3))
+ ->method('getEmailSent')
+ ->willReturnOnConsecutiveCalls(true, false, false);
+ $invoiceMock
+ ->expects($this->once())
+ ->method('sendEmail');
+ $this->replaceByMock('model', 'sales/order', $invoiceMock);
+
+ $order = Mage::getModel('sales/order');
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ Mage::helper('ops/data')->sendTransactionalEmail($order);
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest.php b/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest.php
new file mode 100644
index 0000000..73eac59
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest.php
@@ -0,0 +1,144 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Helper_DirectDebitTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+
+ /**
+ * @return Netresearch_OPS_Helper_DirectDebit
+ */
+ protected function getDirectDebitHelper()
+ {
+ return Mage::helper('ops/directDebit');
+ }
+
+
+ public function testGetDataHelper()
+ {
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getDataHelper() instanceof
+ Netresearch_OPS_Helper_Data
+ );
+ }
+
+ public function testSetDataHelper()
+ {
+ $this->getDirectDebitHelper()->setDataHelper(Mage::helper('ops/data'));
+
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getDataHelper() instanceof
+ Netresearch_OPS_Helper_Data
+ );
+ }
+
+ public function testGetQuoteHelper()
+ {
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getQuoteHelper() instanceof
+ Netresearch_OPS_Helper_Quote
+ );
+ }
+
+ public function testSetQuoteHelper()
+ {
+ $this->getDirectDebitHelper()->setQuoteHelper(Mage::helper('ops/quote'));
+
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getQuoteHelper() instanceof
+ Netresearch_OPS_Helper_Quote
+ );
+ }
+
+ public function testGetOrderHelper()
+ {
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getOrderHelper() instanceof
+ Netresearch_OPS_Helper_Order
+ );
+ }
+
+ public function testSetOrderHelper()
+ {
+ $this->getDirectDebitHelper()->setOrderHelper(Mage::helper('ops/order'));
+
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getOrderHelper() instanceof
+ Netresearch_OPS_Helper_Order
+ );
+ }
+
+ public function testGetCustomerHelper()
+ {
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getCustomerHelper() instanceof
+ Mage_Customer_Helper_Data
+ );
+ }
+
+ public function testSetCustomerHelper()
+ {
+ $this->getDirectDebitHelper()->setCustomerHelper(Mage::helper('customer/data'));
+
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->getCustomerHelper() instanceof
+ Mage_Customer_Helper_Data
+ );
+ }
+
+ public function testHandleAdminPayment()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $this->assertTrue(
+ $this->getDirectDebitHelper()->handleAdminPayment($quote, array())
+ instanceof Netresearch_OPS_Helper_DirectDebit
+ );
+ }
+
+ /**
+ * @loadFixture orders.yaml
+ */
+ public function testGetPaymentSpecificParamsForFrontend()
+ {
+ $this->mockSessions();
+ $order = Mage::getModel('sales/order')->load(1);
+ $quote = Mage::getModel('sales/quote')->load(1);
+ $helper = $this->getDirectDebitHelper();
+ $params = array(
+ 'country_id' => 'de',
+ 'CN' => 'Account Holder',
+ 'account' => '1234567',
+ 'bankcode' => '1234567'
+ );
+ $result = $helper->getDirectLinkRequestParams($quote, $order, $params);
+
+ $this->assertTrue((isset($result['BRAND'])) && $result['BRAND'] = "Direct Debits DE");
+ $this->assertTrue((isset($result['PM'])) && $result['PM'] = "Direct Debits DE");
+ $this->assertTrue((isset($result['ALIAS'])) && $result['ALIAS'] = "0000000012385139");
+ }
+
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('admin/session')
+ ->disableOriginalConstructor()
+ ->getMock();
+ $this->replaceByMock('singleton', 'admin/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('core/session')
+ ->disableOriginalConstructor()
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest/fixtures/orders.yaml
new file mode 100644
index 0000000..6c6259c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/DirectDebitTest/fixtures/orders.yaml
@@ -0,0 +1,79 @@
+tables:
+ sales/order:
+ - entity_id: 1
+ increment_id: 100000001
+ shipping_address_id: 1
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 1
+ store_id: 0
+
+ sales/quote:
+ - entity_id: 1
+ orig_order_id: 1
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+
+ sales/quote_payment:
+ - payment_id: 1
+ quote_id: 1
+ updated_at: '1970-01-01'
+ method: 'ops_directDebit'
+ additional_information: a:5:{s:5:"alias";s:16:"0000000012385139";s:10:"country_id";s:2:"DE";s:10:"opsAliasId";s:2:"21";s:8:"CC_BRAND";s:16:"Direct Debits DE";s:5:"CC_CN";s:4:"asda";}
+
+
+ sales/order_payment:
+ - entity_id: 1
+ parent_id: 1
+ method: 'ops_directDebit'
+
+
+ sales/shipment:
+ - entity_id: 1
+ increment_id: 100000001
+ order_id: 1
+ shipping_address_id: 42
+
+ sales/order_address:
+ - entity_id: 1
+ parent_id: 1
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 2
+ parent_id: 1
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/DirectLinkTest.php b/app/code/community/Netresearch/OPS/Test/Helper/DirectLinkTest.php
new file mode 100644
index 0000000..9653e71
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/DirectLinkTest.php
@@ -0,0 +1,562 @@
+_helper = Mage::helper('ops/directlink');
+ $transaction = Mage::getModel('sales/order_payment_transaction');
+ $transaction->setAdditionalInformation(
+ 'arrInfo', serialize(
+ array(
+ 'amount' => '184.90'
+ )
+ )
+ );
+ $transaction->setIsClosed(0);
+ $this->_transaction = $transaction;
+ $this->_order = Mage::getModel('sales/order');
+ $this->_order->setGrandTotal('184.90');
+ $this->_order->setBaseGrandTotal('184.90');
+ }
+
+ public function testDeleteActions()
+ {
+ $this->assertFalse(
+ $this->_helper->isValidOpsRequest(
+ $this->_transaction,
+ $this->_order,
+ array('STATUS'=> Netresearch_OPS_Model_Status::PAYMENT_DELETED)
+ )
+ );
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, array('STATUS'=> Netresearch_OPS_Model_Status::PAYMENT_DELETION_PENDING)));
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, array('STATUS'=> Netresearch_OPS_Model_Status::PAYMENT_DELETION_UNCERTAIN)));
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, array('STATUS'=> Netresearch_OPS_Model_Status::PAYMENT_DELETION_REFUSED)));
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, array('STATUS'=> Netresearch_OPS_Model_Status::PAYMENT_DELETION_OK)));
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, array('STATUS'=> Netresearch_OPS_Model_Status::DELETION_HANDLED_BY_MERCHANT)));
+ }
+
+ public function testRefundActions()
+ {
+
+ $opsRequest = array(
+ 'STATUS' => Netresearch_OPS_Model_Status::REFUNDED,
+ 'amount' => '184.90'
+ );
+ $this->assertFalse($this->_helper->isValidOpsRequest(null, $this->_order, $opsRequest), 'Refund should not be possible without open transactions');
+ $this->assertTrue($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, $opsRequest), 'Refund should be possible with open transactions');
+ $opsRequest['amount'] = '14.90';
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, $opsRequest), 'Refund should NOT be possible because of differing amount');
+ }
+
+ public function testCancelActions()
+ {
+ $opsRequest = array(
+ 'STATUS' => Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED,
+ 'amount' => '184.90'
+ );
+ $this->assertFalse($this->_helper->isValidOpsRequest(null, $this->_order, $opsRequest), 'Cancel should not be possible without open transactions');
+ $this->assertTrue($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, $opsRequest), 'Cancel should be possible with open transactions');
+ $opsRequest['amount'] = '14.90';
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, $opsRequest), 'Cancel should NOT be possible because of differing amount');
+ }
+
+ public function testCaptureActions()
+ {
+ $opsRequest = array(
+ 'STATUS' => Netresearch_OPS_Model_Status::PAYMENT_REQUESTED,
+ 'amount' => '184.90'
+ );
+ $this->assertTrue($this->_helper->isValidOpsRequest(null, $this->_order, $opsRequest), 'Capture should be possible because of no open transactions and matching amount');
+ $opsRequest['amount'] = '14.90';
+ $this->assertFalse($this->_helper->isValidOpsRequest($this->_transaction, $this->_order, $opsRequest), 'Capture should NOT be possible because of differing amount');
+ }
+
+ public function testCleanupParameters()
+ {
+ $expected = 123.45;
+ $result = $this->_helper->formatAmount('123.45');
+ $this->assertEquals($expected, $result);
+
+ $result = $this->_helper->formatAmount('\'123.45\'');
+ $this->assertEquals($expected, $result);
+
+ $result = $this->_helper->formatAmount('"123.45"');
+ $this->assertEquals($expected, $result);
+
+ $expected = $this->_helper->formatAmount(0.3);
+ $result = $this->_helper->formatAmount(0.1 + 0.2);
+ $this->assertEquals($expected . '', $result . '');
+ $this->assertEquals((float) $expected, (float) $result);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackCaptureSuccess()
+ {
+ $rssSession = $this->mockSession('rss/session')->disableOriginalConstructor();
+ $this->replaceByMock('model', 'rss/session', $rssSession);
+ $adminSession = $this->mockSession('admin/session')->disableOriginalConstructor();
+ $this->replaceByMock('model', 'admin/session', $adminSession);
+ $this->mockEmailHelper($this->once());
+
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation('status', 9);
+ return $order->getPayment();
+ };
+
+ $captureHelper = $this->getHelperMock('ops/order_capture', array('acceptCapture'));
+ $captureHelper->expects($this->any())
+ ->method('acceptCapture')
+ ->will($this->returnCallback($closure));
+ $this->replaceByMock('helper', 'ops/order_capture', $captureHelper);
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::PAYMENT_REQUESTED);
+ $directlinkHelperMock->processFeedback($order, $params);
+ $this->assertEquals(9, $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackRefundSuccess()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $mock = $this->getModelMock('sales/order', array('getBillingAddress'));
+ $mock->expects($this->any())
+ ->method('getBillingAddress')
+ ->will($this->returnValue(new Varien_Object()));
+ $this->replaceByMock('model', 'sales/order', $mock);
+
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::REFUNDED, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $this->assertEquals($params['STATUS'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackRefundWithStatusEightyFiveSuccess()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation(
+ 'status',
+ Netresearch_OPS_Model_Status::REFUND_PROCESSED_BY_MERCHANT
+ );
+ return $order->getPayment();
+ };
+
+ $refundHelper = $this->getHelperMock('ops/order_refund', array('createRefund'));
+ $refundHelper->expects($this->any())
+ ->method('createRefund')
+ ->will($this->returnCallback($closure));
+ $this->replaceByMock('helper', 'ops/order_refund', $refundHelper);
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::REFUND_PROCESSED_BY_MERCHANT, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $this->assertEquals($params['STATUS'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackPaymentWaiting()
+ {
+ $this->mockEmailHelper($this->once());
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $cntBefore = $order->getStatusHistoryCollection()->count();
+
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation(
+ 'status',
+ Netresearch_OPS_Model_Status::PAYMENT_PROCESSING
+ );
+ return $order->getPayment();
+ };
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::PAYMENT_PROCESSING, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $cntAfter = $order->getStatusHistoryCollection()->count();
+ $this->assertTrue($cntBefore < $cntAfter);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackPaymentRefused()
+ {
+ // mail sending is triggered but getEmailSent takes effect
+ $this->mockEmailHelper($this->once());
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock(
+ 'ops/directlink',
+ array('isValidOpsRequest', 'closePaymentTransaction')
+ );
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation(
+ 'status',
+ Netresearch_OPS_Model_Status::PAYMENT_REFUSED
+ );
+ return $order->getPayment();
+ };
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::PAYMENT_REFUSED, 'PAYID' => '4711');
+
+ $directlinkHelperMock->processFeedback($order, $params);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackRefundWaiting()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $paymentMock = $this->getModelMock('core/resource_transaction', array('save'));
+ $this->replaceByMock('model', 'core/resource_transaction', $paymentMock);
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+
+ $creditMemo = $this->getModelMock('sales/order_creditmemo', array('_beforeSave'));
+ $order->getPayment()->setCreatedCreditMemo($creditMemo);
+ /** @var Netresearch_OPS_Helper_Directlink $directlinkHelperMock */
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $cntBefore = $order->getStatusHistoryCollection()->count();
+
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation(
+ 'status',
+ Netresearch_OPS_Model_Status::REFUND_PENDING
+ );
+ return $order->getPayment();
+ };
+
+ $refundHelper = $this->getHelperMock('ops/order_refund', array('createRefund'));
+ $refundHelper->expects($this->any())
+ ->method('createRefund')
+ ->will($this->returnCallback($closure));
+ $this->replaceByMock('helper', 'ops/order_refund', $refundHelper);
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::REFUND_PENDING, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $cntAfter = $order->getStatusHistoryCollection()->count();
+ $this->assertTrue($cntBefore < $cntAfter);
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackRefundRefused()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $transMock = $this->getModelMock('core/resource_transaction', array('save'));
+ $this->replaceByMock('model', 'core/resource_transaction', $transMock);
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock(
+ 'ops/directlink',
+ array('isValidOpsRequest', 'closePaymentTransaction')
+ );
+ $creditMemo = $this->getModelMock('sales/order_creditmemo', array('_beforeSave'));
+ $order->getPayment()->setCreatedCreditMemo($creditMemo);
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation(
+ 'status',
+ Netresearch_OPS_Model_Status::REFUND_PENDING
+ );
+ return $order->getPayment();
+ };
+
+ $refundHelper = $this->getHelperMock('ops/order_refund', array('createRefund'));
+ $refundHelper->expects($this->any())
+ ->method('createRefund')
+ ->will($this->returnCallback($closure));
+ $this->replaceByMock('helper', 'ops/order_refund', $refundHelper);
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::REFUND_REFUSED, 'PAYID' => '4711');
+
+ $directlinkHelperMock->processFeedback($order, $params);
+
+ $this->assertEquals(Netresearch_OPS_Model_Status::REFUND_REFUSED, $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackVoidSuccess()
+ {
+ $this->mockEmailHelper($this->never());
+ $this->mockOrderConfig();
+
+ $transMock = $this->getModelMock('core/resource_transaction', array('save'));
+ $this->replaceByMock('model', 'core/resource_transaction', $transMock);
+
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation('status', 6);
+ return $order->getPayment();
+ };
+
+ $voidHelper = $this->getHelperMock('ops/order_void', array('acceptVoid'));
+ $voidHelper->expects($this->any())
+ ->method('acceptVoid')
+ ->will($this->returnCallback($closure));
+ $this->replaceByMock('helper', 'ops/order_void', $voidHelper);
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $this->assertEquals($params['STATUS'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackVoidWaiting()
+ {
+ $this->mockEmailHelper($this->never());
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ /** @var Netresearch_OPS_Helper_Directlink $directlinkHelperMock */
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::DELETION_WAITING, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $this->assertNotEmpty($order->getPayment()->getMessage());
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackVoidRefused()
+ {
+ $this->mockEmailHelper($this->never());
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock(
+ 'ops/directlink',
+ array('isValidOpsRequest')
+ );
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation(
+ 'status',
+ Netresearch_OPS_Model_Status::DELETION_REFUSED
+ );
+ return $order->getPayment();
+ };
+
+ $refundHelper = $this->getHelperMock('ops/order_void', array('acceptVoid'));
+ $refundHelper->expects($this->any())
+ ->method('acceptVoid')
+ ->will($this->returnCallback($closure));
+ $this->replaceByMock('helper', 'ops/order_void', $refundHelper);
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::DELETION_REFUSED, 'PAYID' => '4711');
+
+
+ $directlinkHelperMock->processFeedback($order, $params);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackAuthorizeChanged()
+ {
+ // mail sending is triggered but getEmailSent takes effect
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $cntBefore = $order->getStatusHistoryCollection()->count();
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::AUTHORIZED, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $cntAfter = $order->getStatusHistoryCollection()->count();
+ $this->assertTrue($cntBefore < $cntAfter);
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testProcessFeedbackAuthorizeKwixoAccepted()
+ {
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(27);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $cntBefore = $order->getStatusHistoryCollection()->count();
+
+
+ $closure = function ($order, $params = array()) {
+ $order->getPayment()->setAdditionalInformation(
+ 'status', Netresearch_OPS_Model_Status::AUTHORIZED
+ );
+ return $order->getPayment();
+ };
+
+ $paymentHelper = $this->getHelperMock('ops/payment', array('acceptOrder'));
+ $paymentHelper->expects($this->any())
+ ->method('acceptOrder')
+ ->will($this->returnCallback($closure));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelper);
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::AUTHORIZED, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+ $this->assertEquals($params['STATUS'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Can not handle status 4711.
+ */
+ public function testProcessFeedbackUnknownStatus()
+ {
+ $this->mockEmailHelper($this->never());
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+
+ $params = array('STATUS' => 4711, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Ingenico ePayments status 0, the action failed.
+ */
+ public function testProcessFeedbackInvalidStatus()
+ {
+ $helperMock = $this->getHelperMock('ops', array('isAdminSession', 'sendTransactionalEmail'));
+ $helperMock->expects($this->once())
+ ->method('isAdminSession')
+ ->will($this->returnValue(false));
+ $helperMock->expects($this->never())
+ ->method('sendTransactionalEmail');
+ $this->replaceByMock('helper', 'ops', $helperMock);
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->getPayment()->setAdditionalInformation('status', 500);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::INVALID_INCOMPLETE, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Ingenico ePayments status 0, the action failed.
+ */
+ public function testProcessFeedbackInvalidStatusAsAdmin()
+ {
+ $helperMock = $this->getHelperMock('ops', array('isAdminSession', 'sendTransactionalEmail'));
+ $helperMock->expects($this->once())
+ ->method('isAdminSession')
+ ->will($this->returnValue(true));
+ $helperMock->expects($this->never())
+ ->method('sendTransactionalEmail');
+ $this->replaceByMock('helper', 'ops', $helperMock);
+
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->getPayment()->setAdditionalInformation('status', 500);
+ $directlinkHelperMock = $this->getHelperMock('ops/directlink', array('isValidOpsRequest'));
+ $directlinkHelperMock->expects($this->any())
+ ->method('isValidOpsRequest')
+ ->will($this->returnValue(true));
+
+ $params = array('STATUS' => Netresearch_OPS_Model_Status::INVALID_INCOMPLETE, 'PAYID' => '4711');
+ $directlinkHelperMock->processFeedback($order, $params);
+
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/DirectLinkTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/DirectLinkTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/KwixoTest.php b/app/code/community/Netresearch/OPS/Test/Helper/KwixoTest.php
new file mode 100644
index 0000000..346b750
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/KwixoTest.php
@@ -0,0 +1,132 @@
+helperMustThrowException(array());
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsInvalidId()
+ {
+ $this->helperMustThrowException(array('od' => 1));
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsEmptyId()
+ {
+ $this->helperMustThrowException(array('id' => ''));
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsNonNumericId()
+ {
+ $this->helperMustThrowException(array('id' => 'abc'));
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsNegativeId()
+ {
+ $this->helperMustThrowException(array('id' => -1));
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsNoKwixoCategory(
+ )
+ {
+ $this->helperMustThrowException(array('id' => 1));
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsInvalidKwixoCategory(
+ )
+ {
+ $this->helperMustThrowException(
+ array('id' => 1, 'kwixoCategory_id' => 666)
+ );
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsNoCategory()
+ {
+ $this->helperMustThrowException(
+ array('id' => 1, 'kwixoCategory_id' => 1)
+ );
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsNonNumericCategory(
+ )
+ {
+ $this->helperMustThrowException(
+ array('id' => 1, 'kwixoCategory_id' => 1, 'category_id' => 'abc')
+ );
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsNegativeCategory(
+ )
+ {
+ $this->helperMustThrowException(
+ array('id' => 1, 'kwixoCategory_id' => 1, 'category_id' => -1)
+ );
+ }
+
+ public function testValidateKwixoconfigurationMappingContainsNegativeCategory2(
+ )
+ {
+ $helper = Mage::helper('ops/kwixo');
+ $helper->validateKwixoconfigurationMapping(
+ array('id' => 1, 'kwixoCategory_id' => 1, 'category_id' => 1)
+ );
+ }
+
+
+ protected function helperMustThrowException($invalidData)
+ {
+ $helper = Mage::helper('ops/kwixo');
+ $this->setExpectedException('Mage_Core_Exception');
+ $helper->validateKwixoconfigurationMapping($invalidData);
+ }
+
+ /**
+ * @loadFixture category_mapping
+ */
+ public function testSaveKwixoConfigurationMapping()
+ {
+ $helperMock = $this->getHelperMock(
+ 'ops/kwixo', array('validateKwixoconfigurationMapping')
+ );
+ $helperMock->saveKwixoconfigurationMapping(
+ array('id' => 1, 'category_id' => 666, 'kwixoCategory_id' => 777)
+ );
+ $model = Mage::getModel('ops/kwixo_category_mapping')->load(1);
+ $this->assertEquals(666, $model->getCategoryId());
+ $this->assertEquals(777, $model->getKwixoCategoryId());
+ }
+
+ /**
+ * @loadFixture category_mapping
+ */
+ public function testSaveKwixoConfigurationMappingForSubCategories()
+ {
+ $helperMock = $this->getHelperMock(
+ 'ops/kwixo', array('validateKwixoconfigurationMapping')
+ );
+
+ $categoryMock = $this->getModelMock('catalog/category', array('load', 'getAllChildren'));
+ $categoryMock->expects($this->any())
+ ->method('getAllChildren')
+ ->will($this->returnValue(array(11)));
+ $categoryMock->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($categoryMock));
+ $this->replaceByMock('model', 'catalog/category', $categoryMock);
+
+ $helperMock->saveKwixoconfigurationMapping(
+ array('id' => 1, 'category_id' => 666,
+ 'kwixoCategory_id' => 777, 'applysubcat' => true)
+ );
+
+ $model = Mage::getModel('ops/kwixo_category_mapping')->load(1);
+ $this->assertEquals(666, $model->getCategoryId());
+ $this->assertEquals(777, $model->getKwixoCategoryId());
+ $model = Mage::getModel('ops/kwixo_category_mapping')->load(2);
+ $this->assertEquals(777, $model->getKwixoCategoryId());
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/KwixoTest/fixtures/category_mapping.yaml b/app/code/community/Netresearch/OPS/Test/Helper/KwixoTest/fixtures/category_mapping.yaml
new file mode 100644
index 0000000..e18a796
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/KwixoTest/fixtures/category_mapping.yaml
@@ -0,0 +1,11 @@
+tables:
+ ops/kwixo_category_mapping:
+ - id: 1
+ kwixo_category_id: 10
+ category_id: 10
+ - id: 2
+ kwixo_category_id: 1
+ category_id: 11
+ - id: 3
+ kwixo_category_id: 2
+ category_id: 11
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/MobileDetectTest.php b/app/code/community/Netresearch/OPS/Test/Helper/MobileDetectTest.php
new file mode 100644
index 0000000..402d98f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/MobileDetectTest.php
@@ -0,0 +1,77 @@
+detectorMock = $this->getMockBuilder('Mobile_Detect')
+ ->setMethods(array('isMobile', 'isTablet'))
+ ->getMock();
+ $this->helper = Mage::helper('ops/mobileDetect');
+ $this->helper->setDetector($this->detectorMock);
+ }
+
+ /**
+ * @test
+ */
+ public function testGetDeviceTypeMobile()
+ {
+ $this->detectorMock
+ ->expects($this->once())
+ ->method('isMobile')
+ ->willReturn(true);
+
+ $this->detectorMock
+ ->expects($this->once())
+ ->method('isTablet')
+ ->willReturn(false);
+
+ $this->assertEquals(Netresearch_OPS_Helper_MobileDetect::DEVICE_TYPE_MOBILE, $this->helper->getDeviceType());
+ }
+
+ /**
+ * @test
+ */
+ public function testGetDeviceTypeTablet()
+ {
+ $this->detectorMock
+ ->expects($this->once())
+ ->method('isMobile')
+ ->willReturn(false);
+
+ $this->detectorMock
+ ->expects($this->once())
+ ->method('isTablet')
+ ->willReturn(true);
+
+ $this->assertEquals(Netresearch_OPS_Helper_MobileDetect::DEVICE_TYPE_TABLET, $this->helper->getDeviceType());
+ }
+
+ /**
+ * @test
+ */
+ public function testGetDeviceTypeComputer()
+ {
+ $this->detectorMock
+ ->expects($this->once())
+ ->method('isMobile')
+ ->willReturn(false);
+
+ $this->detectorMock
+ ->expects($this->once())
+ ->method('isTablet')
+ ->willReturn(false);
+
+ $this->assertEquals(Netresearch_OPS_Helper_MobileDetect::DEVICE_TYPE_COMPUTER, $this->helper->getDeviceType());
+ }
+}
+
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Order/CaptureTest.php b/app/code/community/Netresearch/OPS/Test/Helper/Order/CaptureTest.php
new file mode 100644
index 0000000..e8fe078
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/Order/CaptureTest.php
@@ -0,0 +1,82 @@
+ "foo");
+ Mage::app()->getRequest()->setParam('invoice', $invoice);
+ $payment = new Varien_Object();
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ // order base_grand_total == grand_total == 119.00
+
+ $expected = array(
+ "items" => $invoice["items"],
+ "operation" => Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_PARTIAL,
+ "type" => "partial",
+ "amount" => 100.00
+ );
+
+ $payment->setBaseAmountPaidOnline(0.00);
+ $amount = 100.00;
+ $this->assertEquals($expected, $helper->prepareOperation($payment, $amount));
+
+ }
+
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testOperationFullAndTypePartial()
+ {
+ $helper = Mage::helper('ops/order_capture');
+ $invoice = array("items" => "foo");
+ Mage::app()->getRequest()->setParam('invoice', $invoice);
+ $payment = new Varien_Object();
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ // order base_grand_total == grand_total == 119.00
+
+ $expected = array(
+ "items" => $invoice["items"],
+ "operation" => Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_FULL,
+ "type" => "partial",
+ "amount" => 100.00
+ );
+
+ $payment->setBaseAmountPaidOnline(19.00);
+ $amount = 100.00;
+ $this->assertEquals($expected, $helper->prepareOperation($payment, $amount));
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testOperationFullAndTypeFull()
+ {
+ $helper = Mage::helper('ops/order_capture');
+ $invoice = array("items" => "foo");
+ Mage::app()->getRequest()->setParam('invoice', $invoice);
+ $payment = new Varien_Object();
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ // order base_grand_total == grand_total == 119.00
+
+ $expected = array(
+ "items" => $invoice["items"],
+ "operation" => Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_FULL,
+ "type" => "full",
+ "amount" => 119.00
+ );
+
+ $payment->setBaseAmountPaidOnline(0.00);
+ $amount = 119.00;
+ $this->assertEquals($expected, $helper->prepareOperation($payment, $amount));
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Order/CaptureTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/Order/CaptureTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Order/RefundTest.php b/app/code/community/Netresearch/OPS/Test/Helper/Order/RefundTest.php
new file mode 100644
index 0000000..c81835b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/Order/RefundTest.php
@@ -0,0 +1,141 @@
+load(11);
+ $payment->setOrder($order);
+ $payment->setBaseAmountRefundedOnline(0.00);
+ $amount = 119.00;
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL, $helper->determineOperationCode($payment, $amount));
+
+ // complete refund should lead to RFS
+ $order = Mage::getModel('sales/order')->load(16);
+ $payment->setOrder($order);
+ $payment->setBaseAmountRefundedOnline(0.00);
+ $amount = 19.99;
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL, $helper->determineOperationCode($payment, $amount));
+
+ // partial refund should lead to RFD
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ $payment->setBaseAmountRefundedOnline(0.00);
+ $amount = 100.00;
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL, $helper->determineOperationCode($payment, $amount));
+
+ // partial refund + new amount to refund should lead to RFS
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ $payment->setBaseAmountRefundedOnline(19.00);
+ $amount = 100.00;
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL, $helper->determineOperationCode($payment, $amount));
+
+ // partial refund + new amount to refund should lead to RFS
+ $order = Mage::getModel('sales/order')->load(16);
+ $payment->setOrder($order);
+ $payment->setBaseAmountRefundedOnline(17.98);
+ $amount = 2.01;
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL, $helper->determineOperationCode($payment, $amount));
+
+ // partial refund + new amount to refund should lead to RFS
+ $order = Mage::getModel('sales/order')->load(16);
+ $payment->setOrder($order);
+ $payment->setBaseAmountRefundedOnline(17.98);
+ $amount = 2.00;
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL, $helper->determineOperationCode($payment, $amount));
+
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testOperationPartialAndTypePartial()
+ {
+ $helper = Mage::helper('ops/order_refund');
+ $creditmemo = array("creditmemo" => array("items" => "foo"));
+ $helper->setCreditMemoRequestParams($creditmemo);
+ $payment = new Varien_Object();
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ // order base_grand_total == grand_total == 119.00
+
+ $expected = array(
+ "items" => $creditmemo["creditmemo"]["items"],
+ "operation" => Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL,
+ "type" => "partial",
+ "amount" => 100.00
+ );
+
+ $payment->setBaseAmountRefundedOnline(0.00);
+ $amount = 100.00;
+ $this->assertEquals($expected, $helper->prepareOperation($payment, $amount));
+
+ }
+
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testOperationFullAndTypePartial()
+ {
+ $helper = Mage::helper('ops/order_refund');
+ $creditmemo = array("creditmemo" => array("items" => "foo"));
+ $helper->setCreditMemoRequestParams($creditmemo);
+ $payment = new Varien_Object();
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ // order base_grand_total == grand_total == 119.00
+
+ $expected = array(
+ "items" => $creditmemo["creditmemo"]["items"],
+ "operation" => Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL,
+ "type" => "partial",
+ "amount" => 100.00
+ );
+
+ $payment->setBaseAmountRefundedOnline(19.00);
+ $amount = 100.00;
+ $this->assertEquals($expected, $helper->prepareOperation($payment, $amount));
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testOperationFullAndTypeFull()
+ {
+ $helper = Mage::helper('ops/order_refund');
+ $creditmemo = array("creditmemo" => array("items" => "foo"));
+ $helper->setCreditMemoRequestParams($creditmemo);
+ $payment = new Varien_Object();
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment->setOrder($order);
+ // order base_grand_total == grand_total == 119.00
+
+ $expected = array(
+ "items" => $creditmemo["creditmemo"]["items"],
+ "operation" => Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL,
+ "type" => "full",
+ "amount" => 119.00
+ );
+
+ $payment->setBaseAmountRefundedOnline(0.00);
+ $amount = 119.00;
+ $this->assertEquals($expected, $helper->prepareOperation($payment, $amount));
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Order/RefundTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/Order/RefundTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/OrderTest.php b/app/code/community/Netresearch/OPS/Test/Helper/OrderTest.php
new file mode 100644
index 0000000..37dd1c5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/OrderTest.php
@@ -0,0 +1,137 @@
+devPrefix = Mage::getModel('ops/config')->getConfigData(
+ 'devprefix'
+ );
+ parent::setUp();
+ }
+
+
+ /**
+ * @loadFixture order.yaml
+ */
+ public function testGetOpsOrderId()
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $helper = Mage::helper('ops/order');
+
+ $store->setConfig(
+ 'payment_services/ops/redirectOrderReference',
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID
+ );
+
+ $order = Mage::getModel('sales/order')->load(1);
+ $delimiter = $helper::DELIMITER;
+ $this->assertEquals(
+ $this->devPrefix . $order->getQuoteId(),
+ $helper->getOpsOrderId($order)
+ );
+
+
+ $store->setConfig(
+ 'payment_services/ops/redirectOrderReference',
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID
+ );
+
+ $order = Mage::getModel('sales/order')->load(2);
+ $this->assertEquals(
+ $this->devPrefix . $delimiter . $order->getIncrementId(),
+ $helper->getOpsOrderId($order)
+ );
+
+ $store->setConfig(
+ 'payment_services/ops/redirectOrderReference',
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID
+ );
+ $order = Mage::getModel('sales/order')->load(3);
+ $this->assertEquals(
+ $this->devPrefix . $order->getQuoteId(),
+ $helper->getOpsOrderId($order)
+ );
+
+ $store->setConfig(
+ 'payment_services/ops/redirectOrderReference',
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID
+ );
+ $order = Mage::getModel('sales/order')->load(3);
+ $this->assertEquals(
+ $this->devPrefix . $order->getQuoteId(),
+ $helper->getOpsOrderId($order, false)
+ );
+ }
+
+
+ /**
+ * @loadFixture order.yaml
+ */
+ public function testGetOrder()
+ {
+ $helper = Mage::helper('ops/order');
+ // old behaviour: load order from quote
+ $opsOrderId = $this->devPrefix . '5';
+ $order = $helper->getOrder($opsOrderId);
+ $this->assertEquals(4, $order->getId());
+
+ // new behaviour
+ $delimiter = $helper::DELIMITER;
+ $opsOrderId = $this->devPrefix . $delimiter . 2000;
+ $order = $helper->getOrder($opsOrderId);
+ $this->assertEquals(2, $order->getId());
+
+
+ }
+
+
+ /**
+ * @loadFixture order.yaml
+ */
+ public function testGetQuote()
+ {
+ $order = Mage::getModel('sales/order')->load(1);
+ $quote = Mage::helper('ops/order')->getQuote($order->getQuoteId());
+ $this->assertTrue($quote instanceof Mage_Sales_Model_Quote);
+ $this->assertEquals(1, $quote->getId());
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testCheckIfAddressAreSameWithSameAddressData()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $this->assertTrue(
+ (bool)Mage::helper('ops/order')->checkIfAddressesAreSame($order)
+ );
+
+ $order = Mage::getModel('sales/order')->load(27);
+ $this->assertFalse(
+ (bool)Mage::helper('ops/order')->checkIfAddressesAreSame($order)
+ );
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testCheckIfAddressAreSameWithDifferentAddressData()
+ {
+ $order = Mage::getModel('sales/order')->load(12);
+ $this->assertFalse(
+ (bool)Mage::helper('ops/order')->checkIfAddressesAreSame($order)
+ );
+ }
+
+ public function testSetDataHelper()
+ {
+ $dataHelper = $this->getHelperMock('ops/data');
+ $helper = Mage::helper('ops/order');
+ $helper->setDataHelper($dataHelper);
+ $this->assertEquals($dataHelper, $helper->getDataHelper());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/OrderTest/fixtures/order.yaml b/app/code/community/Netresearch/OPS/Test/Helper/OrderTest/fixtures/order.yaml
new file mode 100644
index 0000000..68de179
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/OrderTest/fixtures/order.yaml
@@ -0,0 +1,42 @@
+tables:
+ sales/order:
+ - entity_id: 1
+ increment_id: 1000
+ quote_id: 1
+
+ - entity_id: 2
+ increment_id: 2000
+ quote_id: 2
+
+ - entity_id: 3
+ quote_id: 3
+
+ - id: 4
+ entity_id: 4
+ increment_id: 4000
+ quote_id: 5
+
+ - id: 5
+ entity_id: 5
+ increment_id: 1001
+ quote_id: 5
+
+
+ sales/quote:
+ - id: 1
+ entity_id: 1
+ parent_id: 1
+
+ - id: 5
+ entity_id: 5
+ parent_id: 1
+
+ sales/order_payment:
+ - parent_id: 4
+ method: 'ops_test'
+
+ - parent_id: 2
+ method: 'ops_test'
+
+ - parent_id: 5
+ method: 'ops_test'
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Payment/DirectLink/RequestTest.php b/app/code/community/Netresearch/OPS/Test/Helper/Payment/DirectLink/RequestTest.php
new file mode 100644
index 0000000..69e1af9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/Payment/DirectLink/RequestTest.php
@@ -0,0 +1,89 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Helper_Payment_DirectLink_RequestTest extends EcomDev_PHPUnit_Test_Case_Controller
+{
+
+ /**
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetBaseParams()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $quote = Mage::getModel('sales/quote')->load($order->getQuoteId());
+ $quote->getPayment()->setMethod('ops_cc');
+ $configMock = $this->getModelMock('ops/config', array('canSubmitExtraParameter'));
+ $configMock->expects($this->any())
+ ->method('canSubmitExtraParameter')
+ ->will($this->returnValue(false));
+ $paramHelper = Mage::helper('ops/creditcard');
+ $paramHelper->setConfig($configMock);
+ $paramHelper->getRequestHelper()->setConfig($configMock);
+ $params = $paramHelper->getDirectLinkRequestParams($quote, $order);
+ foreach ($this->getOwnerParams() as $ownerParam) {
+ $this->assertArrayNotHasKey($ownerParam, $params);
+ }
+ foreach ($this->getShippingParams() as $shippingParam) {
+ $this->assertArrayNotHasKey($shippingParam, $params);
+ }
+ $this->assertArrayHasKey('RTIMEOUT', $params);
+ }
+
+ /**
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetExtraParams()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $quote = Mage::getModel('sales/quote');
+ $quote->getPayment()->setMethod('ops_cc');
+ $configMock = $this->getModelMock('ops/config', array('canSubmitExtraParameter'));
+ $configMock->expects($this->any())
+ ->method('canSubmitExtraParameter')
+ ->will($this->returnValue(true));
+ $paramHelper = Mage::helper('ops/creditcard');
+ $paramHelper->setConfig($configMock);
+ $paramHelper->getRequestHelper()->setConfig($configMock);
+ $params = $paramHelper->getDirectLinkRequestParams($quote, $order);
+ foreach ($this->getOwnerParams() as $ownerParam) {
+ $this->assertArrayHasKey($ownerParam, $params);
+ }
+ foreach ($this->getShippingParams() as $shippingParam) {
+ $this->assertArrayHasKey($shippingParam, $params);
+ }
+ $this->assertArrayHasKey('RTIMEOUT', $params);
+
+ }
+
+ protected function getOwnerParams()
+ {
+ return $ownerParams = array(
+ 'OWNERADDRESS',
+ 'OWNERTOWN',
+ 'OWNERZIP',
+ 'OWNERTELNO',
+ 'OWNERCTY',
+ 'ECOM_BILLTO_POSTAL_POSTALCODE',
+ );
+ }
+
+ protected function getShippingParams()
+ {
+ $paramValues = array(
+ 'ECOM_SHIPTO_POSTAL_NAME_FIRST',
+ 'ECOM_SHIPTO_POSTAL_NAME_LAST',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE2',
+ 'ECOM_SHIPTO_POSTAL_COUNTRYCODE',
+ 'ECOM_SHIPTO_POSTAL_CITY',
+ 'ECOM_SHIPTO_POSTAL_POSTALCODE'
+ );
+
+ return $paramValues;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Payment/DirectLink/RequestTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/Payment/DirectLink/RequestTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Payment/RequestTest.php b/app/code/community/Netresearch/OPS/Test/Helper/Payment/RequestTest.php
new file mode 100644
index 0000000..5eec80b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/Payment/RequestTest.php
@@ -0,0 +1,323 @@
+getRequestHelper();
+ $configMock = $this->getModelMock('ops/config', array('canSubmitExtraParameter'));
+ $configMock->expects($this->any())
+ ->method('canSubmitExtraParameter')
+ ->will($this->returnValue(true));
+ $helper->setConfig($configMock);
+ $params = $helper->extractShipToParameters($address, Mage::getModel('sales/quote'));
+ $this->assertTrue(is_array($params));
+ foreach ($this->getShipToArrayKeys() as $key) {
+ $this->assertArrayHasKey($key, $params);
+ }
+
+ $address->setFirstname('Hans');
+ $address->setLastname('Wurst');
+ $address->setStreet('Nonnenstrasse 11d');
+ $address->setCountry('DE');
+ $address->setCity('Leipzig');
+ $address->setPostcode('04229');
+ $params = $this->getRequestHelper()->extractShipToParameters($address, Mage::getModel('sales/quote'));
+ $this->assertEquals('Hans', $params['ECOM_SHIPTO_POSTAL_NAME_FIRST']);
+ $this->assertEquals('Wurst', $params['ECOM_SHIPTO_POSTAL_NAME_LAST']);
+ $this->assertEquals('Nonnenstrasse' , $params['ECOM_SHIPTO_POSTAL_STREET_LINE1']);
+ $this->assertEquals('Nonnenstrasse' , $params['ECOM_SHIPTO_POSTAL_STREET_LINE1']);
+ $this->assertEquals('', $params['ECOM_SHIPTO_POSTAL_STREET_LINE2']);
+ $this->assertEquals('DE', $params['ECOM_SHIPTO_POSTAL_COUNTRYCODE']);
+ $this->assertEquals('Leipzig', $params['ECOM_SHIPTO_POSTAL_CITY']);
+ $this->assertEquals('04229', $params['ECOM_SHIPTO_POSTAL_POSTALCODE']);
+ $this->assertEquals('11d', $params['ECOM_SHIPTO_POSTAL_STREET_NUMBER']);
+
+ }
+
+ public function testGetIsoRegionCodeWithIsoRegionCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('SN');
+ $address->setCountry('DE');
+ $this->assertEquals('SN', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+ public function testGetIsoRegionCodeWithIsoRegionCodeContainingTheCountryCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('ES-AB');
+ $address->setCountry('ES');
+ $this->assertEquals('AB', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+
+ public function testGetIsoRegionCodeWithGermanMageRegionCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('SAS');
+ $address->setCountry('DE');
+ $this->assertEquals('SN', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('NDS');
+ $this->assertEquals('NI', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('THE');
+ $this->assertEquals('TH', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+ public function testGetIsoRegionCodeWithAustrianMageRegionCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('WI');
+ $address->setCountry('AT');
+ $this->assertEquals('9', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('NO');
+ $this->assertEquals('3', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('VB');
+ $this->assertEquals('8', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+ public function testGetIsoRegionCodeWithSpanishMageRegionCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('A Coruсa');
+ $address->setCountry('ES');
+ $this->assertEquals('C', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('Barcelona');
+ $this->assertEquals('B', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('Madrid');
+ $this->assertEquals('M', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+ public function testGetIsoRegionCodeWithFinnishMageRegionCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('Lappi');
+ $address->setCountry('FI');
+ $this->assertEquals('10', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('Etelä-Savo');
+ $this->assertEquals('04', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('Itä-Uusimaa');
+ $this->assertEquals('19', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+ public function testGetIsoRegionCodeWithLatvianMageRegionCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('Ādažu novads');
+ $address->setCountry('LV');
+ $this->assertEquals('LV', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('Engures novads');
+ $this->assertEquals('029', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('Viļakas novads');
+ $this->assertEquals('108', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+ public function testGetIsoRegionCodeWithUnknownRegionCode()
+ {
+ $address = Mage::getModel('customer/address');
+ $address->setRegionCode('DEFG');
+ $address->setCountry('AB');
+ $this->assertEquals('AB', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('DEF');
+ $this->assertEquals('DEF', $this->getRequestHelper()->getIsoRegionCode($address));
+ $address->setRegionCode('DF');
+ $this->assertEquals('DF', $this->getRequestHelper()->getIsoRegionCode($address));
+ }
+
+ public function testGetTemplateParamsIframeMode()
+ {
+ $config = $this->getModelMock('ops/config', array('getConfigData'));
+ $config->expects($this->any())
+ ->method('getConfigData')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_IFRAME));
+ $helper = Mage::helper('ops/payment_request');
+ $helper->setConfig($config);
+
+ $params = $helper->getTemplateParams();
+
+ $this->assertArrayHasKey('PARAMPLUS', $params);
+ $this->assertEquals('IFRAME=1', $params['PARAMPLUS']);
+ $this->assertArrayHasKey('TITLE', $params);
+ $this->assertArrayNotHasKey('TP', $params);
+ }
+
+ public function testGetTemplateParamsNoMode()
+ {
+ $config = $this->getModelMock('ops/config', array('getConfigData'));
+ $config->expects($this->any())
+ ->method('getConfigData')
+ ->will($this->returnValue(null));
+ $helper = Mage::helper('ops/payment_request');
+ $helper->setConfig($config);
+
+ $params = $helper->getTemplateParams();
+
+ $this->assertArrayNotHasKey('PARAMPLUS', $params);
+ $this->assertArrayNotHasKey('TITLE', $params);
+ $this->assertArrayNotHasKey('TP', $params);
+
+ }
+
+ public function testGetTemplateParamsRedirectMode()
+ {
+ $config = $this->getModelMock('ops/config', array('getConfigData'));
+ $config->expects($this->any())
+ ->method('getConfigData')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_REDIRECT));
+ $helper = Mage::helper('ops/payment_request');
+ $helper->setConfig($config);
+
+ $params = $helper->getTemplateParams();
+ $this->assertArrayNotHasKey('PARAMPLUS', $params);
+ $this->assertArrayHasKey('TITLE', $params);
+ $this->assertArrayNotHasKey('TP', $params);
+ }
+
+ public function testExtractOrderItemParametersWithAllItems()
+ {
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ // setup one item
+ $item = Mage::getModel('sales/order_item');
+ $item->setId(1);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(10.00);
+ $item->setQtyOrdered(1);
+ $item->setTaxPercent(19.00);
+ $item->setProductType(Mage_Catalog_Model_Product_Type::TYPE_SIMPLE);
+
+ $order = $this->getModelMock('sales/order', array('getAllItems'));
+ $order->expects($this->once())
+ ->method('getAllItems')
+ ->will($this->returnValue(array($item)));
+
+ // prepare discount item
+ $order->setBaseDiscountAmount(1.00)
+ ->setCouponRuleName('DISCOUNT');
+
+ //prepare shipping Item
+ $order->setShippingDescription('SHIPPING')
+ ->setBaseShippingInclTax(5.00)
+ ->setIsVirtual(0);
+
+ $helper = Mage::helper('ops/payment_request');
+
+ $formFields = $helper->extractOrderItemParameters($order);
+
+ $this->assertArrayHasKey('ITEMID1', $formFields);
+ $this->assertArrayHasKey('ITEMID2', $formFields);
+ $this->assertArrayHasKey('ITEMID3', $formFields);
+ }
+
+ public function testExtractOrderItemParametersWithNoItems()
+ {
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ // setup one item
+ $item = Mage::getModel('sales/order_item');
+ $item->setProductType(Mage_Catalog_Model_Product_Type::TYPE_BUNDLE);
+
+ $order = $this->getModelMock('sales/order', array('getAllItems'));
+ $order->expects($this->once())
+ ->method('getAllItems')
+ ->will($this->returnValue(array($item)));
+
+ // prepare discount item
+ $order->setBaseDiscountAmount(0.00);
+
+ //prepare shipping Item
+ $order->setIsVirtual(true);
+
+ $helper = Mage::helper('ops/payment_request');
+
+ $formFields = $helper->extractOrderItemParameters($order);
+
+ $this->assertArrayNotHasKey('ITEMID1', $formFields);
+ $this->assertArrayNotHasKey('ITEMID2', $formFields);
+ $this->assertArrayNotHasKey('ITEMID3', $formFields);
+ }
+
+ public function testGetTemplateParamsTemplateMode()
+ {
+ $config = $this->getModelMock('ops/config', array('getConfigData'));
+ $config->expects($this->any())
+ ->method('getConfigData')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_TEMPLATE));
+ $helper = Mage::helper('ops/payment_request');
+ $helper->setConfig($config);
+
+ $params = $helper->getTemplateParams();
+ $this->assertArrayNotHasKey('PARAMPLUS', $params);
+ $this->assertArrayNotHasKey('TITLE', $params);
+ $this->assertArrayHasKey('TP', $params);
+
+ }
+
+ public function testGetTemplateParamsInternalTemplateMode()
+ {
+ $config = $this->getModelMock('ops/config', array('getConfigData'));
+ $config->expects($this->any())
+ ->method('getConfigData')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_MAGENTO_INTERNAL));
+ $helper = Mage::helper('ops/payment_request');
+ $helper->setConfig($config);
+
+ $params = $helper->getTemplateParams();
+ $this->assertArrayNotHasKey('PARAMPLUS', $params);
+ $this->assertArrayNotHasKey('TITLE', $params);
+ $this->assertArrayHasKey('TP', $params);
+ $this->assertEquals($config->getPayPageTemplate(), $params['TP']);
+ }
+
+ public function testGetMandatoryRequestFieldsWithFPActiveOff()
+ {
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_cc');
+ $order = Mage::getModel('sales/order');
+ $order->setStoreId(0)->setPayment($payment);
+ $subject = Mage::helper('ops/payment_request');
+ $sessionMock = $this->mockSession('customer/session', array('getData'));
+ $sessionMock->expects($this->any())
+ ->method('getData')
+ ->with(Netresearch_OPS_Model_Payment_Abstract::FINGERPRINT_CONSENT_SESSION_KEY)
+ ->will($this->returnValue(true));
+
+ $params = $subject->getMandatoryRequestFields($order);
+
+ $this->assertEquals(0, $params['FP_ACTIV']);
+
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/PaymentTest.php b/app/code/community/Netresearch/OPS/Test/Helper/PaymentTest.php
new file mode 100644
index 0000000..bb6711b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/PaymentTest.php
@@ -0,0 +1,708 @@
+_helper = Mage::helper('ops/payment');
+ $this->store = Mage::app()->getStore(0)->load(0);
+ $this->store->resetConfig();
+ }
+
+ public function testIsPaymentAuthorizeType()
+ {
+ $this->assertTrue(
+ $this->_helper->isPaymentAuthorizeType(
+ Netresearch_OPS_Model_Status::AUTHORIZED
+ )
+ );
+ $this->assertTrue(
+ $this->_helper->isPaymentAuthorizeType(
+ Netresearch_OPS_Model_Status::AUTHORIZATION_WAITING
+ )
+ );
+ $this->assertTrue(
+ $this->_helper->isPaymentAuthorizeType(
+ Netresearch_OPS_Model_Status::AUTHORIZED_UNKNOWN
+ )
+ );
+ $this->assertTrue(
+ $this->_helper->isPaymentAuthorizeType(
+ Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT
+ )
+ );
+ $this->assertFalse($this->_helper->isPaymentAuthorizeType(0));
+ }
+
+ public function testIsPaymentCaptureType()
+ {
+ $this->assertTrue(
+ $this->_helper->isPaymentCaptureType(
+ Netresearch_OPS_Model_Status::PAYMENT_REQUESTED
+ )
+ );
+ $this->assertTrue(
+ $this->_helper->isPaymentCaptureType(
+ Netresearch_OPS_Model_Status::PAYMENT_PROCESSING
+ )
+ );
+ $this->assertTrue(
+ $this->_helper->isPaymentCaptureType(
+ Netresearch_OPS_Model_Status::PAYMENT_UNCERTAIN
+ )
+ );
+ $this->assertFalse($this->_helper->isPaymentCaptureType(0));
+ }
+
+ /**
+ * send no invoice mail if it is denied by configuration
+ */
+ public function testSendNoInvoiceToCustomerIfDenied()
+ {
+ $this->store->setConfig('payment_services/ops/send_invoice', 0);
+ $this->assertFalse(Mage::getModel('ops/config')->getSendInvoice());
+ $sentInvoice = $this->getModelMock(
+ 'sales/order_invoice', array('getEmailSent', 'sendEmail')
+ );
+ $sentInvoice->expects($this->any())
+ ->method('getEmailSent')
+ ->will($this->returnValue(false));
+ $sentInvoice->expects($this->never())
+ ->method('sendEmail');
+ $this->_helper->sendInvoiceToCustomer($sentInvoice);
+ }
+
+ /**
+ * send no invoice mail if it was already sent
+ */
+ public function testSendNoInvoiceToCustomerIfAlreadySent()
+ {
+ $this->store->setConfig('payment_services/ops/send_invoice', 1);
+ $this->assertTrue(Mage::getModel('ops/config')->getSendInvoice());
+ $someInvoice = $this->getModelMock(
+ 'sales/order_invoice', array('getEmailSent', 'sendEmail')
+ );
+ $someInvoice->expects($this->any())
+ ->method('getEmailSent')
+ ->will($this->returnValue(true));
+ $someInvoice->expects($this->never())
+ ->method('sendEmail');
+ $this->_helper->sendInvoiceToCustomer($someInvoice);
+ }
+
+ /**
+ * send invoice mail
+ */
+ public function testSendInvoiceToCustomerIfEnabled()
+ {
+ $this->store->setConfig('payment_services/ops/send_invoice', 1);
+ $this->assertTrue(Mage::getModel('ops/config')->getSendInvoice());
+ $anotherInvoice = $this->getModelMock(
+ 'sales/order_invoice', array('getEmailSent', 'sendEmail')
+ );
+ $anotherInvoice->expects($this->any())
+ ->method('getEmailSent')
+ ->will($this->returnValue(false));
+ $anotherInvoice->expects($this->once())
+ ->method('sendEmail')
+ ->with($this->equalTo(true));
+ $this->_helper->sendInvoiceToCustomer($anotherInvoice);
+ }
+
+ public function testPrepareParamsAndSort()
+ {
+ $params = array(
+ 'CVC' => '123',
+ 'CARDNO' => '4111111111111111',
+ 'CN' => 'JohnSmith',
+ 'PSPID' => 'test1',
+ 'ED' => '1212',
+ 'ACCEPTURL' => 'https=//www.myshop.com/ok.html',
+ 'EXCEPTIONURL' => 'https=//www.myshop.com/nok.html',
+ 'BRAND' => 'VISA',
+ );
+ $sortedParams = array(
+ 'ACCEPTURL' => array('key' => 'ACCEPTURL',
+ 'value' => 'https=//www.myshop.com/ok.html'),
+ 'BRAND' => array('key' => 'BRAND', 'value' => 'VISA'),
+ 'CARDNO' => array('key' => 'CARDNO',
+ 'value' => '4111111111111111'),
+ 'CN' => array('key' => 'CN', 'value' => 'JohnSmith'),
+ 'CVC' => array('key' => 'CVC', 'value' => '123'),
+ 'ED' => array('key' => 'ED', 'value' => '1212'),
+ 'EXCEPTIONURL' => array('key' => 'EXCEPTIONURL',
+ 'value' => 'https=//www.myshop.com/nok.html'),
+ 'PSPID' => array('key' => 'PSPID', 'value' => 'test1'),
+ );
+ $secret = 'Mysecretsig1875!?';
+ $shaInSet
+ = 'ACCEPTURL=https=//www.myshop.com/ok.htmlMysecretsig1875!?BRAND=VISAMysecretsig1875!?'
+ . 'CARDNO=4111111111111111Mysecretsig1875!?CN=JohnSmithMysecretsig1875!?CVC=123Mysecretsig1875!?'
+ . 'ED=1212Mysecretsig1875!?EXCEPTIONURL=https=//www.myshop.com/nok.htmlMysecretsig1875!?'
+ . 'PSPID=test1Mysecretsig1875!?';
+ $key = 'a28dc9fe69b63fe81da92471fefa80aca3f4851a';
+ $this->assertEquals(
+ $sortedParams, $this->_helper->prepareParamsAndSort($params)
+ );
+ $this->assertEquals(
+ $shaInSet, $this->_helper->getSHAInSet($params, $secret)
+ );
+ $this->assertEquals($key, $this->_helper->shaCrypt($shaInSet, $secret));
+ }
+
+ public function testHandleUnknownStatus()
+ {
+ $order = $this->getModelMock('sales/order', array('save'));
+ $order->expects($this->any())
+ ->method('save')
+ ->will($this->returnValue(true));
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_NEW,
+ Mage_Sales_Model_Order::STATE_NEW
+ );
+ $statusHistoryCount = $order->getStatusHistoryCollection()->count();
+ Mage::helper('ops/payment')->handleUnknownStatus($order);
+ $this->assertEquals(
+ Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, $order->getState()
+ );
+ $this->assertTrue(
+ $statusHistoryCount < $order->getStatusHistoryCollection()->count()
+ );
+ $statusHistoryCount = $order->getStatusHistoryCollection()->count();
+ $order->setState(
+ Mage_Sales_Model_Order::STATE_PROCESSING,
+ Mage_Sales_Model_Order::STATE_PROCESSING
+ );
+
+ Mage::helper('ops/payment')->handleUnknownStatus($order);
+ $this->assertEquals(
+ Mage_Sales_Model_Order::STATE_PROCESSING, $order->getState()
+ );
+ $this->assertTrue(
+ $statusHistoryCount < $order->getStatusHistoryCollection()->count()
+ );
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testGetBaseGrandTotalFromSalesObject()
+ {
+ $helper = Mage::helper('ops/payment');
+ $order = Mage::getModel('sales/order')->load(14);
+ $amount = $helper->getBaseGrandTotalFromSalesObject($order);
+ $this->assertEquals($order->getBaseGrandTotal(), $amount);
+ $order = Mage::getModel('sales/order')->load(15);
+ $amount = $helper->getBaseGrandTotalFromSalesObject($order);
+ $this->assertEquals($order->getBaseGrandTotal(), $amount);
+ $quote = Mage::getModel('sales/quote')->load(1);
+ $amount = $helper->getBaseGrandTotalFromSalesObject($quote);
+ $this->assertEquals($quote->getBaseGrandTotal(), $amount);
+ $quote = Mage::getModel('sales/quote')->load(2);
+ $amount = $helper->getBaseGrandTotalFromSalesObject($quote);
+ $this->assertEquals($quote->getBaseGrandTotal(), $amount);
+ $someOtherObject = new Varien_Object();
+ $this->setExpectedException('Mage_Core_Exception');
+ $helper->getBaseGrandTotalFromSalesObject($someOtherObject);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSaveOpsRefundOperationCodeToPayment()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment = $order->getPayment();
+ $helper = Mage::helper('ops/payment');
+
+ // no last refund operation code is set if an empty string is passed
+ $helper->saveOpsRefundOperationCodeToPayment($payment, '');
+ $this->assertFalse(
+ array_key_exists(
+ 'lastRefundOperationCode', $payment->getAdditionalInformation()
+ )
+ );
+
+ // no last refund operation code is set if it's no refund operation code
+ $helper->saveOpsRefundOperationCodeToPayment(
+ $payment, Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_FULL
+ );
+ $this->assertFalse(
+ array_key_exists(
+ 'lastRefundOperationCode', $payment->getAdditionalInformation()
+ )
+ );
+
+ // last ops refund code is present if a valid refund code is passed
+ $helper->saveOpsRefundOperationCodeToPayment(
+ $payment, Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL
+ );
+ $this->assertTrue(
+ array_key_exists(
+ 'lastRefundOperationCode', $payment->getAdditionalInformation()
+ )
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL,
+ $payment->getAdditionalInformation('lastRefundOperationCode')
+ );
+
+ // last ops refund code is present if a valid refund code is passed and will override a previous one
+ $helper->saveOpsRefundOperationCodeToPayment(
+ $payment, Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL
+ );
+ $this->assertTrue(
+ array_key_exists(
+ 'lastRefundOperationCode', $payment->getAdditionalInformation()
+ )
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_FULL,
+ $payment->getAdditionalInformation('lastRefundOperationCode')
+ );
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testSetCanRefundToPayment()
+ {
+
+ $helper = Mage::helper('ops/payment');
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment = $order->getPayment();
+ $helper->setCanRefundToPayment($payment);
+ $this->assertFalse(
+ array_key_exists('canRefund', $payment->getAdditionalInformation())
+ );
+
+ $order = Mage::getModel('sales/order')->load(15);
+ $payment = $order->getPayment();
+ $helper->setCanRefundToPayment($payment);
+ $this->assertTrue($payment->getAdditionalInformation('canRefund'));
+
+ $order = Mage::getModel('sales/order')->load(16);
+ $payment = $order->getPayment();
+ $helper->setCanRefundToPayment($payment);
+ $this->assertFalse($payment->getAdditionalInformation('canRefund'));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ *
+ */
+ public function testSetPaymentTransactionInformation()
+ {
+ $dataMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $dataMock->expects($this->any())
+ ->method('isAdminSession')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/data', $dataMock);
+
+ $order = Mage::getModel('sales/order')->load(15);
+ $reflectionClass = new ReflectionClass(
+ get_class(
+ Mage::helper('ops/payment')
+ )
+ );
+ $method = $reflectionClass->getMethod(
+ 'setPaymentTransactionInformation'
+ );
+ $method->setAccessible(true);
+ $paymentHelper = Mage::helper('ops/payment');
+ $params = array(
+ 'PAYID' => '0815',
+ 'STATUS' => 9
+ );
+ $method->invoke(
+ $paymentHelper, $order->getPayment(), $params, 'accept'
+ );
+ $this->assertEquals(
+ '0815', $order->getPayment()->getAdditionalInformation('paymentId')
+ );
+ $this->assertEquals(
+ 9, $order->getPayment()->getAdditionalInformation('status')
+ );
+
+ $params = array(
+ 'PAYID' => '0815',
+ 'STATUS' => 9,
+ 'ACCEPTANCE' => ''
+ );
+ $method->invoke(
+ $paymentHelper, $order->getPayment(), $params, 'accept'
+ );
+ $this->assertEquals(
+ '0815', $order->getPayment()->getAdditionalInformation('paymentId')
+ );
+ $this->assertEquals(
+ '', $order->getPayment()->getAdditionalInformation('acceptance')
+ );
+
+ $params = array(
+ 'PAYID' => '0815',
+ 'STATUS' => 9,
+ 'ACCEPTANCE' => 'Akzeptanz'
+ );
+ $method->invoke(
+ $paymentHelper, $order->getPayment(), $params, 'accept'
+ );
+ $this->assertEquals(
+ '0815', $order->getPayment()->getAdditionalInformation('paymentId')
+ );
+ $this->assertEquals(
+ 'Akzeptanz',
+ $order->getPayment()->getAdditionalInformation('acceptance')
+ );
+
+ $params = array(
+ 'PAYID' => '0815',
+ 'STATUS' => 9,
+ 'ACCEPTANCE' => 'Akzeptanz',
+ 'HTML_ANSWER' => '3D Secure',
+ 'BRAND' => 'Brand'
+ );
+ $method->invoke(
+ $paymentHelper, $order->getPayment(), $params, 'accept'
+ );
+ $this->assertEquals(
+ '0815', $order->getPayment()->getAdditionalInformation('paymentId')
+ );
+ $this->assertEquals(
+ 'Akzeptanz',
+ $order->getPayment()->getAdditionalInformation('acceptance')
+ );
+ $this->assertEquals(
+ '3D Secure',
+ $order->getPayment()->getAdditionalInformation('HTML_ANSWER')
+ );
+ $this->assertEquals(
+ 'Brand',
+ $order->getPayment()->getAdditionalInformation('CC_BRAND')
+ );
+ }
+
+ /**
+ * @param int $opsStatus Incoming postBack status
+ * @param bool $sendMail Indicates whether opsStatus should trigger order confirmation mail
+ * @param string $feedbackStatus Indicates the route that the customer should get redirected to
+ *
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ * @dataProvider applyStateForOrderProvider
+ */
+ public function testApplyStateForOrder($opsStatus, $sendMail, $feedbackStatus)
+ {
+ $this->mockEmailHelper($this->exactly(intval($sendMail)));
+ $this->mockOrderConfig();
+
+ $helperMock = $this->getHelperMock('ops', array('isAdminSession', 'sendTransactionalEmail'));
+ $helperMock->expects($this->any())
+ ->method('isAdminSession')
+ ->will($this->returnValue(false));
+ $helperMock->expects($this->any())
+ ->method('sendTransactionalEmail')
+ ->will($this->returnArgument(0));
+ $this->replaceByMock('helper', 'ops', $helperMock);
+
+ /** @var Netresearch_OPS_Helper_Payment $paymenthelperMock */
+ $paymenthelperMock = $this->getHelperMock(
+ 'ops/payment', array(
+ 'acceptOrder', 'waitOrder', 'declineOrder', 'cancelOrder', 'handleException',
+ )
+ );
+
+ $order = Mage::getModel('sales/order')->load(19);
+ $this->assertEquals(
+ $feedbackStatus,
+ $paymenthelperMock->applyStateForOrder($order, array('STATUS' => $opsStatus))
+ );
+ }
+
+ public function applyStateForOrderProvider()
+ {
+ return array(
+ // assertion for WAITING_FOR_IDENTIFICATION = 46
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::WAITING_FOR_IDENTIFICATION,
+ $sendMail = false,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ ),
+ // assertion for AUTHORIZED = 5
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::AUTHORIZED,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ ),
+ // assertion for AUTHORIZED_WAITING_EXTERNAL_RESULT = 50
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ ),
+ // assertion for AUTHORIZATION_WAITING = 51
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::AUTHORIZATION_WAITING,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ ),
+ // assertion for AUTHORIZED_UNKNOWN = 52
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::AUTHORIZED_UNKNOWN,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_EXCEPTION,
+ ),
+ // assertion for WAITING_CLIENT_PAYMENT = 41
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ ),
+ // assertion for PAYMENT_REQUESTED = 9
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::PAYMENT_REQUESTED,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ ),
+ // assertion for PAYMENT_PROCESSING = 91
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::PAYMENT_PROCESSING,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_ACCEPT,
+ ),
+ // assertion for AUTHORISATION_DECLINED = 2
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_DECLINE,
+ ),
+ // assertion for PAYMENT_REFUSED = 93
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::PAYMENT_REFUSED,
+ $sendMail = true,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_DECLINE,
+ ),
+ // assertion for CANCELED_BY_CUSTOMER = 1
+ array(
+ $opsStatus = Netresearch_OPS_Model_Status::CANCELED_BY_CUSTOMER,
+ $sendMail = false,
+ $feedbackStatus = Netresearch_OPS_Model_Status_Feedback::OPS_ORDER_FEEDBACK_STATUS_CANCEL,
+ ),
+ );
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testForceAuthorize()
+ {
+ $helper = Mage::helper('ops/payment');
+ $reflectionClass = new ReflectionClass(get_class($helper));
+ $method = $reflectionClass->getMethod("forceAuthorize");
+ $method->setAccessible(true);
+
+ $order = Mage::getModel('sales/order')->load(11);
+ $this->assertFalse($method->invoke($helper, $order));
+
+ $order = Mage::getModel('sales/order')->load(27);
+ $this->assertTrue($method->invoke($helper, $order));
+
+ $order = Mage::getModel('sales/order')->load(28);
+ $this->assertTrue($method->invoke($helper, $order));
+
+ // $order = Mage::getModel('sales/order')->load(29);
+ // $this->assertTrue($method->invoke($helper, $order));
+ }
+
+ public function testCheckIfCCisInCheckoutMethodsFalse()
+ {
+ $testMethod = $this->getProtectedMethod($this->_helper, 'checkIfCCisInCheckoutMethods');
+ $paymentMethods = new Varien_Object();
+ $paymentMethods->setCode('ops_iDeal');
+ $this->assertFalse($testMethod->invoke($this->_helper, array($paymentMethods)));
+
+
+ }
+
+ public function testCheckIfCCisInCheckoutMethodsTrue()
+ {
+ $testMethod = $this->getProtectedMethod($this->_helper, 'checkIfCCisInCheckoutMethods');
+ $paymentMethods = new Varien_Object();
+ $paymentMethods->setCode('ops_cc');
+ $this->assertTrue($testMethod->invoke($this->_helper, array($paymentMethods)));
+
+
+ }
+
+ public function testAddCCForZeroAmountCheckout()
+ {
+ $block = new Mage_Payment_Block_Form_Container();
+ $method = new Varien_Object();
+ $method->setCode('ops_ideal');
+ $block->setData('methods', array($method));
+ $quote = Mage::getModel('sales/quote');
+ $block->setQuote($quote);
+
+ $featureModelMock = $this->getModelMock(
+ 'ops/payment_features_zeroAmountAuth', array('isCCAndZeroAmountAuthAllowed')
+ );
+ $featureModelMock->expects($this->any())
+ ->method('isCCAndZeroAmountAuthAllowed')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/payment_features_zeroAmountAuth', $featureModelMock);
+
+ $this->_helper->addCCForZeroAmountCheckout($block);
+
+ $methods = $block->getMethods();
+ $this->assertTrue($methods[1] instanceof Netresearch_OPS_Model_Payment_Cc);
+ $this->assertFalse($methods[0] instanceof Netresearch_OPS_Model_Payment_Cc);
+
+ }
+
+ protected function getProtectedMethod($class, $method)
+ {
+ $reflection_class = new ReflectionClass(get_class($class));
+ $method = $reflection_class->getMethod($method);
+ $method->setAccessible(true);
+
+ return $method;
+ }
+
+ public function testIsInlinePaymentWithOrderIdIsTrueForInlineCcWithOrderId()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference'));
+
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID));
+ $this->replaceByMock('singleton', 'ops/config', $configMock);
+
+ $ccMock = $this->getModelMock('ops/payment_cc', array('hasBrandAliasInterfaceSupport'));
+ $ccMock->expects($this->once())
+ ->method('hasBrandAliasInterfaceSupport')
+ ->will($this->returnValue(true));
+
+
+ $payment = $this->getModelMock('payment/info', array('getMethodInstance'));
+ $payment->expects($this->any())
+ ->method('getMethodInstance')
+ ->will($this->returnValue($ccMock));
+
+ $this->assertTrue(Mage::helper('ops/payment')->isInlinePaymentWithOrderId($payment));
+ }
+
+ public function testIsInlinePaymentWithOrderIdIsFalseForRedirectCcWithOrderId()
+ {
+ $ccMock = $this->getModelMock(
+ 'ops/payment_cc', array('getConfigPaymentAction', 'hasBrandAliasInterfaceSupport')
+ );
+ $ccMock->expects($this->any())
+ ->method('getConfigPaymentAction')
+ ->will($this->returnValue('authorize'));
+ $ccMock->expects($this->once())
+ ->method('hasBrandAliasInterfaceSupport')
+ ->will($this->returnValue(false));
+
+
+ $payment = $this->getModelMock('payment/info', array('getMethodInstance'));
+ $payment->expects($this->any())
+ ->method('getMethodInstance')
+ ->will($this->returnValue($ccMock));
+
+ $this->assertFalse(Mage::helper('ops/payment')->isInlinePaymentWithOrderId($payment));
+ }
+
+ public function testIsInlinePaymentWithOrderIdIsFalseIfQuoteIdIsConfigured()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference'));
+
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID));
+ $this->replaceByMock('singleton', 'ops/config', $configMock);
+
+ $ccMock = $this->getModelMock('ops/payment_cc', array('hasBrandAliasInterfaceSupport', 'getConfig'));
+ $ccMock->expects($this->once())
+ ->method('hasBrandAliasInterfaceSupport')
+ ->will($this->returnValue(true));
+
+
+ $payment = $this->getModelMock('payment/info', array('getMethodInstance'));
+ $payment->expects($this->any())
+ ->method('getMethodInstance')
+ ->will($this->returnValue($ccMock));
+
+ $this->assertFalse(Mage::helper('ops/payment')->isInlinePaymentWithOrderId($payment));
+ }
+
+ public function testIsInlinePaymentWithOrderIdIsFalseIfQuoteIdIsConfiguredForDirectDebit()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference'));
+
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID));
+ $this->replaceByMock('singleton', 'ops/config', $configMock);
+
+ $payment = $this->getModelMock('payment/info', array('getMethodInstance'));
+ $payment->expects($this->any())
+ ->method('getMethodInstance')
+ ->will($this->returnValue(Mage::getModel('ops/payment_directDebit')));
+
+ $this->assertFalse(Mage::helper('ops/payment')->isInlinePaymentWithOrderId($payment));
+ }
+
+ public function testIsInlinePaymentWithOrderIdIsTrueIfOrderIdIsConfiguredForDirectDebit()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference'));
+
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID));
+ $this->replaceByMock('singleton', 'ops/config', $configMock);
+
+
+ $payment = $this->getModelMock('payment/info', array('getMethodInstance'));
+ $payment->expects($this->any())
+ ->method('getMethodInstance')
+ ->will($this->returnValue(Mage::getModel('ops/payment_directDebit')));
+
+ $this->assertTrue(Mage::helper('ops/payment')->isInlinePaymentWithOrderId($payment));
+ }
+
+ public function testIsInlinePaymentWithQuoteId()
+ {
+ $directDebitMock = $this->getModelMock('ops/payment_directDebit', array('getConfigPaymentAction'));
+ $directDebitMock->expects($this->once())
+ ->method('getConfigPaymentAction')
+ ->will($this->returnValue(''));
+
+ $payment = $this->getModelMock('payment/info', array('getMethodInstance'));
+ $payment->expects($this->any())
+ ->method('getMethodInstance')
+ ->will($this->returnValue($directDebitMock));
+
+ $this->assertTrue(Mage::helper('ops/payment')->isInlinePaymentWithQuoteId($payment));
+ }
+
+ public function testSetInvoicesToPaid()
+ {
+ /** @var Mage_Sales_Model_Resource_Order_Invoice_Collection $invoiceCollection */
+ $invoiceCollection = $this->getResourceModelMock('sales/order_invoice_collection', array('save'));
+ $invoiceCollection->addItem(Mage::getModel('sales/order_invoice'));
+ $order = $this->getModelMock('sales/order', array('save', 'getInvoiceCollection'));
+ $order->expects($this->any())
+ ->method('getInvoiceCollection')
+ ->will($this->returnValue($invoiceCollection));
+ Mage::helper('ops/payment')->setInvoicesToPaid($order);
+ foreach ($order->getInvoiceCollection() as $invoice) {
+ $this->assertEquals(Mage_Sales_Model_Order_Invoice::STATE_PAID, $invoice->getState());
+ }
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/PaymentTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/PaymentTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/QuoteTest.php b/app/code/community/Netresearch/OPS/Test/Helper/QuoteTest.php
new file mode 100644
index 0000000..8a655ea
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/QuoteTest.php
@@ -0,0 +1,176 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Test_Helper_QuoteTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ public function testGetDataHelper()
+ {
+ $this->assertTrue(Mage::helper('ops/quote')->getDataHelper() instanceof Netresearch_OPS_Helper_Data);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testCleanUpOldPaymentInformation()
+ {
+ $payment = Mage::getModel('sales/quote_payment')->load(3);
+ $this->assertArrayHasKey('cvc', $payment->getAdditionalInformation());
+ Mage::helper('ops/quote')->cleanUpOldPaymentInformation();
+ $payment = Mage::getModel('sales/quote_payment')->load(3);
+ $this->assertArrayNotHasKey(
+ 'cvc', $payment->getAdditionalInformation()
+ );
+ }
+
+ public function testGetQuoteCurrency()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $this->assertEquals(
+ Mage::app()->getStore($quote->getStoreId())->getBaseCurrencyCode(),
+ Mage::helper('ops/quote')->getQuoteCurrency($quote)
+ );
+ $forcedCurrency = new Varien_Object();
+ $forcedCurrency->setCode('USD');
+ $quote->setForcedCurrency($forcedCurrency);
+ $this->assertEquals(
+ 'USD', Mage::helper('ops/quote')->getQuoteCurrency($quote)
+ );
+ }
+
+ public function testGetPaymentActionForAuthorize()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $order->setPayment($payment);
+ $modelMock = $this->getModelMock(
+ 'ops/config', array('getPaymentAction')
+ );
+ $modelMock->expects($this->any())
+ ->method('getPaymentAction')
+ ->will(
+ $this->returnValue(
+ 'Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION'
+ )
+ );
+ $this->replaceByMock('model', 'ops/config', $modelMock);
+ $helper = Mage::helper('ops/quote');
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION,
+ $helper->getPaymentAction($order)
+ );
+ $order->getPayment()->setAdditionalInformation(
+ 'PM', 'Direct Debits DE'
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION,
+ $helper->getPaymentAction($order)
+ );
+ $order->getPayment()->setAdditionalInformation(
+ 'PM', 'Direct Debits AT'
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION,
+ $helper->getPaymentAction($order)
+ );
+ $order->getPayment()->setAdditionalInformation(
+ 'PM', 'Direct Debits NL'
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_ACTION,
+ $helper->getPaymentAction($order)
+ );
+ }
+
+ public function testGetPaymentActionForAuthorizeCapture()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $order->setPayment($payment);
+ $modelMock = $this->getModelMock(
+ 'ops/config', array('getPaymentAction')
+ );
+ $modelMock->expects($this->any())
+ ->method('getPaymentAction')
+ ->will($this->returnValue('authorize_capture'));
+ $this->replaceByMock('model', 'ops/config', $modelMock);
+ $helper = Mage::helper('ops/quote');
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION,
+ $helper->getPaymentAction($order)
+ );
+ $order->getPayment()->setAdditionalInformation(
+ 'PM', 'Direct Debits DE'
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION,
+ $helper->getPaymentAction($order)
+ );
+ $order->getPayment()->setAdditionalInformation(
+ 'PM', 'Direct Debits AT'
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION,
+ $helper->getPaymentAction($order)
+ );
+ $order->getPayment()->setAdditionalInformation(
+ 'PM', 'Direct Debits NL'
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_DIRECTDEBIT_NL,
+ $helper->getPaymentAction($order)
+ );
+ }
+
+
+ public function testGetQuoteWithAdminSession()
+ {
+ $fakeQuote = $this->getModelMock('sales/quote');
+ $this->replaceByMock('model', 'sales/quote', $fakeQuote);
+
+ $sessionMock = $this->getModelMockBuilder('adminhtml/session_quote')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->setMethods(null) // Enables original methods usage, because by default it overrides all methods
+ ->getMock();
+ $sessionMock->setData('quote', $fakeQuote);
+ $this->replaceByMock('singleton', 'adminhtml/session_quote', $sessionMock);
+ $helper = Mage::helper('ops/quote');
+ $this->assertEquals($fakeQuote, $helper->getQuote());
+ }
+
+ public function testGetQuoteWithCheckoutSession()
+ {
+ Mage::app()->setCurrentStore(1);
+
+ $fakeQuote = $this->getModelMock('sales/quote', array('setStoreId'));
+ $fakeQuote->expects($this->any())
+ ->method('setStoreId')
+ ->will($this->returnValue($fakeQuote));
+ $this->replaceByMock('model', 'sales/quote', $fakeQuote);
+
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $sessionMock->setData('quote', $fakeQuote);
+ $this->replaceByMock('singleton', 'checkout/session', $sessionMock);
+ /** @var Netresearch_OPS_Helper_Quote $helper */
+ $helper = Mage::helper('ops/quote');
+ $this->assertEquals($fakeQuote, $helper->getQuote());
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/QuoteTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Helper/QuoteTest/fixtures/.gitkeep
new file mode 100644
index 0000000..8b13789
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/QuoteTest/fixtures/.gitkeep
@@ -0,0 +1 @@
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest.php b/app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest.php
new file mode 100644
index 0000000..11bc23a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest.php
@@ -0,0 +1,116 @@
+
+ */
+?>
+setId(123)
+ ->setTrialPeriodUnit(true);
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . '123';
+ $this->assertEquals($id, $subject->generateSubscriptionId($profile));
+ $id .= Netresearch_OPS_Helper_Subscription::TRIAL_SUFFIX;
+ $this->assertEquals($id, $subject->generateSubscriptionId($profile, true));
+ }
+
+ public function testIsSubscriptionFeedback()
+ {
+ $subject = Mage::helper('ops/subscription');
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . '123'
+ . Netresearch_OPS_Helper_Subscription::TRIAL_SUFFIX;
+ $params = array(
+ 'orderID' => $id
+ );
+ $this->assertTrue($subject->isSubscriptionFeedback($params));
+ $params['orderID'] = '#10123123120';
+ $this->assertFalse($subject->isSubscriptionFeedback($params));
+
+ }
+
+ /**
+ * @loadFixture profile.yaml
+ */
+ public function testGetProfileForSubscription()
+ {
+ $subject = Mage::helper('ops/subscription');
+
+ $id = $subject::SUBSCRIPTION_PREFIX . 1;
+
+ $profile = $subject->getProfileForSubscription($id);
+ $this->assertEquals(1, $profile->getId());
+
+ $id = $subject::SUBSCRIPTION_PREFIX . 1 . $subject::TRIAL_SUFFIX;
+
+ $profile = $subject->getProfileForSubscription($id);
+ $this->assertEquals(1, $profile->getId());
+ }
+ /**
+ * @loadFixture profile.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Could find no subscription for id 2
+ */
+ public function testGetProfileForSubscriptionWithException()
+ {
+ $subject = Mage::helper('ops/subscription');
+
+ $id = $subject::SUBSCRIPTION_PREFIX . 2;
+
+ $profile = $subject->getProfileForSubscription($id);
+ $this->assertEquals(1, $profile->getId());
+ }
+
+ public function testIsTrialFeedback()
+ {
+ $subject = Mage::helper('ops/subscription');
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . '123';
+ $this->assertFalse($subject->isTrialFeedback($id));
+ $id .= Netresearch_OPS_Helper_Subscription::TRIAL_SUFFIX;
+ $this->assertTrue($subject->isTrialFeedback($id));
+
+ }
+
+ public function testGetBillingDayForPeriodUnit()
+ {
+ $subject = Mage::helper('ops/subscription');
+
+ $this->assertEquals(1, $subject->getBillingDayForPeriodUnit('abc'));
+ $this->assertEquals(1, $subject->getBillingDayForPeriodUnit(Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_WEEK));
+ $this->assertEquals(15, $subject->getBillingDayForPeriodUnit(Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_MONTH));
+ }
+
+
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest/fixtures/profile.yaml b/app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest/fixtures/profile.yaml
new file mode 100644
index 0000000..dc4f2ed
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/SubscriptionTest/fixtures/profile.yaml
@@ -0,0 +1,11 @@
+tables:
+ customer/entity:
+ - entity_id: 1
+
+ sales/recurring_profile:
+ - profile_id: 1
+ state: 'active'
+ customer_id: 1
+ store_id: 1
+ method_code: 'ops_recurring_cc'
+ reference_id: 'SUB-1'
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Validation/Checkout/StepTest.php b/app/code/community/Netresearch/OPS/Test/Helper/Validation/Checkout/StepTest.php
new file mode 100644
index 0000000..62f319b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/Validation/Checkout/StepTest.php
@@ -0,0 +1,44 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+
+
+class Netresearch_OPS_Test_Helper_Validation_Checkout_StepTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $stepHelper = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->stepHelper = Mage::helper('ops/validation_checkout_step');
+ }
+
+ public function testHelperReturnsNoStep()
+ {
+ $this->assertEquals('', $this->stepHelper->getStep(array()));
+ $this->assertEquals('', $this->stepHelper->getStep(array('SOME_OTHER_FIELD')));
+ }
+
+ public function testHelperReturnsBillingStep()
+ {
+ $expectedStep = Netresearch_OPS_Helper_Validation_Checkout_Step::BILLING_STEP;
+ $this->assertEquals($expectedStep, $this->stepHelper->getStep(array('OWNERADDRESS')));
+ $this->assertEquals($expectedStep, $this->stepHelper->getStep(array('OWNERADDRESS', 'SOME_OTHER_FIELD')));
+ $this->assertEquals($expectedStep, $this->stepHelper->getStep(array('ECOM_SHIPTO_POSTAL_STATE', 'SOME_OTHER_FIELD', 'CN')));
+ }
+
+ public function testHelperReturnsShippingStep()
+ {
+ $expectedStep = Netresearch_OPS_Helper_Validation_Checkout_Step::SHIPPING_STEP;
+ $this->assertEquals($expectedStep, $this->stepHelper->getStep(array('ECOM_SHIPTO_POSTAL_STATE')));
+ $this->assertEquals($expectedStep, $this->stepHelper->getStep(array('ECOM_SHIPTO_POSTAL_STATE', 'SOME_OTHER_FIELD')));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest.php b/app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest.php
new file mode 100644
index 0000000..03557a5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest.php
@@ -0,0 +1,94 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Helper_Validation_ResultTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $validationResultHelper = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ Mage::unregister('_helper/ops/validation_result');
+ $this->validationResultHelper = Mage::helper('ops/validation_result');
+ }
+
+ public function testBaseErroneousFields()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $messages = array('foo', 'bar');
+ $result = $this->validationResultHelper->getValidationFailedResult($messages, $quote);
+ $this->assertArrayHasKey('error', $result);
+ $this->assertArrayHasKey('goto_section', $result);
+ $this->assertArrayHasKey('opsError', $result);
+ $this->assertArrayHasKey('fields', $result);
+ }
+
+ public function testGetValidationFailedResultWithFieldMapping()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $configMock = $this->getModelMock('ops/config', array('getFrontendFieldMapping'));
+ $configMock->expects($this->once())
+ ->method('getFrontendFieldMapping')
+ ->will($this->returnValue(array('foo' => 'bar')));
+ $this->validationResultHelper->setConfig($configMock);
+ $this->validationResultHelper->setFormBlock(Mage::app()->getLayout()->createBlock('ops/form'));
+ $messages = array('foo' => 'bar');
+ $result = $this->validationResultHelper->getValidationFailedResult($messages, $quote);
+ $this->assertArrayHasKey('fields', $result);
+ $this->assertArrayHasKey('bar', $result['fields']);
+ }
+
+ /**
+ * @loadFixture quotes
+ */
+ public function testGetValidationFailedResultWithExistingAddress()
+ {
+ $quote = Mage::getModel('sales/quote')->load(1);
+ $checkoutStepHelperMock = $this->getHelperMock('ops/validation_checkout_step', array('getStep'));
+ $checkoutStepHelperMock->expects($this->exactly(2))
+ ->method('getStep')
+ ->will($this->onConsecutiveCalls('billing', 'shipping'));
+
+ $configMock = $this->getModelMock('ops/config', array('getFrontendFieldMapping'));
+ $configMock->expects($this->exactly(2))
+ ->method('getFrontendFieldMapping')
+ ->will($this->returnValue(array('foo' => 'bar')));
+ $this->validationResultHelper->setConfig($configMock);
+
+ $messages = array('foo' => 'bar');
+ $this->validationResultHelper->setCheckoutStepHelper($checkoutStepHelperMock);
+ $this->validationResultHelper->setFormBlock(Mage::app()->getLayout()->createBlock('ops/form'));
+ $result = $this->validationResultHelper->getValidationFailedResult($messages, $quote);
+ $this->assertArrayHasKey('fields', $result);
+ $this->assertArrayHasKey('billing-address-select', $result['fields']);
+
+ $result = $this->validationResultHelper->getValidationFailedResult($messages, $quote);
+ $this->assertArrayHasKey('fields', $result);
+ $this->assertArrayHasKey('shipping-address-select', $result['fields']);
+ }
+
+ public function testCleanResult()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $messages = array('foo' => 'bar');
+ $prevResult = array('update_section' => 'foo');
+
+ $configMock = $this->getModelMock('ops/config', array('getFrontendFieldMapping'));
+ $configMock->expects($this->once())
+ ->method('getFrontendFieldMapping')
+ ->will($this->returnValue(array('foo' => 'bar')));
+ $this->validationResultHelper->setConfig($configMock);
+ $this->validationResultHelper->setFormBlock(Mage::app()->getLayout()->createBlock('ops/form'));
+
+ $this->validationResultHelper->setResult($prevResult);
+ $result = $this->validationResultHelper->getValidationFailedResult($messages, $quote);
+ $this->assertArrayNotHasKey('update_section', $result);
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest/fixtures/quotes.yaml b/app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest/fixtures/quotes.yaml
new file mode 100644
index 0000000..1e3415c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/Validation/ResultTest/fixtures/quotes.yaml
@@ -0,0 +1,42 @@
+tables:
+ sales/quote:
+ - entity_id: 1
+ increment_id: 100000001
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ sales/quote_address:
+ - entity_id: 42
+ quote_id: 1
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: '12345678'
+
+ - entity_id: 43
+ quote_id: 1
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: '12345678'
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Helper/VersionTest.php b/app/code/community/Netresearch/OPS/Test/Helper/VersionTest.php
new file mode 100644
index 0000000..a27aeb8
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Helper/VersionTest.php
@@ -0,0 +1,92 @@
+helper = Mage::helper('ops/version');
+ }
+
+ public function testGetVersionForEditionEE()
+ {
+ $helperMethod = $this->getProtectedMethod($this->helper, 'getVersionForEdition');
+ $this->assertEquals(
+ Netresearch_OPS_Helper_Version::CAN_USE_APPLICABLE_FOR_QUOTE_EE_MINOR,
+ $helperMethod->invoke($this->helper, 'Enterprise')
+ );
+ }
+
+ public function testGetVersionForEditionCE()
+ {
+ $helperMethod = $this->getProtectedMethod($this->helper, 'getVersionForEdition');
+ $this->assertEquals(
+ Netresearch_OPS_Helper_Version::CAN_USE_APPLICABLE_FOR_QUOTE_CE_MINOR,
+ $helperMethod->invoke($this->helper, 'Community')
+ );
+ }
+
+ public function testGetVersionForEditionDefaultCE()
+ {
+ $helperMethod = $this->getProtectedMethod($this->helper, 'getVersionForEdition');
+ $this->assertEquals(
+ Netresearch_OPS_Helper_Version::CAN_USE_APPLICABLE_FOR_QUOTE_CE_MINOR,
+ $helperMethod->invoke($this->helper, null)
+ );
+ }
+
+ public function testCanUseApplicableForQuoteForEE()
+ {
+ $helperMock = $this->getHelperMock('ops/version', array('getVersionInfo'));
+ $helperMock->expects($this->any())
+ ->method('getVersionInfo')
+ ->will($this->returnValue(array('minor' => '14')));
+
+ $this->assertTrue($helperMock->canUseApplicableForQuote('Enterprise'));
+
+ $helperMock = $this->getHelperMock('ops/version', array('getVersionInfo'));
+ $helperMock->expects($this->any())
+ ->method('getVersionInfo')
+ ->will($this->returnValue(array('minor' => '13')));
+
+ $this->assertFalse($helperMock->canUseApplicableForQuote('Enterprise'));
+ }
+
+ public function testCanUseApplicableForQuoteForCE()
+ {
+ $helperMock = $this->getHelperMock('ops/version', array('getVersionInfo'));
+ $helperMock->expects($this->any())
+ ->method('getVersionInfo')
+ ->will($this->returnValue(array('minor' => '8')));
+
+ $this->assertTrue($helperMock->canUseApplicableForQuote('Community'));
+
+ $helperMock = $this->getHelperMock('ops/version', array('getVersionInfo'));
+ $helperMock->expects($this->any())
+ ->method('getVersionInfo')
+ ->will($this->returnValue(array('minor' => '7')));
+
+ $this->assertFalse($helperMock->canUseApplicableForQuote('Community'));
+
+
+ }
+
+ public function testGetVersionInfo()
+ {
+ $helperMethod = $this->getProtectedMethod($this->helper, 'getVersionInfo');
+ $this->assertEquals(Mage::getVersionInfo(), $helperMethod->invoke($this->helper));
+
+ }
+
+ protected function getProtectedMethod($class, $method)
+ {
+ $reflection_class = new ReflectionClass(get_class($class));
+ $method = $reflection_class->getMethod($method);
+ $method->setAccessible(true);
+ return $method;
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/AliasTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Model/AliasTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkShaTest.php b/app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkShaTest.php
new file mode 100644
index 0000000..2c440c1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkShaTest.php
@@ -0,0 +1,44 @@
+_model = Mage::getModel('ops/api_directlink');
+ $this->_shaKey = 'ksdf239sdnkvs2e9';
+ }
+
+ public function testShaGenerationWithoutSpecialChars()
+ {
+ $params = array(
+ 'ALIAS' => 'foo'
+ );
+ $expected = $params;
+ $expected['SHASIGN'] = '44194456a31b8ea1de461612b19f7255732438d5';
+ $this->assertEquals($expected, $this->_model->getEncodedParametersWithHash($params, $this->_shaKey, 0));
+ }
+
+ public function testShaGenerationWithSpecialChars()
+ {
+ $params = array(
+ 'AMOUNT' => '36980',
+ 'CARDNO' => '257354109BLZ86010090',
+ 'CN' => 'André Herrn',
+ 'CURRENCY' => 'EUR',
+ 'ED' => '9999',
+ 'OPERATION' => 'SAL',
+ 'ORDERID' => '20190',
+ 'PM' => 'Direct Debits DE',
+ 'PSPID' => 'NRMAGENTO',
+ 'PSWD' => 'magento1',
+ 'USERID' => 'NRMAGENTO1API',
+ );
+ $expected = $params;
+ $expected['SHASIGN'] = 'eb95f7d66879e9801fdbdf75095ce23147202c30';
+ $result = $this->_model->getEncodedParametersWithHash($params, $this->_shaKey, 0);
+ $this->assertEquals($expected, $result);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkTest.php b/app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkTest.php
new file mode 100644
index 0000000..f843684
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Api/DirectLinkTest.php
@@ -0,0 +1,253 @@
+_model = Mage::getModel('ops/api_directlink');
+ }
+
+ public function testCallInvalidUrl()
+ {
+ $response = $this->_model->call(array(), 'http://localhost');
+ $this->assertInternalType('string', $response);
+ }
+
+ public function testType()
+ {
+ $this->assertInstanceOf('Netresearch_OPS_Model_Api_DirectLink', $this->_model);
+ }
+
+ public function testXmlParser()
+ {
+ $xmlExample =
+ '
+
+ ';
+ $arrParams = $this->_model->getParamArrFromXmlString($xmlExample);
+ $this->assertEquals("1121212", $arrParams['orderID']);
+ $this->assertEquals("232", $arrParams['PAYID']);
+ $this->assertEquals("0", $arrParams['PAYIDSUB']);
+ $this->assertEquals("5", $arrParams['NCSTATUS']);
+ $this->assertEquals("50001111", $arrParams['NCERROR']);
+ $this->assertEquals("Some of the data entered is incorrect. Please retry.", $arrParams['NCERRORPLUS']);
+ $this->assertEquals("", $arrParams['ACCEPTANCE']);
+ $this->assertEquals("0", $arrParams['STATUS']);
+ $this->assertEquals("", $arrParams['amount']);
+ $this->assertEquals("", $arrParams['currency']);
+ }
+
+ public function testXmlParserWithHtmlAnswer()
+ {
+ $xmlExample =
+ '
+
+ PGZvcm0gbmFtZT0iZG93bmxvYWRmb3JtM0QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9UZXN0XzNEX0FDUy5hc3AiIG1ldGhvZD0icG9zdCI+DQo8Tk9TQ1JJUFQ+DQpKYXZhU2NyaXB0IGlzIGN1cnJlbnRseSBkaXNhYmxlZCBvciBpcyBub3Qgc3VwcG9ydGVkIGJ5IHlvdXIgYnJvd3Nlci48YnI+DQpQbGVhc2UgY2xpY2sgb24gdGhlICZxdW90O0NvbnRpbnVlJnF1b3Q7IGJ1dHRvbiB0byBjb250aW51ZSB0aGUgcHJvY2Vzc2luZyBvZiB5b3VyIDMtRCBzZWN1cmUgdHJhbnNhY3Rpb24uPGJyPg0KPGlucHV0IGNsYXNzPSJuY29sIiB0eXBlPSJzdWJtaXQiIHZhbHVlPSJDb250aW51ZSIgaWQ9InN1Ym1pdDEiIG5hbWU9InN1Ym1pdDEiIC8+DQo8L05PU0NSSVBUPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRktFWSIgdmFsdWU9IjA0MzA0MzI4NkE0M0ZDM0YyRDhFMDFCOUM2MzYwRTA1Qzg5NkZEMzYiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGVFMiIHZhbHVlPSIyMDExMDkxMjE2MjQ1MCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZTUCIgdmFsdWU9Ii9uY29sL3Rlc3Qvb3JkZXJkaXJlY3QuYXNwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iUGFSZXEiIHZhbHVlPSI8P3htbCB2ZXJzaW9uPSZxdW90OzEuMCZxdW90Oz8+PFRocmVlRFNlY3VyZT48TWVzc2FnZSBpZD0mcXVvdDsxMjMmcXVvdDs+PFBBUmVxPjx2ZXJzaW9uPjEuMDI8L3ZlcnNpb24+PE1lcmNoYW50PjxtZXJJRD5OUk1BR0VOVE8zPC9tZXJJRD48bmFtZT5OZXRyZXNlYXJjaCBHbWJIICZhbXA7YW1wOyBDby5LRzwvbmFtZT48dXJsPmh0dHA6Ly93d3cubmV0cmVzZWFyY2guZGU8L3VybD48L01lcmNoYW50PjxQdXJjaGFzZT48eGlkPjExNjI4OTgzPC94aWQ+PGFtb3VudD4xMjY4Ljc1PC9hbW91bnQ+PHB1cmNoQW1vdW50PjEyNjguNzU8L3B1cmNoQW1vdW50PjxjdXJyZW5jeT5FVVI8L2N1cnJlbmN5PjwvUHVyY2hhc2U+PENIPjxhY2N0SUQ+NDAwMDAwWFhYWFhYMDAwMjwvYWNjdElEPjxleHBpcnk+MDExNjwvZXhwaXJ5PjxzZWxCcmFuZD48L3NlbEJyYW5kPjwvQ0g+PC9QQVJlcT48L01lc3NhZ2U+PC9UaHJlZURTZWN1cmU+DQoiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJUZXJtVXJsIiB2YWx1ZT0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9BM0RTLmFzcCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Ik1EIiB2YWx1ZT0iTUFJTldQVEVTVDAwMDAxMTYyODk4MzAxKjEwNzUyNjIiIC8+DQo8L2Zvcm0+DQo8Zm9ybSBtZXRob2Q9InBvc3QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9hZ3JlZS5hc3AiIG5hbWU9InVwbG9hZEZvcm0zRCI+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGS0VZIiB2YWx1ZT0iMDZGM0MzMUQ2RkI1MzIzODg4NjhFRjlGNTA5RUNGNzlBQzIwRDJGMyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZUUyIgdmFsdWU9IjIwMTEwOTEyMTYyNDUwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRlNQIiB2YWx1ZT0iL25jb2wvdGVzdC9vcmRlcmRpcmVjdC5hc3AiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJicmFuZGluZyIgdmFsdWU9Ik9nb25lIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0icGF5aWQiIHZhbHVlPSIxMTYyODk4MyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0b3JlYWxpYXMiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJoYXNoX3BhcmFtIiB2YWx1ZT0iOTFBMzA1MjFEMEI0QTA1MEFBRDkzRDM5RDY2RkEyM0Y5OEIzRDQ4RCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InhpZF8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0YXR1c18zRCIgdmFsdWU9IlhYIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iZWNpXzNEIiB2YWx1ZT0iNyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhcmRudW1iZXIiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJFY29tX1BheW1lbnRfQ2FyZF9WZXJpZmljYXRpb24iIHZhbHVlPSIqMTA3NTI2MiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNWQ0ZsYWciIHZhbHVlPSIxIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iY2F2dl8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhdnZhbGdvcml0aG1fM0QiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJzaWduYXR1cmVPS18zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Imhhc2hfcGFyYW1fM0QiIHZhbHVlPSIwMzAzREZDMkI1OTM0MjZCQTExRkQ5RjJBNkQ0NDk5ODEwN0JGN0YzIiAvPg0KPC9mb3JtPg0KPFNDUklQVCBMQU5HVUFHRT0iSmF2YXNjcmlwdCIgRk9SPSJ3aW5kb3ciIEVWRU5UPSJvbkxvYWQiPg0KdmFyIHBvcHVwV2luOw0KdmFyIHN1Ym1pdHBvcHVwV2luID0gMDsNCg0KZnVuY3Rpb24gTG9hZFBvcHVwKCkgew0KCWlmIChzZWxmLm5hbWUgPT0gbnVsbCkJew0KCQlzZWxmLm5hbWUgPSAib2dvbmVNYWluIjsNCgl9DQoJcG9wdXBXaW4gPSB3aW5kb3cub3BlbignYWJvdXQ6YmxhbmsnLCAncG9wdXBXaW4nLCAnaGVpZ2h0PTQwMCwgd2lkdGg9MzkwLCBzdGF0dXM9eWVzLCBkZXBlbmRlbnQ9bm8sIHNjcm9sbGJhcnM9eWVzLCByZXNpemFibGU9bm8nKTsNCglpZiAocG9wdXBXaW4gIT0gbnVsbCkgew0KCQlpZiAgKCFwb3B1cFdpbiB8fCBwb3B1cFdpbi5jbG9zZWQpIHsNCgkJCXJldHVybiAxOw0KCQl9IGVsc2Ugew0KCQkJaWYgKCFwb3B1cFdpbi5vcGVuZXIgfHwgcG9wdXBXaW4ub3BlbmVyID09IG51bGwpIHsNCgkJCQlwb3B1cFdpbi5vcGVuZXIgPSBzZWxmOw0KCQkJfQ0KCQkJc2VsZi5kb2N1bWVudC5mb3Jtcy5kb3dubG9hZGZvcm0zRC50YXJnZXQgPSAncG9wdXBXaW4nOw0KCQkJaWYgKHN1Ym1pdHBvcHVwV2luID09IDEpIHsNCgkJCQlzZWxmLmRvY3VtZW50LmZvcm1zLmRvd25sb2FkZm9ybTNELnN1Ym1pdCgpOw0KCQkJfQ0KCQkJcG9wdXBXaW4uZm9jdXMoKTsNCgkJCXJldHVybiAwOw0KCQl9DQoJfSBlbHNlIHsNCgkJcmV0dXJuIDE7DQoJfQ0KfQ0KCXNlbGYuZG9jdW1lbnQuZm9ybXMuZG93bmxvYWRmb3JtM0Quc3VibWl0KCk7DQovLy0tPg0KPC9TQ1JJUFQ+DQo=
+ ';
+ $arrParams = $this->_model->getParamArrFromXmlString($xmlExample);
+ $this->assertEquals("1121212", $arrParams['orderID']);
+ $this->assertEquals("232", $arrParams['PAYID']);
+ $this->assertEquals("PGZvcm0gbmFtZT0iZG93bmxvYWRmb3JtM0QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9UZXN0XzNEX0FDUy5hc3AiIG1ldGhvZD0icG9zdCI+DQo8Tk9TQ1JJUFQ+DQpKYXZhU2NyaXB0IGlzIGN1cnJlbnRseSBkaXNhYmxlZCBvciBpcyBub3Qgc3VwcG9ydGVkIGJ5IHlvdXIgYnJvd3Nlci48YnI+DQpQbGVhc2UgY2xpY2sgb24gdGhlICZxdW90O0NvbnRpbnVlJnF1b3Q7IGJ1dHRvbiB0byBjb250aW51ZSB0aGUgcHJvY2Vzc2luZyBvZiB5b3VyIDMtRCBzZWN1cmUgdHJhbnNhY3Rpb24uPGJyPg0KPGlucHV0IGNsYXNzPSJuY29sIiB0eXBlPSJzdWJtaXQiIHZhbHVlPSJDb250aW51ZSIgaWQ9InN1Ym1pdDEiIG5hbWU9InN1Ym1pdDEiIC8+DQo8L05PU0NSSVBUPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRktFWSIgdmFsdWU9IjA0MzA0MzI4NkE0M0ZDM0YyRDhFMDFCOUM2MzYwRTA1Qzg5NkZEMzYiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGVFMiIHZhbHVlPSIyMDExMDkxMjE2MjQ1MCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZTUCIgdmFsdWU9Ii9uY29sL3Rlc3Qvb3JkZXJkaXJlY3QuYXNwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iUGFSZXEiIHZhbHVlPSI8P3htbCB2ZXJzaW9uPSZxdW90OzEuMCZxdW90Oz8+PFRocmVlRFNlY3VyZT48TWVzc2FnZSBpZD0mcXVvdDsxMjMmcXVvdDs+PFBBUmVxPjx2ZXJzaW9uPjEuMDI8L3ZlcnNpb24+PE1lcmNoYW50PjxtZXJJRD5OUk1BR0VOVE8zPC9tZXJJRD48bmFtZT5OZXRyZXNlYXJjaCBHbWJIICZhbXA7YW1wOyBDby5LRzwvbmFtZT48dXJsPmh0dHA6Ly93d3cubmV0cmVzZWFyY2guZGU8L3VybD48L01lcmNoYW50PjxQdXJjaGFzZT48eGlkPjExNjI4OTgzPC94aWQ+PGFtb3VudD4xMjY4Ljc1PC9hbW91bnQ+PHB1cmNoQW1vdW50PjEyNjguNzU8L3B1cmNoQW1vdW50PjxjdXJyZW5jeT5FVVI8L2N1cnJlbmN5PjwvUHVyY2hhc2U+PENIPjxhY2N0SUQ+NDAwMDAwWFhYWFhYMDAwMjwvYWNjdElEPjxleHBpcnk+MDExNjwvZXhwaXJ5PjxzZWxCcmFuZD48L3NlbEJyYW5kPjwvQ0g+PC9QQVJlcT48L01lc3NhZ2U+PC9UaHJlZURTZWN1cmU+DQoiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJUZXJtVXJsIiB2YWx1ZT0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9BM0RTLmFzcCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Ik1EIiB2YWx1ZT0iTUFJTldQVEVTVDAwMDAxMTYyODk4MzAxKjEwNzUyNjIiIC8+DQo8L2Zvcm0+DQo8Zm9ybSBtZXRob2Q9InBvc3QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9hZ3JlZS5hc3AiIG5hbWU9InVwbG9hZEZvcm0zRCI+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGS0VZIiB2YWx1ZT0iMDZGM0MzMUQ2RkI1MzIzODg4NjhFRjlGNTA5RUNGNzlBQzIwRDJGMyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZUUyIgdmFsdWU9IjIwMTEwOTEyMTYyNDUwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRlNQIiB2YWx1ZT0iL25jb2wvdGVzdC9vcmRlcmRpcmVjdC5hc3AiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJicmFuZGluZyIgdmFsdWU9Ik9nb25lIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0icGF5aWQiIHZhbHVlPSIxMTYyODk4MyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0b3JlYWxpYXMiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJoYXNoX3BhcmFtIiB2YWx1ZT0iOTFBMzA1MjFEMEI0QTA1MEFBRDkzRDM5RDY2RkEyM0Y5OEIzRDQ4RCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InhpZF8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0YXR1c18zRCIgdmFsdWU9IlhYIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iZWNpXzNEIiB2YWx1ZT0iNyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhcmRudW1iZXIiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJFY29tX1BheW1lbnRfQ2FyZF9WZXJpZmljYXRpb24iIHZhbHVlPSIqMTA3NTI2MiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNWQ0ZsYWciIHZhbHVlPSIxIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iY2F2dl8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhdnZhbGdvcml0aG1fM0QiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJzaWduYXR1cmVPS18zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Imhhc2hfcGFyYW1fM0QiIHZhbHVlPSIwMzAzREZDMkI1OTM0MjZCQTExRkQ5RjJBNkQ0NDk5ODEwN0JGN0YzIiAvPg0KPC9mb3JtPg0KPFNDUklQVCBMQU5HVUFHRT0iSmF2YXNjcmlwdCIgRk9SPSJ3aW5kb3ciIEVWRU5UPSJvbkxvYWQiPg0KdmFyIHBvcHVwV2luOw0KdmFyIHN1Ym1pdHBvcHVwV2luID0gMDsNCg0KZnVuY3Rpb24gTG9hZFBvcHVwKCkgew0KCWlmIChzZWxmLm5hbWUgPT0gbnVsbCkJew0KCQlzZWxmLm5hbWUgPSAib2dvbmVNYWluIjsNCgl9DQoJcG9wdXBXaW4gPSB3aW5kb3cub3BlbignYWJvdXQ6YmxhbmsnLCAncG9wdXBXaW4nLCAnaGVpZ2h0PTQwMCwgd2lkdGg9MzkwLCBzdGF0dXM9eWVzLCBkZXBlbmRlbnQ9bm8sIHNjcm9sbGJhcnM9eWVzLCByZXNpemFibGU9bm8nKTsNCglpZiAocG9wdXBXaW4gIT0gbnVsbCkgew0KCQlpZiAgKCFwb3B1cFdpbiB8fCBwb3B1cFdpbi5jbG9zZWQpIHsNCgkJCXJldHVybiAxOw0KCQl9IGVsc2Ugew0KCQkJaWYgKCFwb3B1cFdpbi5vcGVuZXIgfHwgcG9wdXBXaW4ub3BlbmVyID09IG51bGwpIHsNCgkJCQlwb3B1cFdpbi5vcGVuZXIgPSBzZWxmOw0KCQkJfQ0KCQkJc2VsZi5kb2N1bWVudC5mb3Jtcy5kb3dubG9hZGZvcm0zRC50YXJnZXQgPSAncG9wdXBXaW4nOw0KCQkJaWYgKHN1Ym1pdHBvcHVwV2luID09IDEpIHsNCgkJCQlzZWxmLmRvY3VtZW50LmZvcm1zLmRvd25sb2FkZm9ybTNELnN1Ym1pdCgpOw0KCQkJfQ0KCQkJcG9wdXBXaW4uZm9jdXMoKTsNCgkJCXJldHVybiAwOw0KCQl9DQoJfSBlbHNlIHsNCgkJcmV0dXJuIDE7DQoJfQ0KfQ0KCXNlbGYuZG9jdW1lbnQuZm9ybXMuZG93bmxvYWRmb3JtM0Quc3VibWl0KCk7DQovLy0tPg0KPC9TQ1JJUFQ+DQo=", $arrParams['HTML_ANSWER']);
+ }
+
+
+ public function testWithNoXmlResponse()
+ {
+ $xmlExample = '';
+ $this->assertTrue($this->setExpectedException('PHPUnit_Framework_ExpectationFailedException'));
+ $arrParams = $this->_model->getParamArrFromXmlString($xmlExample);
+ $xmlExample = 'N';
+ $arrParams = $this->_model->getParamArrFromXmlString($xmlExample);
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testIsInvalidResponseWithEmptyData()
+ {
+ $this->_model->checkResponse(null);
+ }
+
+ public function testIsValidResponse()
+ {
+ $this->assertTrue(is_null($this->_model->checkResponse(array('NCERROR' => 0))));
+ }
+
+ public function testGetResponseParamsWithValidCallResponse()
+ {
+ $xmlExample =
+ '
+
+ PGZvcm0gbmFtZT0iZG93bmxvYWRmb3JtM0QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9UZXN0XzNEX0FDUy5hc3AiIG1ldGhvZD0icG9zdCI+DQo8Tk9TQ1JJUFQ+DQpKYXZhU2NyaXB0IGlzIGN1cnJlbnRseSBkaXNhYmxlZCBvciBpcyBub3Qgc3VwcG9ydGVkIGJ5IHlvdXIgYnJvd3Nlci48YnI+DQpQbGVhc2UgY2xpY2sgb24gdGhlICZxdW90O0NvbnRpbnVlJnF1b3Q7IGJ1dHRvbiB0byBjb250aW51ZSB0aGUgcHJvY2Vzc2luZyBvZiB5b3VyIDMtRCBzZWN1cmUgdHJhbnNhY3Rpb24uPGJyPg0KPGlucHV0IGNsYXNzPSJuY29sIiB0eXBlPSJzdWJtaXQiIHZhbHVlPSJDb250aW51ZSIgaWQ9InN1Ym1pdDEiIG5hbWU9InN1Ym1pdDEiIC8+DQo8L05PU0NSSVBUPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRktFWSIgdmFsdWU9IjA0MzA0MzI4NkE0M0ZDM0YyRDhFMDFCOUM2MzYwRTA1Qzg5NkZEMzYiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGVFMiIHZhbHVlPSIyMDExMDkxMjE2MjQ1MCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZTUCIgdmFsdWU9Ii9uY29sL3Rlc3Qvb3JkZXJkaXJlY3QuYXNwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iUGFSZXEiIHZhbHVlPSI8P3htbCB2ZXJzaW9uPSZxdW90OzEuMCZxdW90Oz8+PFRocmVlRFNlY3VyZT48TWVzc2FnZSBpZD0mcXVvdDsxMjMmcXVvdDs+PFBBUmVxPjx2ZXJzaW9uPjEuMDI8L3ZlcnNpb24+PE1lcmNoYW50PjxtZXJJRD5OUk1BR0VOVE8zPC9tZXJJRD48bmFtZT5OZXRyZXNlYXJjaCBHbWJIICZhbXA7YW1wOyBDby5LRzwvbmFtZT48dXJsPmh0dHA6Ly93d3cubmV0cmVzZWFyY2guZGU8L3VybD48L01lcmNoYW50PjxQdXJjaGFzZT48eGlkPjExNjI4OTgzPC94aWQ+PGFtb3VudD4xMjY4Ljc1PC9hbW91bnQ+PHB1cmNoQW1vdW50PjEyNjguNzU8L3B1cmNoQW1vdW50PjxjdXJyZW5jeT5FVVI8L2N1cnJlbmN5PjwvUHVyY2hhc2U+PENIPjxhY2N0SUQ+NDAwMDAwWFhYWFhYMDAwMjwvYWNjdElEPjxleHBpcnk+MDExNjwvZXhwaXJ5PjxzZWxCcmFuZD48L3NlbEJyYW5kPjwvQ0g+PC9QQVJlcT48L01lc3NhZ2U+PC9UaHJlZURTZWN1cmU+DQoiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJUZXJtVXJsIiB2YWx1ZT0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9BM0RTLmFzcCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Ik1EIiB2YWx1ZT0iTUFJTldQVEVTVDAwMDAxMTYyODk4MzAxKjEwNzUyNjIiIC8+DQo8L2Zvcm0+DQo8Zm9ybSBtZXRob2Q9InBvc3QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9hZ3JlZS5hc3AiIG5hbWU9InVwbG9hZEZvcm0zRCI+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGS0VZIiB2YWx1ZT0iMDZGM0MzMUQ2RkI1MzIzODg4NjhFRjlGNTA5RUNGNzlBQzIwRDJGMyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZUUyIgdmFsdWU9IjIwMTEwOTEyMTYyNDUwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRlNQIiB2YWx1ZT0iL25jb2wvdGVzdC9vcmRlcmRpcmVjdC5hc3AiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJicmFuZGluZyIgdmFsdWU9Ik9nb25lIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0icGF5aWQiIHZhbHVlPSIxMTYyODk4MyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0b3JlYWxpYXMiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJoYXNoX3BhcmFtIiB2YWx1ZT0iOTFBMzA1MjFEMEI0QTA1MEFBRDkzRDM5RDY2RkEyM0Y5OEIzRDQ4RCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InhpZF8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0YXR1c18zRCIgdmFsdWU9IlhYIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iZWNpXzNEIiB2YWx1ZT0iNyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhcmRudW1iZXIiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJFY29tX1BheW1lbnRfQ2FyZF9WZXJpZmljYXRpb24iIHZhbHVlPSIqMTA3NTI2MiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNWQ0ZsYWciIHZhbHVlPSIxIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iY2F2dl8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhdnZhbGdvcml0aG1fM0QiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJzaWduYXR1cmVPS18zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Imhhc2hfcGFyYW1fM0QiIHZhbHVlPSIwMzAzREZDMkI1OTM0MjZCQTExRkQ5RjJBNkQ0NDk5ODEwN0JGN0YzIiAvPg0KPC9mb3JtPg0KPFNDUklQVCBMQU5HVUFHRT0iSmF2YXNjcmlwdCIgRk9SPSJ3aW5kb3ciIEVWRU5UPSJvbkxvYWQiPg0KdmFyIHBvcHVwV2luOw0KdmFyIHN1Ym1pdHBvcHVwV2luID0gMDsNCg0KZnVuY3Rpb24gTG9hZFBvcHVwKCkgew0KCWlmIChzZWxmLm5hbWUgPT0gbnVsbCkJew0KCQlzZWxmLm5hbWUgPSAib2dvbmVNYWluIjsNCgl9DQoJcG9wdXBXaW4gPSB3aW5kb3cub3BlbignYWJvdXQ6YmxhbmsnLCAncG9wdXBXaW4nLCAnaGVpZ2h0PTQwMCwgd2lkdGg9MzkwLCBzdGF0dXM9eWVzLCBkZXBlbmRlbnQ9bm8sIHNjcm9sbGJhcnM9eWVzLCByZXNpemFibGU9bm8nKTsNCglpZiAocG9wdXBXaW4gIT0gbnVsbCkgew0KCQlpZiAgKCFwb3B1cFdpbiB8fCBwb3B1cFdpbi5jbG9zZWQpIHsNCgkJCXJldHVybiAxOw0KCQl9IGVsc2Ugew0KCQkJaWYgKCFwb3B1cFdpbi5vcGVuZXIgfHwgcG9wdXBXaW4ub3BlbmVyID09IG51bGwpIHsNCgkJCQlwb3B1cFdpbi5vcGVuZXIgPSBzZWxmOw0KCQkJfQ0KCQkJc2VsZi5kb2N1bWVudC5mb3Jtcy5kb3dubG9hZGZvcm0zRC50YXJnZXQgPSAncG9wdXBXaW4nOw0KCQkJaWYgKHN1Ym1pdHBvcHVwV2luID09IDEpIHsNCgkJCQlzZWxmLmRvY3VtZW50LmZvcm1zLmRvd25sb2FkZm9ybTNELnN1Ym1pdCgpOw0KCQkJfQ0KCQkJcG9wdXBXaW4uZm9jdXMoKTsNCgkJCXJldHVybiAwOw0KCQl9DQoJfSBlbHNlIHsNCgkJcmV0dXJuIDE7DQoJfQ0KfQ0KCXNlbGYuZG9jdW1lbnQuZm9ybXMuZG93bmxvYWRmb3JtM0Quc3VibWl0KCk7DQovLy0tPg0KPC9TQ1JJUFQ+DQo=
+ ';
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('call'));
+ $directLinkMock->expects($this->any())
+ ->method('call')
+ ->will($this->returnValue($xmlExample));
+
+ $class = new ReflectionClass(get_class(Mage::getModel('ops/api_directlink')));
+ $method = $class->getMethod('getResponseParams');
+ $method->setAccessible(true);
+ $result = $method->invokeArgs($directLinkMock, array(array('foo' => '111', 'ORDERID' => 4711), 'bar'));
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(array_key_exists('orderID', $result));
+ $this->assertTrue(array_key_exists('PAYID', $result));
+ $this->assertTrue(array_key_exists('PAYIDSUB', $result));
+ $this->assertTrue(array_key_exists('NCSTATUS', $result));
+ $this->assertTrue(array_key_exists('NCERROR', $result));
+ $this->assertTrue(array_key_exists('NCERROR', $result));
+ $this->assertTrue(array_key_exists('NCERRORPLUS', $result));
+ $this->assertTrue(array_key_exists('ACCEPTANCE', $result));
+ $this->assertTrue(array_key_exists('STATUS', $result));
+ $this->assertTrue(array_key_exists('amount', $result));
+ $this->assertTrue(array_key_exists('currency', $result));
+ $this->assertTrue(array_key_exists('HTML_ANSWER', $result));
+ }
+
+ public function testGetResponseParamsWithValidCallButWrongEncodedResponse()
+ {
+ $xmlExample =
+ '
+
+ PGZvcm0gbmFtZT0iZG93bmxvYWRmb3JtM0QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9UZXN0XzNEX0FDUy5hc3AiIG1ldGhvZD0icG9zdCI+DQo8Tk9TQ1JJUFQ+DQpKYXZhU2NyaXB0IGlzIGN1cnJlbnRseSBkaXNhYmxlZCBvciBpcyBub3Qgc3VwcG9ydGVkIGJ5IHlvdXIgYnJvd3Nlci48YnI+DQpQbGVhc2UgY2xpY2sgb24gdGhlICZxdW90O0NvbnRpbnVlJnF1b3Q7IGJ1dHRvbiB0byBjb250aW51ZSB0aGUgcHJvY2Vzc2luZyBvZiB5b3VyIDMtRCBzZWN1cmUgdHJhbnNhY3Rpb24uPGJyPg0KPGlucHV0IGNsYXNzPSJuY29sIiB0eXBlPSJzdWJtaXQiIHZhbHVlPSJDb250aW51ZSIgaWQ9InN1Ym1pdDEiIG5hbWU9InN1Ym1pdDEiIC8+DQo8L05PU0NSSVBUPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRktFWSIgdmFsdWU9IjA0MzA0MzI4NkE0M0ZDM0YyRDhFMDFCOUM2MzYwRTA1Qzg5NkZEMzYiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGVFMiIHZhbHVlPSIyMDExMDkxMjE2MjQ1MCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZTUCIgdmFsdWU9Ii9uY29sL3Rlc3Qvb3JkZXJkaXJlY3QuYXNwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iUGFSZXEiIHZhbHVlPSI8P3htbCB2ZXJzaW9uPSZxdW90OzEuMCZxdW90Oz8+PFRocmVlRFNlY3VyZT48TWVzc2FnZSBpZD0mcXVvdDsxMjMmcXVvdDs+PFBBUmVxPjx2ZXJzaW9uPjEuMDI8L3ZlcnNpb24+PE1lcmNoYW50PjxtZXJJRD5OUk1BR0VOVE8zPC9tZXJJRD48bmFtZT5OZXRyZXNlYXJjaCBHbWJIICZhbXA7YW1wOyBDby5LRzwvbmFtZT48dXJsPmh0dHA6Ly93d3cubmV0cmVzZWFyY2guZGU8L3VybD48L01lcmNoYW50PjxQdXJjaGFzZT48eGlkPjExNjI4OTgzPC94aWQ+PGFtb3VudD4xMjY4Ljc1PC9hbW91bnQ+PHB1cmNoQW1vdW50PjEyNjguNzU8L3B1cmNoQW1vdW50PjxjdXJyZW5jeT5FVVI8L2N1cnJlbmN5PjwvUHVyY2hhc2U+PENIPjxhY2N0SUQ+NDAwMDAwWFhYWFhYMDAwMjwvYWNjdElEPjxleHBpcnk+MDExNjwvZXhwaXJ5PjxzZWxCcmFuZD48L3NlbEJyYW5kPjwvQ0g+PC9QQVJlcT48L01lc3NhZ2U+PC9UaHJlZURTZWN1cmU+DQoiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJUZXJtVXJsIiB2YWx1ZT0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9BM0RTLmFzcCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Ik1EIiB2YWx1ZT0iTUFJTldQVEVTVDAwMDAxMTYyODk4MzAxKjEwNzUyNjIiIC8+DQo8L2Zvcm0+DQo8Zm9ybSBtZXRob2Q9InBvc3QiIGFjdGlvbj0iaHR0cHM6Ly9zZWN1cmUub2dvbmUuY29tL25jb2wvdGVzdC9vcmRlcl9hZ3JlZS5hc3AiIG5hbWU9InVwbG9hZEZvcm0zRCI+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJDU1JGS0VZIiB2YWx1ZT0iMDZGM0MzMUQ2RkI1MzIzODg4NjhFRjlGNTA5RUNGNzlBQzIwRDJGMyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNTUkZUUyIgdmFsdWU9IjIwMTEwOTEyMTYyNDUwIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iQ1NSRlNQIiB2YWx1ZT0iL25jb2wvdGVzdC9vcmRlcmRpcmVjdC5hc3AiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJicmFuZGluZyIgdmFsdWU9Ik9nb25lIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0icGF5aWQiIHZhbHVlPSIxMTYyODk4MyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0b3JlYWxpYXMiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJoYXNoX3BhcmFtIiB2YWx1ZT0iOTFBMzA1MjFEMEI0QTA1MEFBRDkzRDM5RDY2RkEyM0Y5OEIzRDQ4RCIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InhpZF8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9InN0YXR1c18zRCIgdmFsdWU9IlhYIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iZWNpXzNEIiB2YWx1ZT0iNyIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhcmRudW1iZXIiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJFY29tX1BheW1lbnRfQ2FyZF9WZXJpZmljYXRpb24iIHZhbHVlPSIqMTA3NTI2MiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9IkNWQ0ZsYWciIHZhbHVlPSIxIiAvPg0KPGlucHV0IHR5cGU9ImhpZGRlbiIgbmFtZT0iY2F2dl8zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9ImNhdnZhbGdvcml0aG1fM0QiIHZhbHVlPSIiIC8+DQo8aW5wdXQgdHlwZT0iaGlkZGVuIiBuYW1lPSJzaWduYXR1cmVPS18zRCIgdmFsdWU9IiIgLz4NCjxpbnB1dCB0eXBlPSJoaWRkZW4iIG5hbWU9Imhhc2hfcGFyYW1fM0QiIHZhbHVlPSIwMzAzREZDMkI1OTM0MjZCQTExRkQ5RjJBNkQ0NDk5ODEwN0JGN0YzIiAvPg0KPC9mb3JtPg0KPFNDUklQVCBMQU5HVUFHRT0iSmF2YXNjcmlwdCIgRk9SPSJ3aW5kb3ciIEVWRU5UPSJvbkxvYWQiPg0KdmFyIHBvcHVwV2luOw0KdmFyIHN1Ym1pdHBvcHVwV2luID0gMDsNCg0KZnVuY3Rpb24gTG9hZFBvcHVwKCkgew0KCWlmIChzZWxmLm5hbWUgPT0gbnVsbCkJew0KCQlzZWxmLm5hbWUgPSAib2dvbmVNYWluIjsNCgl9DQoJcG9wdXBXaW4gPSB3aW5kb3cub3BlbignYWJvdXQ6YmxhbmsnLCAncG9wdXBXaW4nLCAnaGVpZ2h0PTQwMCwgd2lkdGg9MzkwLCBzdGF0dXM9eWVzLCBkZXBlbmRlbnQ9bm8sIHNjcm9sbGJhcnM9eWVzLCByZXNpemFibGU9bm8nKTsNCglpZiAocG9wdXBXaW4gIT0gbnVsbCkgew0KCQlpZiAgKCFwb3B1cFdpbiB8fCBwb3B1cFdpbi5jbG9zZWQpIHsNCgkJCXJldHVybiAxOw0KCQl9IGVsc2Ugew0KCQkJaWYgKCFwb3B1cFdpbi5vcGVuZXIgfHwgcG9wdXBXaW4ub3BlbmVyID09IG51bGwpIHsNCgkJCQlwb3B1cFdpbi5vcGVuZXIgPSBzZWxmOw0KCQkJfQ0KCQkJc2VsZi5kb2N1bWVudC5mb3Jtcy5kb3dubG9hZGZvcm0zRC50YXJnZXQgPSAncG9wdXBXaW4nOw0KCQkJaWYgKHN1Ym1pdHBvcHVwV2luID09IDEpIHsNCgkJCQlzZWxmLmRvY3VtZW50LmZvcm1zLmRvd25sb2FkZm9ybTNELnN1Ym1pdCgpOw0KCQkJfQ0KCQkJcG9wdXBXaW4uZm9jdXMoKTsNCgkJCXJldHVybiAwOw0KCQl9DQoJfSBlbHNlIHsNCgkJcmV0dXJuIDE7DQoJfQ0KfQ0KCXNlbGYuZG9jdW1lbnQuZm9ybXMuZG93bmxvYWRmb3JtM0Quc3VibWl0KCk7DQovLy0tPg0KPC9TQ1JJUFQ+DQo=
+ ';
+ $xmlExample = utf8_decode($xmlExample);
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('call'));
+ $directLinkMock->expects($this->any())
+ ->method('call')
+ ->will($this->returnValue($xmlExample));
+
+ $class = new ReflectionClass(get_class(Mage::getModel('ops/api_directlink')));
+ $method = $class->getMethod('getResponseParams');
+ $method->setAccessible(true);
+ $result = $method->invokeArgs($directLinkMock, array(array('foo' => '111', 'ORDERID' => 4711), 'bar'));
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(array_key_exists('orderID', $result));
+ $this->assertTrue(array_key_exists('PAYID', $result));
+ $this->assertTrue(array_key_exists('PAYIDSUB', $result));
+ $this->assertTrue(array_key_exists('NCSTATUS', $result));
+ $this->assertTrue(array_key_exists('NCERROR', $result));
+ $this->assertTrue(array_key_exists('NCERROR', $result));
+ $this->assertTrue(array_key_exists('NCERRORPLUS', $result));
+ $this->assertTrue(array_key_exists('ACCEPTANCE', $result));
+ $this->assertTrue(array_key_exists('STATUS', $result));
+ $this->assertTrue(array_key_exists('amount', $result));
+ $this->assertTrue(array_key_exists('currency', $result));
+ $this->assertTrue(array_key_exists('HTML_ANSWER', $result));
+ $this->assertTrue(array_key_exists('CN', $result));
+ $this->assertEquals('Max Mueller', $result['CN']);
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testGetResponseParamsWithRetryCountExceeded()
+ {
+ $maxAllowedRetryCount = Netresearch_OPS_Model_Api_DirectLink::MAX_RETRY_COUNT;
+ $class = new ReflectionClass(get_class(Mage::getModel('ops/api_directlink')));
+ $method = $class->getMethod('getResponseParams');
+ $method->setAccessible(true);
+ $result = $method->invokeArgs(Mage::getModel('ops/api_directlink'), array(array('foo' => '123', 'ORDERID' => '4711'), 'bar', ++$maxAllowedRetryCount));
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testGetResponseParamsWithInvalidResponse()
+ {
+ $xmlExample = '';
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('call'));
+ $directLinkMock->expects($this->any())
+ ->method('call')
+ ->will($this->returnValue($xmlExample));
+
+ $class = new ReflectionClass(get_class(Mage::getModel('ops/api_directlink')));
+ $method = $class->getMethod('getResponseParams');
+ $method->setAccessible(true);
+ $result = $method->invokeArgs($directLinkMock, array(array('foo' => '12334', 'ORDERID' => 4711), 'bar'));
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testCheckResponseNcErrorSet()
+ {
+ $responseParams = array('NCERROR' => '50001111');
+ $this->_model->checkResponse($responseParams);
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testCheckResponseNcErrorEmpty()
+ {
+ $responseParams = array('NCERROR' => '1', 'NCERRORPLUS' => 'Error occured');
+ $this->_model->checkResponse($responseParams);
+ }
+
+ public function testCheckResponseNrErrorWithStatus()
+ {
+ $responseParams = array('NCERROR' => '1', 'STATUS' => 4);
+ try {
+ $this->_model->checkResponse($responseParams);
+ }
+ catch (Exception $e) {
+ $this->fail('An unexpected exception has been raised.');
+ }
+ }
+
+ public function testPerformRequest()
+ {
+ $result = array('NCERROR' => 0);
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('getResponseParams'));
+ $directLinkMock->expects($this->any())
+ ->method('getResponseParams')
+ ->will($this->returnValue($result));
+ $this->assertEquals($result, $directLinkMock->performRequest(array('foo'), 'bla'));
+
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/Additional/OpenInvoiceNlTest.php b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/Additional/OpenInvoiceNlTest.php
new file mode 100644
index 0000000..9eb424c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/Additional/OpenInvoiceNlTest.php
@@ -0,0 +1,291 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+
+class Netresearch_OPS_Test_Model_Backend_Operation_Capture_Additional_OpenInvoiceNlTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $openInvoiceNlModel = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->openInvoiceNlModel = Mage::getModel('ops/backend_operation_capture_additional_openInvoiceNl');
+ $this->mockSessions();
+ }
+
+ public function testExtractAdditionalParamsWithoutShipping1()
+ {
+ $itemsContainer = Mage::getModel('sales/order_invoice');
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(1);
+ $orderItem->setQtyOrdered(2);
+ $item = Mage::getModel('sales/order_invoice_item');
+ $item->setOrderItemId(1);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+ $itemsContainer->addItem($item);
+ $payment = Mage::getModel('sales/order_payment')->setMethod('ops_openInvoiceNl');
+ $payment->setInvoice($itemsContainer);
+ $result = $this->openInvoiceNlModel->extractAdditionalParams($payment);
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(0 < count($result));
+ $this->assertArrayHasKey('ITEMID1', $result);
+ $this->assertEquals(1, $result['ITEMID1']);
+ $this->assertArrayHasKey('ITEMNAME1', $result);
+ $this->assertEquals('Item', $result['ITEMNAME1']);
+ $this->assertArrayHasKey('ITEMPRICE1', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE1']);
+ $this->assertArrayHasKey('ITEMVATCODE1', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE1']);
+ $this->assertArrayHasKey('TAXINCLUDED1', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED1']);
+ }
+
+ public function testExtractAdditionalParamsWithoutShippingButWithConfigurable()
+ {
+ $itemsContainer = Mage::getModel('sales/order_invoice');
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(1);
+ $orderItem->setQtyOrdered(2);
+ $orderItem->setProductType(Mage_Catalog_Model_Product_Type::TYPE_CONFIGURABLE);
+ $item = Mage::getModel('sales/order_invoice_item');
+ $item->setOrderItemId(1);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+ $itemsContainer->addItem($item);
+ $item = Mage::getModel('sales/order_invoice_item');
+ $simpleOrderItem = Mage::getModel('sales/order_item');
+ $simpleOrderItem->setId(1);
+ $simpleOrderItem->setQtyOrdered(2);
+ $simpleOrderItem->setParentItemId(1);
+ $simpleOrderItem->setParentItem($orderItem);
+ $item->setOrderItemId(2);
+ $item->setOrderItem($simpleOrderItem);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+ $itemsContainer->addItem($item);
+ $payment = Mage::getModel('sales/order_payment')->setMethod('ops_openInvoiceNl');
+ $payment->setInvoice($itemsContainer);
+ $result = $this->openInvoiceNlModel->extractAdditionalParams($payment);
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(0 < count($result));
+ $this->assertArrayHasKey('ITEMID1', $result);
+ $this->assertEquals(1, $result['ITEMID1']);
+ $this->assertArrayHasKey('ITEMNAME1', $result);
+ $this->assertEquals('Item', $result['ITEMNAME1']);
+ $this->assertArrayHasKey('ITEMPRICE1', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE1']);
+ $this->assertArrayHasKey('ITEMVATCODE1', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE1']);
+ $this->assertArrayHasKey('TAXINCLUDED1', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED1']);
+ }
+
+ public function testExtractAdditionalParamsWithoutShippingButWithTwoNormalInvoiceItems()
+ {
+ $itemsContainer = Mage::getModel('sales/order_invoice');
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(1);
+ $orderItem->setQtyOrdered(2);
+ $item = Mage::getModel('sales/order_invoice_item');
+ $item->setOrderItemId(1);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+ $itemsContainer->addItem($item);
+ $item = Mage::getModel('sales/order_invoice_item');
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(1);
+ $orderItem->setQtyOrdered(2);
+ $item->setOrderItemId(2);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+ $itemsContainer->addItem($item);
+ $payment = Mage::getModel('sales/order_payment')->setMethod('ops_openInvoiceNl');
+ $payment->setInvoice($itemsContainer);
+ $result = $this->openInvoiceNlModel->extractAdditionalParams($payment);
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(0 < count($result));
+ $this->assertArrayHasKey('ITEMID1', $result);
+ $this->assertEquals(1, $result['ITEMID1']);
+ $this->assertArrayHasKey('ITEMNAME1', $result);
+ $this->assertEquals('Item', $result['ITEMNAME1']);
+ $this->assertArrayHasKey('ITEMPRICE1', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE1']);
+ $this->assertArrayHasKey('ITEMVATCODE1', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE1']);
+ $this->assertArrayHasKey('TAXINCLUDED1', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED1']);
+
+ $this->assertArrayHasKey('ITEMID2', $result);
+ $this->assertEquals(1, $result['ITEMID2']);
+ $this->assertArrayHasKey('ITEMNAME2', $result);
+ $this->assertEquals('Item', $result['ITEMNAME2']);
+ $this->assertArrayHasKey('ITEMPRICE2', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE2']);
+ $this->assertArrayHasKey('ITEMVATCODE2', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE2']);
+ $this->assertArrayHasKey('TAXINCLUDED2', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED2']);
+ }
+
+ public function testExtractAdditionalParamsWithShipping()
+ {
+ $itemsContainer = Mage::getModel('sales/order_invoice');
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(1);
+ $orderItem->setQtyOrdered(2);
+ $item = Mage::getModel('sales/order_invoice_item');
+ $item->setOrderItemId(1);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+ $itemsContainer->addItem($item);
+ $itemsContainer->setBaseShippingInclTax(10.00);
+ $order = Mage::getModel('sales/order');
+ $order->setShippingDescription('foo');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_openInvoiceNl');
+ $order->setPayment($payment);
+ $itemsContainer->setOrder($order);
+ $payment->setInvoice($itemsContainer);
+ $result = $this->openInvoiceNlModel->extractAdditionalParams($payment);
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(0 < count($result));
+ $this->assertArrayHasKey('ITEMID1', $result);
+ $this->assertEquals(1, $result['ITEMID1']);
+ $this->assertArrayHasKey('ITEMNAME1', $result);
+ $this->assertEquals('Item', $result['ITEMNAME1']);
+ $this->assertArrayHasKey('ITEMPRICE1', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE1']);
+ $this->assertArrayHasKey('ITEMVATCODE1', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE1']);
+ $this->assertArrayHasKey('TAXINCLUDED1', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED1']);
+ $this->assertArrayHasKey('ITEMID2', $result);
+ $this->assertEquals('SHIPPING', $result['ITEMID2']);
+ $this->assertArrayHasKey('ITEMNAME2', $result);
+ $this->assertEquals(substr($order->getShippingDescription(), 0, 30), $result['ITEMNAME2']);
+ $this->assertArrayHasKey('ITEMPRICE2', $result);
+ $this->assertEquals(Mage::helper('ops/data')->getAmount(10.00), $result['ITEMPRICE2']);
+ $this->assertArrayHasKey('ITEMQUANT2', $result);
+ $this->assertEquals(1, $result['ITEMQUANT2']);
+ $this->assertArrayHasKey('ITEMVATCODE2', $result);
+ $this->assertEquals(floatval($payment->getMethodInstance()->getShippingTaxRate($order)).'%', $result['ITEMVATCODE2']);
+ $this->assertArrayHasKey('TAXINCLUDED2', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED2']);
+ }
+
+ public function testExtractAdditionalParamsWithShippingAndDiscount()
+ {
+ $itemsContainer = Mage::getModel('sales/order_invoice');
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(1);
+ $orderItem->setQtyOrdered(2);
+ $item = Mage::getModel('sales/order_invoice_item');
+ $item->setOrderItemId(1);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+ $itemsContainer->addItem($item);
+ $itemsContainer->setBaseShippingInclTax(10.00);
+ $itemsContainer->setBaseDiscountAmount(-10.00);
+ $order = Mage::getModel('sales/order');
+ $order->setShippingDescription('foo');
+ $order->setCouponRuleName('Foo');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_openInvoiceNl');
+ $order->setPayment($payment);
+ $itemsContainer->setOrder($order);
+ $payment->setInvoice($itemsContainer);
+ $result = $this->openInvoiceNlModel->extractAdditionalParams($payment);
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(0 < count($result));
+ $this->assertArrayHasKey('ITEMID1', $result);
+ $this->assertEquals(1, $result['ITEMID1']);
+ $this->assertArrayHasKey('ITEMNAME1', $result);
+ $this->assertEquals('Item', $result['ITEMNAME1']);
+ $this->assertArrayHasKey('ITEMPRICE1', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE1']);
+ $this->assertArrayHasKey('ITEMVATCODE1', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE1']);
+ $this->assertArrayHasKey('TAXINCLUDED1', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED1']);
+
+ $this->assertArrayHasKey('ITEMID2', $result);
+ $this->assertEquals('DISCOUNT', $result['ITEMID2']);
+ $this->assertArrayHasKey('ITEMNAME2', $result);
+ $this->assertEquals('Foo', $result['ITEMNAME2']);
+ $this->assertArrayHasKey('ITEMPRICE2', $result);
+ $this->assertEquals(Mage::helper('ops/data')->getAmount(-10.00), $result['ITEMPRICE2']);
+ $this->assertArrayHasKey('ITEMQUANT2', $result);
+ $this->assertEquals(1, $result['ITEMQUANT2']);
+ $this->assertArrayHasKey('ITEMVATCODE2', $result);
+ $this->assertEquals(floatval($payment->getMethodInstance()->getShippingTaxRate($order)).'%', $result['ITEMVATCODE2']);
+ $this->assertArrayHasKey('TAXINCLUDED2', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED2']);
+
+ $this->assertArrayHasKey('ITEMID3', $result);
+ $this->assertEquals('SHIPPING', $result['ITEMID3']);
+ $this->assertArrayHasKey('ITEMNAME3', $result);
+ $this->assertEquals(substr($order->getShippingDescription(), 0, 30), $result['ITEMNAME3']);
+ $this->assertArrayHasKey('ITEMPRICE3', $result);
+ $this->assertEquals(Mage::helper('ops/data')->getAmount(10.00), $result['ITEMPRICE3']);
+ $this->assertArrayHasKey('ITEMQUANT3', $result);
+ $this->assertEquals(1, $result['ITEMQUANT3']);
+ $this->assertArrayHasKey('ITEMVATCODE3', $result);
+ $this->assertEquals(floatval($payment->getMethodInstance()->getShippingTaxRate($order)).'%', $result['ITEMVATCODE3']);
+ $this->assertArrayHasKey('TAXINCLUDED3', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED3']);
+ }
+
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'checkout/session', $sessionMock);
+ $sessionMock = $this->getModelMockBuilder('adminhtml/session_quote')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'adminhtml/session_quote', $sessionMock);
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+
+ public function tearDown()
+ {
+ parent::tearDown();
+ $this->openInvoiceNlModel = null;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/ParameterTest.php b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/ParameterTest.php
new file mode 100644
index 0000000..e488fa7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Capture/ParameterTest.php
@@ -0,0 +1,70 @@
+
+ * @category Netresearch_OPS
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Model_Backend_Operation_Capture_ParameterTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ public function testGetRequestParams()
+ {
+ $sessionMock = $this->mockSession('customer/session');
+ $sessionMock->disableOriginalConstructor();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ $fakePayment = Mage::getModel('sales/order_payment');
+ $fakePayment->setOrder(Mage::getModel('sales/order'));
+ $fakePayment->setAdditionalInformation(array('paymentId' => '4711'));
+ $arrInfo = array('operation' => 'capture');
+ $amount = 10;
+ $opsPaymentMethod = Mage::getModel('ops/payment_abstract');
+
+ $captureParameterModel = Mage::getModel('ops/backend_operation_capture_parameter');
+ $requestParams = $captureParameterModel->getRequestParams($opsPaymentMethod, $fakePayment, $amount, $arrInfo);
+ $this->assertArrayHasKey('AMOUNT', $requestParams);
+ $this->assertArrayHasKey('PAYID', $requestParams);
+ $this->assertArrayHasKey('OPERATION', $requestParams);
+ $this->assertArrayHasKey('CURRENCY', $requestParams);
+
+ $this->assertEquals(1000, $requestParams['AMOUNT']);
+ $this->assertEquals(4711, $requestParams['PAYID']);
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_PARTIAL, $requestParams['OPERATION']);
+ $this->assertEquals(
+ Mage::app()->getStore($fakePayment->getOrder()->getStoreId())->getBaseCurrencyCode(),
+ $requestParams['CURRENCY']
+ );
+ }
+
+ public function testGetRequestParamsWithAdditionalParameters()
+ {
+ $sessionMock = $this->mockSession('customer/session');
+ $sessionMock->disableOriginalConstructor();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ $fakePayment = Mage::getModel('sales/order_payment');
+ $fakePayment->setOrder(Mage::getModel('sales/order'));
+ $fakePayment->setAdditionalInformation(array('paymentId' => '4711'));
+ $fakeInvoice = Mage::getModel('sales/order_invoice');
+ $fakePayment->setInvoice($fakeInvoice);
+ $arrInfo = array('operation' => 'capture');
+ $amount = 10;
+ $opsPaymentMethod = Mage::getModel('ops/payment_openInvoiceNl');
+ $captureParameterModel = Mage::getModel('ops/backend_operation_capture_parameter');
+ $requestParams = $captureParameterModel->getRequestParams($opsPaymentMethod, $fakePayment, $amount, $arrInfo);
+ $this->assertArrayHasKey('AMOUNT', $requestParams);
+ $this->assertArrayHasKey('PAYID', $requestParams);
+ $this->assertArrayHasKey('OPERATION', $requestParams);
+ $this->assertArrayHasKey('CURRENCY', $requestParams);
+
+ $this->assertEquals(1000, $requestParams['AMOUNT']);
+ $this->assertEquals(4711, $requestParams['PAYID']);
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_PARTIAL, $requestParams['OPERATION']);
+ $this->assertEquals(
+ Mage::app()->getStore($fakePayment->getOrder()->getStoreId())->getBaseCurrencyCode(),
+ $requestParams['CURRENCY']
+ );
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/ParameterTest.php b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/ParameterTest.php
new file mode 100644
index 0000000..75e7e1e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/ParameterTest.php
@@ -0,0 +1,52 @@
+
+ * @category Netresearch_OPS
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+class Netresearch_OPS_Test_Model_Backend_Operation_ParameterTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testGetParameterForWillThrowException()
+ {
+ $fakePayment = new Varien_Object();
+ $arrInfo = array();
+ $amount = 0;
+ $opsPaymentMethod = Mage::getModel('ops/payment_abstract');
+ Mage::getModel('ops/backend_operation_parameter')->getParameterFor(
+ 'NOT SUPPORTED OPERATION TYPE', $opsPaymentMethod, $fakePayment, $amount, $arrInfo
+ );
+ }
+
+ public function testGetParameterForCaptureWillReturnArray()
+ {
+ $fakePayment = Mage::getModel('sales/order_payment');
+ $fakePayment->setOrder(Mage::getModel('sales/order'));
+ $fakePayment->setAdditionalInformation(array('paymentId' => '4711'));
+ $arrInfo = array('operation' => Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_PARTIAL);
+ $amount = 10;
+ $opsPaymentMethod = Mage::getModel('ops/payment_abstract');
+ $requestParams = Mage::getModel('ops/backend_operation_parameter')->getParameterFor(
+ Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_TRANSACTION_TYPE,
+ $opsPaymentMethod,
+ $fakePayment,
+ $amount,
+ $arrInfo
+ );
+ $this->assertArrayHasKey('AMOUNT', $requestParams);
+ $this->assertArrayHasKey('PAYID', $requestParams);
+ $this->assertArrayHasKey('OPERATION', $requestParams);
+ $this->assertArrayHasKey('CURRENCY', $requestParams);
+
+ $this->assertEquals(1000, $requestParams['AMOUNT']);
+ $this->assertEquals(4711, $requestParams['PAYID']);
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_PARTIAL, $requestParams['OPERATION']);
+ $this->assertEquals(Mage::app()->getStore($fakePayment->getOrder()->getStoreId())->getBaseCurrencyCode(), $requestParams['CURRENCY']);
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/Additional/OpenInvoiceNlTest.php b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/Additional/OpenInvoiceNlTest.php
new file mode 100644
index 0000000..4f9f8d0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/Additional/OpenInvoiceNlTest.php
@@ -0,0 +1,248 @@
+openInvoiceNlModel = Mage::getModel('ops/backend_operation_refund_additional_openInvoiceNl');
+ $creditMemo = Mage::getModel('sales/order_creditmemo');
+ $invoice = Mage::getModel('sales/order_invoice');
+ // add first item to invoice
+
+
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(1);
+ $orderItem->setQtyOrdered(2);
+ $orderItem->setTaxPercent(19);
+
+ $item = Mage::getModel('sales/order_invoice_item');
+ $item->setOrderItemId(1);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item 1');
+ $item->setBasePriceInclTax(42.99);
+ $item->setQty(2);
+ $item->setTaxPercent(19);
+
+ $orderItem->setQtyInvoiced(2);
+ $creditMemoItem = Mage::getModel('sales/order_creditmemo_item');
+ $creditMemoItem->setOrderItemId(1);
+ $creditMemoItem->setOrderItem($orderItem);
+ $creditMemoItem->setName('Item 1');
+ $creditMemoItem->setBasePriceInclTax(42.99);
+ $creditMemoItem->setQty(2);
+
+ $creditMemo->addItem($creditMemoItem);
+ $invoice->addItem($item);
+
+ // add second item to invoice
+ $orderItem = Mage::getModel('sales/order_item');
+ $orderItem->setId(2);
+ $orderItem->setQtyOrdered(2);
+ $orderItem->setTaxPercent(7);
+
+ $item = Mage::getModel('sales/order_invoice_item');
+ $item->setOrderItemId(2);
+ $item->setOrderItem($orderItem);
+ $item->setName('Item 2');
+ $item->setBasePriceInclTax(19.99);
+ $item->setQty(2);
+ $item->setTaxPercent(7);
+
+ $orderItem->setQtyInvoiced(2);
+ $creditMemoItem = Mage::getModel('sales/order_creditmemo_item');
+ $creditMemoItem->setOrderItemId(2);
+ $creditMemoItem->setOrderItem($orderItem);
+ $creditMemoItem->setName('Item 2');
+ $creditMemoItem->setBasePriceInclTax(19.99);
+ $creditMemoItem->setQty(2);
+
+ $creditMemo->addItem($creditMemoItem);
+ $invoice->addItem($item);
+ // add shipping and discount
+ $invoice->setBaseShippingInclTax(10.00);
+ $order = Mage::getModel('sales/order');
+ $order->setShippingDescription('SuperFunShipping');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_openInvoiceNl');
+ $order->setPayment($payment);
+ $invoice->setOrder($order);
+ $payment->setInvoice($invoice);
+ $payment->setCreditmemo($creditMemo);
+ $this->testPayment = $payment;
+
+ $sessionMock = $this->getModelMockBuilder('adminhtml/session_quote')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'adminhtml/session_quote', $sessionMock);
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'checkout/session', $sessionMock);
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+ }
+
+
+ public function testExtractWithoutShippingAndAdjustments()
+ {
+ $params = array(
+
+ 'shipping_amount' => 0,
+ 'adjustment_positive' => 0,
+ 'adjustment_negative' => 0
+
+
+ );
+ $this->testPayment->getCreditmemo()->addData($params);
+ $this->mockRefundHelper($params);
+ $result = $this->openInvoiceNlModel->extractAdditionalParams($this->testPayment);
+ // refunded item
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(0 < count($result));
+ $this->assertArrayHasKey('ITEMID1', $result);
+ $this->assertEquals(1, $result['ITEMID1']);
+ $this->assertArrayHasKey('ITEMNAME1', $result);
+ $this->assertEquals('Item 1', $result['ITEMNAME1']);
+ $this->assertArrayHasKey('ITEMPRICE1', $result);
+ $this->assertEquals(4299, $result['ITEMPRICE1']);
+ $this->assertArrayHasKey('ITEMVATCODE1', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE1']);
+ $this->assertArrayHasKey('TAXINCLUDED1', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED1']);
+ $this->assertArrayHasKey('ITEMQUANT1', $result);
+ $this->assertEquals(2, $result['ITEMQUANT1']);
+ // 'ignored item'
+ $this->assertArrayHasKey('ITEMID2', $result);
+ $this->assertEquals(2, $result['ITEMID2']);
+ $this->assertArrayHasKey('ITEMNAME2', $result);
+ $this->assertEquals('Item 2', $result['ITEMNAME2']);
+ $this->assertArrayHasKey('ITEMPRICE2', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE2']);
+ $this->assertArrayHasKey('ITEMVATCODE2', $result);
+ $this->assertEquals('7%', $result['ITEMVATCODE2']);
+ $this->assertArrayHasKey('TAXINCLUDED2', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED2']);
+ $this->assertArrayHasKey('ITEMQUANT2', $result);
+ $this->assertEquals(2, $result['ITEMQUANT2']);
+ // amount
+ $this->assertArrayHasKey('AMOUNT', $result);
+ $this->assertEquals(12596, $result['AMOUNT']);
+ }
+
+
+ public function testWithShippingAndAllAdjustments()
+ {
+ $params = array(
+
+ 'base_shipping_incl_tax' => 5,
+ 'base_adjustment_positive' => 5,
+ 'base_adjustment_negative' => 10
+
+
+ );
+ $this->mockRefundHelper($params);
+ $this->testPayment->getCreditmemo()->addData($params);
+
+ $result = $this->openInvoiceNlModel->extractAdditionalParams($this->testPayment);
+ // Test our items
+ $this->assertTrue(is_array($result));
+ $this->assertTrue(0 < count($result));
+ $this->assertArrayHasKey('ITEMID1', $result);
+ $this->assertEquals(1, $result['ITEMID1']);
+ $this->assertArrayHasKey('ITEMNAME1', $result);
+ $this->assertEquals('Item 1', $result['ITEMNAME1']);
+ $this->assertArrayHasKey('ITEMPRICE1', $result);
+ $this->assertEquals(4299, $result['ITEMPRICE1']);
+ $this->assertArrayHasKey('ITEMVATCODE1', $result);
+ $this->assertEquals('19%', $result['ITEMVATCODE1']);
+ $this->assertArrayHasKey('TAXINCLUDED1', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED1']);
+ $this->assertArrayHasKey('ITEMQUANT1', $result);
+ $this->assertEquals(2, $result['ITEMQUANT1']);
+ $this->assertArrayHasKey('ITEMID2', $result);
+ $this->assertEquals(2, $result['ITEMID2']);
+ $this->assertArrayHasKey('ITEMNAME2', $result);
+ $this->assertEquals('Item 2', $result['ITEMNAME2']);
+ $this->assertArrayHasKey('ITEMPRICE2', $result);
+ $this->assertEquals(1999, $result['ITEMPRICE2']);
+ $this->assertArrayHasKey('ITEMVATCODE2', $result);
+ $this->assertEquals('7%', $result['ITEMVATCODE2']);
+ $this->assertArrayHasKey('TAXINCLUDED2', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED2']);
+ $this->assertArrayHasKey('ITEMQUANT2', $result);
+ $this->assertEquals(2, $result['ITEMQUANT2']);
+
+ // shipping
+ $this->assertArrayHasKey('ITEMID3', $result);
+ $this->assertEquals('SHIPPING', $result['ITEMID3']);
+ $this->assertArrayHasKey('ITEMNAME3', $result);
+ $this->assertEquals('SuperFunShipping', $result['ITEMNAME3']);
+ $this->assertArrayHasKey('ITEMPRICE3', $result);
+ // note, that this is the refunded amount, not the actual shipping cost of the invoice
+ $this->assertEquals(500, $result['ITEMPRICE3']);
+ $this->assertArrayHasKey('ITEMVATCODE3', $result);
+ $this->assertEquals('0%', $result['ITEMVATCODE3']);
+ $this->assertArrayHasKey('TAXINCLUDED3', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED3']);
+ $this->assertArrayHasKey('ITEMQUANT3', $result);
+ $this->assertEquals(1, $result['ITEMQUANT3']);
+ // adjustment refund
+ $this->assertArrayHasKey('ITEMID4', $result);
+ $this->assertEquals('ADJUSTREFUND', $result['ITEMID4']);
+ $this->assertArrayHasKey('ITEMNAME3', $result);
+ $this->assertEquals('Adjustment Refund', $result['ITEMNAME4']);
+ $this->assertArrayHasKey('ITEMPRICE4', $result);
+ $this->assertEquals(500, $result['ITEMPRICE4']);
+ $this->assertArrayHasKey('ITEMVATCODE4', $result);
+ $this->assertEquals('0%', $result['ITEMVATCODE4']);
+ $this->assertArrayHasKey('TAXINCLUDED4', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED4']);
+ $this->assertArrayHasKey('ITEMQUANT4', $result);
+ $this->assertEquals(1, $result['ITEMQUANT4']);
+ // adjustment fee
+ $this->assertArrayHasKey('ITEMID5', $result);
+ $this->assertEquals('ADJUSTFEE', $result['ITEMID5']);
+ $this->assertArrayHasKey('ITEMNAME5', $result);
+ $this->assertEquals('Adjustment Fee', $result['ITEMNAME5']);
+ $this->assertArrayHasKey('ITEMPRICE5', $result);
+ $this->assertEquals(-1000, $result['ITEMPRICE5']);
+ $this->assertArrayHasKey('ITEMVATCODE5', $result);
+ $this->assertEquals('0%', $result['ITEMVATCODE5']);
+ $this->assertArrayHasKey('TAXINCLUDED5', $result);
+ $this->assertEquals(1, $result['TAXINCLUDED5']);
+ $this->assertArrayHasKey('ITEMQUANT5', $result);
+ $this->assertEquals(1, $result['ITEMQUANT5']);
+ // amount: 5+5+(-10)
+ $this->assertArrayHasKey('AMOUNT', $result);
+ $this->assertEquals(12596, $result['AMOUNT']);
+ }
+
+ protected function mockRefundHelper($params)
+ {
+ $helperMock = $this->getHelperMock(
+ 'ops/order_refund', array('getCreditMemoRequestParams', 'createRefundTransaction')
+ );
+ $helperMock->expects($this->any())
+ ->method('getCreditMemoRequestParams')
+ ->will($this->returnValue($params));
+ $this->replaceByMock('helper', 'ops/order_refund', $helperMock);
+ }
+
+
+ public function tearDown()
+ {
+ parent::tearDown();
+ $this->openInvoiceNlModel = null;
+ $this->testPayment = null;
+ }
+}
+
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/ParameterTest.php b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/ParameterTest.php
new file mode 100644
index 0000000..4624e60
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Backend/Operation/Refund/ParameterTest.php
@@ -0,0 +1,91 @@
+setCreditmemo($creditMemo);
+ $fakePayment->setOrder(Mage::getModel('sales/order'));
+ $fakePayment->setAdditionalInformation(array('paymentId' => '4711'));
+ $arrInfo = array(
+ 'operation' => 'refund',
+ 'invoice_id' => 2
+ );
+ $amount = 10;
+ $opsPaymentMethod = Mage::getModel('ops/payment_abstract');
+
+ $captureParameterModel = Mage::getModel('ops/backend_operation_refund_parameter');
+ $requestParams = $captureParameterModel->getRequestParams($opsPaymentMethod, $fakePayment, $amount, $arrInfo);
+ $this->assertArrayHasKey('AMOUNT', $requestParams);
+ $this->assertArrayHasKey('PAYID', $requestParams);
+ $this->assertArrayHasKey('OPERATION', $requestParams);
+ $this->assertArrayHasKey('CURRENCY', $requestParams);
+
+ $this->assertEquals(1000, $requestParams['AMOUNT']);
+ $this->assertEquals(4711, $requestParams['PAYID']);
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL, $requestParams['OPERATION']);
+ $this->assertEquals(Mage::app()->getStore($fakePayment->getOrder()->getStoreId())->getBaseCurrencyCode(), $requestParams['CURRENCY']);
+ }
+
+ public function testGetRequestParamsWithAdditionalParameters()
+ {
+ $customerSession = $this->getModelMockBuilder('customer/session')->disableOriginalConstructor()->getMock();
+ $this->replaceByMock('model', 'customer/session', $customerSession);
+
+ $fakePayment = Mage::getModel('sales/order_payment');
+ $creditMemo = Mage::getModel('sales/order_creditmemo');
+ $creditMemo->setBaseShippingInclTax(10);
+ $fakePayment->setCreditmemo($creditMemo);
+ $fakePayment->setOrder(Mage::getModel('sales/order')->setBaseGrandTotal(100));
+ $fakePayment->setAdditionalInformation(array('paymentId' => '4711'));
+ $fakeInvoice = Mage::getModel('sales/order_invoice');
+ $fakePayment->setInvoice($fakeInvoice);
+ $arrInfo = array(
+ 'operation' => 'refund',
+ 'invoice_id' => 2
+ );
+ $opsPaymentMethod = Mage::getModel('ops/payment_openInvoiceNl');
+ $captureParameterModel = Mage::getModel('ops/backend_operation_refund_parameter');
+ $this->mockRefundHelper();
+ $requestParams = $captureParameterModel->getRequestParams($opsPaymentMethod, $fakePayment, 0, $arrInfo);
+ $this->assertArrayHasKey('AMOUNT', $requestParams);
+ $this->assertArrayHasKey('PAYID', $requestParams);
+ $this->assertArrayHasKey('OPERATION', $requestParams);
+ $this->assertArrayHasKey('CURRENCY', $requestParams);
+
+ $this->assertEquals(1000, $requestParams['AMOUNT']);
+ $this->assertEquals(4711, $requestParams['PAYID']);
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL, $requestParams['OPERATION']);
+ $this->assertEquals(Mage::app()->getStore($fakePayment->getOrder()->getStoreId())->getBaseCurrencyCode(), $requestParams['CURRENCY']);
+ }
+
+ protected function mockRefundHelper()
+ {
+ $helperMock = $this->getHelperMock('ops/order_refund', array('getCreditMemoRequestParams', 'createRefundTransaction'));
+ $params = array(
+ 'creditmemo' => array(
+ 'items' => array(
+ 1 => array(
+ 'qty' => 0
+ ),
+ 2 => array(
+ 'qty' => 0
+ )
+ ),
+ 'shipping_amount' => 0,
+ 'adjustment_positive' => 10,
+ 'adjustment_negative' => 0
+
+ )
+ );
+ $helperMock->expects($this->any())
+ ->method('getCreditMemoRequestParams')
+ ->will($this->returnValue($params));
+ $this->replaceByMock('helper', 'ops/order_refund', $helperMock);
+ }
+
+}
+
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/ConfigTest.php b/app/code/community/Netresearch/OPS/Test/Model/ConfigTest.php
new file mode 100644
index 0000000..77dae8c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/ConfigTest.php
@@ -0,0 +1,611 @@
+_model = Mage::getModel('ops/config');
+ }
+
+
+ public function testType()
+ {
+ $this->assertInstanceOf('Netresearch_OPS_Model_Config', $this->_model);
+ }
+
+ public function testGetIntersolveBrands()
+ {
+ $path = 'payment/ops_interSolve/brands';
+
+
+ Mage::getConfig()->saveConfig($path, serialize(array()));
+ Mage::getConfig()->cleanCache();
+ $this->assertTrue(is_array($this->_model->getIntersolveBrands(null)));
+
+ $this->assertEquals(
+ sizeof(unserialize(Mage::getStoreConfig('payment/ops_interSolve/brands', 0))),
+ sizeof($this->_model->getIntersolveBrands(0))
+ );
+
+
+ $newVouchers = array(
+ array('brand' => '1234', 'value' => '1234'),
+ array('brand' => '5678', 'value' => '5678'),
+ array('brand' => '9012', 'value' => '9012'),
+ );
+
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->setConfig($path, serialize($newVouchers));
+ $this->assertEquals(
+ sizeof($newVouchers),
+ sizeof($this->_model->getIntersolveBrands(null))
+ );
+ }
+
+ public function testGetInlinePaymentCcTypes()
+ {
+ $sourceModel = Mage::getModel(
+ 'ops/source_cc_aliasInterfaceEnabledTypes'
+ );
+
+ $pathRedirectAll = 'payment/ops_cc/redirect_all';
+ $pathSpecific = 'payment/ops_cc/inline_types';
+ $store = Mage::app()->getStore(0)->load(0);
+
+ $store->resetConfig();
+ $store->setConfig($pathRedirectAll, 0);
+ $store->setConfig($pathSpecific, 'MasterCard,VISA');
+ $this->assertEquals(
+ array('MasterCard', 'VISA'),
+ $this->_model->getInlinePaymentCcTypes('ops_cc')
+ );
+
+ $store->resetConfig();
+ $store->setConfig($pathRedirectAll, 1);
+ $store->setConfig($pathSpecific, 'MasterCard,VISA');
+ $this->assertEquals(array(), $this->_model->getInlinePaymentCcTypes('ops_cc'));
+
+ $store->resetConfig();
+ }
+
+ public function testGetGenerateHashUrl()
+ {
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with(
+ 'ops/alias/generatehash',
+ array('_secure' => false, '_nosid' => true)
+ );
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getGenerateHashUrl();
+
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with(
+ 'ops/alias/generatehash',
+ array('_secure' => false, '_nosid' => true, '_store' => 1)
+ );
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getGenerateHashUrl(1);
+ }
+
+ public function testGetAliasAcceptUrl()
+ {
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with(
+ 'ops/alias/accept',
+ array('_secure' => false, '_nosid' => true)
+ );
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getAliasAcceptUrl();
+
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with(
+ 'ops/alias/accept',
+ array('_secure' => false, '_nosid' => true, '_store' => 1)
+ );
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getAliasAcceptUrl(1);
+ }
+
+ public function testGetAliasExceptionUrl()
+ {
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with(
+ 'ops/alias/exception',
+ array('_secure' => false, '_nosid' => true)
+ );
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getAliasExceptionUrl();
+
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with(
+ 'ops/alias/exception',
+ array('_secure' => false, '_nosid' => true, '_store' => 1)
+ );
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getAliasExceptionUrl(1);
+ }
+
+ public function testGetCcSaveAliasUrl()
+ {
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with('ops/alias/save', array('_secure' => false));
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getCcSaveAliasUrl();
+
+ $urlModel = $this->getModelMock('core/url', array('getUrl'));
+ $urlModel->expects($this->any())
+ ->method('getUrl')
+ ->with(
+ 'ops/alias/save',
+ array('_secure' => false, '_store' => 1)
+ );
+ $this->replaceByMock('model', 'core/url', $urlModel);
+ $this->_model->getCcSaveAliasUrl(1);
+ }
+
+ public function testIsAliasInfoBlockEnabled()
+ {
+ $path = 'payment/ops_cc/show_alias_manager_info_for_guests';
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig($path, 0);
+ $this->assertFalse($this->_model->isAliasInfoBlockEnabled());
+
+ $store->resetConfig();
+ $store->setConfig($path, 1);
+ $this->assertTrue($this->_model->isAliasInfoBlockEnabled());
+ }
+
+
+ public function testObserveCreditMemoCreation()
+ {
+ $this->assertEventObserverDefined(
+ 'adminhtml',
+ 'core_block_abstract_to_html_after',
+ 'ops/observer',
+ 'showWarningForClosedTransactions'
+ );
+ }
+
+ public function testAppendCheckboxToRefundForm()
+ {
+ $this->assertEventObserverDefined(
+ 'adminhtml',
+ 'core_block_abstract_to_html_after',
+ 'ops/observer',
+ 'appendCheckBoxToRefundForm'
+ );
+ }
+
+ public function testGetOrderReference()
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID,
+ $this->_model->getOrderReference()
+ );
+
+ $store->setConfig(
+ 'payment_services/ops/redirectOrderReference',
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID,
+ $this->_model->getOrderReference()
+ );
+ }
+
+ public function testGetShowQuoteIdInOrderGrid()
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $this->assertEquals(1, $this->_model->getShowQuoteIdInOrderGrid());
+
+ $store->setConfig('payment_services/ops/showQuoteIdInOrderGrid', 0);
+ $this->assertEquals(0, $this->_model->getShowQuoteIdInOrderGrid());
+ }
+
+ public function testIsAliasManagerEnabled()
+ {
+ $path = 'payment/ops_cc/active_alias';
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig($path, 0);
+ $this->assertFalse($this->_model->isAliasManagerEnabled('ops_cc'));
+
+ $store->resetConfig();
+ $store->setConfig($path, 1);
+ $this->assertTrue($this->_model->isAliasManagerEnabled('ops_cc'));
+
+ }
+
+
+ public function getAliasUsageForNewAlias()
+ {
+ $path = 'payment/ops_cc/alias_usage_for_new_alias';
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig($path, 'my text goes here');
+
+ $this->assertEquals('my text goes here', $this->_model->getAliasUsageForNewAlias('ops_cc', 0));
+
+ $store->resetConfig();
+ $store->setConfig($path, 'my text goes here two');
+ $this->assertNotEquals('my text goes here', $this->_model->getAliasUsageForNewAlias('ops_cc', 0));
+ }
+
+
+ public function getAliasUsageForExistingAlias()
+ {
+ $path = 'payment/ops_cc/alias_usage_for_existing_alias';
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig($path, 'my text goes here');
+
+ $this->assertEquals('my text goes here', $this->_model->getAliasUsageForNewAlias('ops_cc', 0));
+
+ $store->resetConfig();
+ $store->setConfig($path, 'my text goes here two');
+ $this->assertNotEquals('my text goes here', $this->_model->getAliasUsageForNewAlias('ops_cc', 0));
+ }
+
+ public function testGetAcceptRedirectLocation()
+ {
+ $this->assertEquals(
+ Netresearch_OPS_Model_Config::OPS_CONTROLLER_ROUTE_PAYMENT
+ . 'accept',
+ $this->_model->getAcceptRedirectRoute()
+ );
+ }
+
+ public function testGetCancelRedirectLocation()
+ {
+ $this->assertEquals(
+ Netresearch_OPS_Model_Config::OPS_CONTROLLER_ROUTE_PAYMENT
+ . 'cancel',
+ $this->_model->getCancelRedirectRoute()
+ );
+ }
+
+ public function testGetDeclineRedirectLocation()
+ {
+ $this->assertEquals(
+ Netresearch_OPS_Model_Config::OPS_CONTROLLER_ROUTE_PAYMENT
+ . 'decline',
+ $this->_model->getDeclineRedirectRoute()
+ );
+ }
+
+ public function testGetExceptionRedirectLocation()
+ {
+ $this->assertEquals(
+ Netresearch_OPS_Model_Config::OPS_CONTROLLER_ROUTE_PAYMENT
+ . 'exception',
+ $this->_model->getExceptionRedirectRoute()
+ );
+ }
+
+ /**
+ * asserts that the event for clearing old data for the payment methods is set up properly
+ */
+ public function testClearMethodBeforeImportEventExists()
+ {
+ $this->assertEventObserverDefined(
+ 'global',
+ 'sales_quote_payment_import_data_before',
+ 'ops/observer',
+ 'clearPaymentMethodFromQuote'
+ );
+ }
+
+
+ /**
+ * asserts that the event for clearing old data for the payment methods is set up properly
+ */
+ public function testSalesOrderPaymentCapture()
+ {
+ $this->assertEventObserverDefined(
+ 'adminhtml',
+ 'sales_order_payment_capture',
+ 'ops/observer',
+ 'salesOrderPaymentCapture'
+ );
+ }
+
+ public function testGetMethodsRequiringAdditionalParametersFor()
+ {
+ $capturePms = Mage::getModel('ops/config')->getMethodsRequiringAdditionalParametersFor('capture');
+ $this->assertTrue(is_array($capturePms));
+ $this->assertTrue(0 < count($capturePms));
+ $this->assertTrue(array_key_exists('OpenInvoiceNl', $capturePms));
+ $this->assertTrue(array_key_exists('OpenInvoiceNl', $capturePms));
+ $this->assertEquals('Netresearch_OPS_Model_Payment_OpenInvoiceNl', $capturePms['OpenInvoiceNl']);
+ }
+
+ public function testDisableCaptureForZeroAmountInvoiceEventExists()
+ {
+ $this->assertEventObserverDefined(
+ 'adminhtml',
+ 'core_block_abstract_prepare_layout_before',
+ 'ops/observer',
+ 'disableCaptureForZeroAmountInvoice'
+ );
+ }
+
+ public function testGetIdealIssuers()
+ {
+ $issuers = $this->_model->getIDealIssuers();
+ $this->assertTrue(is_array($issuers));
+ $this->assertTrue(array_key_exists('ABNANL2A', $issuers));
+ $this->assertEquals('ABN AMRO', $issuers['ABNANL2A']);
+
+ $this->assertTrue(array_key_exists('RABONL2U', $issuers));
+ $this->assertEquals('Rabobank', $issuers['RABONL2U']);
+
+ $this->assertTrue(array_key_exists('INGBNL2A', $issuers));
+ $this->assertEquals('ING', $issuers['INGBNL2A']);
+
+ $this->assertTrue(array_key_exists('SNSBNL2A', $issuers));
+ $this->assertEquals('SNS Bank', $issuers['SNSBNL2A']);
+
+ $this->assertTrue(array_key_exists('RBRBNL21', $issuers));
+ $this->assertEquals('Regio Bank', $issuers['RBRBNL21']);
+
+ $this->assertTrue(array_key_exists('ASNBNL21', $issuers));
+ $this->assertEquals('ASN Bank', $issuers['ASNBNL21']);
+
+ $this->assertTrue(array_key_exists('TRIONL2U', $issuers));
+ $this->assertEquals('Triodos Bank', $issuers['TRIONL2U']);
+
+ $this->assertTrue(array_key_exists('FVLBNL22', $issuers));
+ $this->assertEquals('Van Lanschot Bankiers', $issuers['FVLBNL22']);
+
+ $this->assertTrue(array_key_exists('KNABNL2H', $issuers));
+ $this->assertEquals('Knab Bank', $issuers['KNABNL2H']);
+ }
+
+ public function testAddCcPaymentMethodEventExists()
+ {
+ $this->assertEventObserverDefined(
+ 'global',
+ 'core_block_abstract_prepare_layout_before',
+ 'ops/observer',
+ 'addCcPaymentMethod'
+ );
+ }
+
+
+ public function testCanSubmitExtraParameters()
+ {
+ $this->assertTrue($this->_model->canSubmitExtraParameter());
+ $path = 'payment_services/ops/submitExtraParameters';
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig($path, 0);
+ $this->assertFalse($this->_model->isAliasManagerEnabled('ops_cc'));
+ }
+
+
+ public function testGetParameterLengths()
+ {
+ $fieldLengths = $this->_model->getParameterLengths();
+ $this->assertEquals($this->validFieldLengths(), $fieldLengths);
+ }
+
+
+ protected function validFieldLengths()
+ {
+ return array(
+ 'ECOM_SHIPTO_POSTAL_NAME_FIRST' => 50,
+ 'ECOM_SHIPTO_POSTAL_NAME_LAST' => 50,
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1' => 35,
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE2' => 35,
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE3' => 35,
+ 'ECOM_SHIPTO_POSTAL_COUNTRYCODE' => 2,
+ 'ECOM_SHIPTO_POSTAL_COUNTY' => 25,
+ 'ECOM_SHIPTO_POSTAL_POSTALCODE' => 10,
+ 'ECOM_SHIPTO_POSTAL_CITY' => 25,
+ 'ECOM_SHIPTO_POSTAL_STREET_NUMBER' => 10,
+ 'CN' => 35,
+ 'OWNERZIP' => 10,
+ 'OWNERCTY' => 2,
+ 'OWNERTOWN' => 40,
+ 'OWNERTELNO' => 30,
+ 'OWNERADDRESS' => 35,
+ 'ECOM_BILLTO_POSTAL_POSTALCODE' => 10,
+ 'ECOM_BILLTO_POSTAL_NAME_FIRST' => 50,
+ 'ECOM_BILLTO_POSTAL_NAME_LAST' => 50,
+ 'ECOM_SHIPTO_POSTAL_STATE' => 35
+ );
+
+ }
+
+ public function testGetInlineOrderReference()
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID,
+ $this->_model->getInlineOrderReference()
+ );
+
+ $store->setConfig(
+ 'payment_services/ops/inlineOrderReference',
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID
+ );
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID,
+ $this->_model->getInlineOrderReference()
+ );
+ }
+
+ public function testSetOrderStateDirectLinkExists()
+ {
+ $this->assertEventObserverDefined(
+ 'global',
+ 'sales_order_payment_place_end',
+ 'ops/observer',
+ 'setOrderStateDirectLink'
+ );
+ }
+
+ public function testGetFrontendGatewayPath()
+ {
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ $expectedResult = Mage::getStoreConfig('payment_services/ops/frontend_gateway');
+ $this->assertEquals($expectedResult, $this->_model->getFrontendGatewayPath(0));
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::TEST);
+ $this->assertContains('test', $this->_model->getFrontendGatewayPath(0));
+ }
+
+ public function testGetDirectLinkGatewayPath()
+ {
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ $expectedResult = Mage::getStoreConfig('payment_services/ops/directlink_gateway');
+ $this->assertEquals($expectedResult, $this->_model->getDirectLinkGatewayPath(0));
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::TEST);
+ $this->assertContains('test', $this->_model->getDirectLinkGatewayPath(0));
+ }
+
+ public function testGetDirectLinkGatewayOrderPath()
+ {
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ $expectedResult = Mage::getStoreConfig('payment_services/ops/directlink_gateway_order');
+ $this->assertEquals($expectedResult, $this->_model->getDirectLinkGatewayOrderPath(0));
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::TEST);
+ $this->assertContains('test', $this->_model->getDirectLinkGatewayOrderPath(0));
+ }
+
+ public function testGetAliasGatewayUrl()
+ {
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ $expectedResult = Mage::getStoreConfig('payment_services/ops/ops_alias_gateway');
+ $this->assertEquals($expectedResult, $this->_model->getAliasGatewayUrl(0));
+
+ // test with standard alias gateway
+ Mage::app()->getStore(0)->setConfig(
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'ops_alias_gateway_test', ''
+ );
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::TEST);
+ $this->assertContains('ncol/test', $this->_model->getAliasGatewayUrl(0));
+
+ Mage::app()->getStore(0)->setConfig(
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'ops_alias_gateway_test', 'abc'
+ );
+ $this->assertEquals('abc', $this->_model->getAliasGatewayUrl(0));
+
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::PROD);
+ $this->assertNotContains('ncol/prod', $this->_model->getAliasGatewayUrl(0));
+ }
+
+ public function testGetDirectLinkMaintenanceApiPath()
+ {
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ $expectedResult = Mage::getStoreConfig('payment_services/ops/directlink_maintenance_api');
+ $this->assertEquals($expectedResult, $this->_model->getDirectLinkMaintenanceApiPath(0));
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::TEST);
+ $this->assertContains('test', $this->_model->getDirectLinkMaintenanceApiPath(0));
+ }
+
+ public function testGetMode()
+ {
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ $this->assertEquals($this->_model->getMode(0), Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ }
+
+ protected function setMode($mode, $storeId = 0)
+ {
+ Mage::app()->getStore($storeId)->setConfig(Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'mode', $mode);
+ }
+
+ public function testGetResendPaymentInfoTemplate()
+ {
+ $config = Mage::getModel('ops/config');
+ $this->assertEquals($config->getResendPaymentInfoTemplate(), 'payment_services_ops_resendPaymentInfo_template');
+ }
+
+
+ public function testGetPayPerMailTemplate()
+ {
+ $config = Mage::getModel('ops/config');
+ $this->assertEquals($config->getPayPerMailTemplate(), 'payment_services_ops_payPerMail_template');
+ }
+
+
+ public function testGetResendPaymentInfoIdentity()
+ {
+ $config = Mage::getModel('ops/config');
+ $this->assertEquals($config->getResendPaymentInfoIdentity(), 'sales');
+ }
+
+ public function testGetOpsBaseUrl()
+ {
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::TEST);
+ $this->assertEquals('https://secure.domain.tld/ncol/test', $this->_model->getOpsBaseUrl(0));
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::PROD);
+ $this->assertEquals('https://secure.domain.tld/ncol/prod', $this->_model->getOpsBaseUrl(0));
+ $this->setMode(Netresearch_OPS_Model_Source_Mode::CUSTOM);
+ $this->assertEmpty($this->_model->getOpsBaseUrl(0));
+ }
+
+ public function testGetAllRecurringCcTypes()
+ {
+ /** @var Netresearch_OPS_Model_Config $config */
+ $config = Mage::getModel('ops/config');
+ $ccTypes = $config->getAllRecurringCcTypes();
+ $this->assertEquals(
+ $ccTypes, array('American Express', 'Diners Club', 'MaestroUK', 'MasterCard', 'VISA', 'JCB')
+ );
+ }
+
+ public function testGetAcceptedRecurringCcTypes()
+ {
+ /** @var Netresearch_OPS_Model_Config $config */
+ $config = Mage::getModel('ops/config');
+ $ccTypes = $config->getAcceptedRecurringCcTypes();
+ $this->assertEquals(
+ $ccTypes, array('American Express', 'Diners Club', 'MaestroUK', 'MasterCard', 'VISA', 'JCB')
+ );
+ }
+
+ public function testGetDeviceFingerPrinting()
+ {
+ $config = Mage::getModel('ops/config');
+ // default false
+ $this->assertFalse($config->getDeviceFingerPrinting(0));
+ Mage::app()->getStore(0)->setConfig(
+ Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'device_fingerprinting', 1
+ );
+ $this->assertTrue($config->getDeviceFingerPrinting(0));
+ }
+
+ public function testGetTransActionTimeout()
+ {
+ $config = Mage::getModel('ops/config');
+ // default false
+ Mage::app()->getStore(0)->setConfig(Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'ops_rtimeout', 0);
+ $this->assertEquals(0, $config->getTransActionTimeout(0));
+ Mage::app()->getStore(0)->setConfig(Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'ops_rtimeout', 45);
+ $this->assertEquals(45, $config->getTransActionTimeout(0));
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/File/Download.php b/app/code/community/Netresearch/OPS/Test/Model/File/Download.php
new file mode 100644
index 0000000..a6e1afa
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/File/Download.php
@@ -0,0 +1,37 @@
+testFile = Mage::helper('ops/data')->getLogPath();
+ if(!file_exists($this->testFile)){
+ $file = fopen($this->testFile, 'c');
+ fclose($file);
+ }
+
+ }
+ /**
+ * @expectedException Exception
+ */
+ public function testFailingGetFile()
+ {
+ $model = Mage::getModel('ops/file_download');
+ $path = 'abc';
+ $model->getFile($path);
+ }
+
+ public function testSuccessGetFile()
+ {
+ $model = Mage::getModel('ops/file_download');
+ if(filesize($this->testFile) > $model::ONE_MEGABYTE){
+ $this->assertEquals(0, strpos(basename($model->getFile($this->testFile)), 'tempFile'));
+ }else{
+ $this->assertEquals($model->getFile($this->testFile), $this->testFile);
+ }
+
+ }
+
+}
+
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest.php b/app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest.php
new file mode 100644
index 0000000..a30514a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest.php
@@ -0,0 +1,28 @@
+assertEquals(
+ 10,
+ Mage::getModel('ops/kwixo_category_mapping')->loadByCategoryId(10)
+ ->getKwixoCategoryId()
+ );
+ $this->assertEquals(
+ 1,
+ Mage::getModel('ops/kwixo_category_mapping')->loadByCategoryId(11)
+ ->getKwixoCategoryId()
+ );
+ $this->assertEquals(
+ null,
+ Mage::getModel('ops/kwixo_category_mapping')->loadByCategoryId(12)
+ ->getKwixoCategoryId()
+ );
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest/fixtures/category_mapping.yaml b/app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest/fixtures/category_mapping.yaml
new file mode 100644
index 0000000..e18a796
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Kwixo/Category/MappingTest/fixtures/category_mapping.yaml
@@ -0,0 +1,11 @@
+tables:
+ ops/kwixo_category_mapping:
+ - id: 1
+ kwixo_category_id: 10
+ category_id: 10
+ - id: 2
+ kwixo_category_id: 1
+ category_id: 11
+ - id: 3
+ kwixo_category_id: 2
+ category_id: 11
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Mysql4/Alias/AliasTest.php b/app/code/community/Netresearch/OPS/Test/Model/Mysql4/Alias/AliasTest.php
new file mode 100644
index 0000000..51b888b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Mysql4/Alias/AliasTest.php
@@ -0,0 +1,9 @@
+assertTypeOf('Netresearch_OPS_Model_Mysql4_Alias_Collection', Mage::getModel('ops/mysql4_alias')->getCollection());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Mysql4/AliasTest.php b/app/code/community/Netresearch/OPS/Test/Model/Mysql4/AliasTest.php
new file mode 100644
index 0000000..eb97365
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Mysql4/AliasTest.php
@@ -0,0 +1,11 @@
+assertInstanceOf(
+ 'Netresearch_OPS_Model_Mysql4_Alias',
+ Mage::getModel('ops/mysql4_alias')
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/ObserverTest.php b/app/code/community/Netresearch/OPS/Test/Model/ObserverTest.php
new file mode 100644
index 0000000..67697b8
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/ObserverTest.php
@@ -0,0 +1,1111 @@
+_model = Mage::getModel('ops/observer');
+ }
+
+ public function testType()
+ {
+ $this->assertInstanceOf('Netresearch_OPS_Model_Observer', $this->_model);
+ }
+
+ public function testPerformDirectLinkRequestWithUnknownResponse()
+ {
+ $quote = $this->getModelMock('sales/quote', array('save'));
+ $aliasHelperMock = $this->getHelperMock('ops/alias', array('setAliasActive'));
+ $this->replaceByMock('helper', 'ops/alias', $aliasHelperMock);
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->expects($this->any())
+ ->method('save')
+ ->will($this->returnValue(null));
+ $this->replaceByMock('model', 'sales/quote_payment', $payment);
+ $quote->setPayment($payment);
+ $response = null;
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkMock->expects($this->any())
+ ->method('performRequest')
+ ->will($this->returnValue($response));
+ $this->replaceByMock('model', 'ops/api_directlink', $directLinkMock);
+ $observer = Mage::getModel('ops/observer');
+ $observer->performDirectLinkRequest($quote, array());
+ $this->assertFalse($this->setExpectedException('PHPUnit_Framework_ExpectationFailedException'));
+ $this->assertTrue(array_key_exists('ops_response', $quote->getPayment()->getAdditionalInformation()));
+ }
+
+ public function testPerformDirectLinkRequestWithInvalidResponse()
+ {
+ $quote = new Varien_Object();
+ $aliasHelperMock = $this->getHelperMock('ops/alias', array('setAliasActive'));
+ $this->replaceByMock('helper', 'ops/alias', $aliasHelperMock);
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->expects($this->any())
+ ->method('save')
+ ->will($this->returnValue(null));
+ $this->replaceByMock('model', 'sales/quote_payment', $payment);
+ $quote->setPayment($payment);
+ $response = '';
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkMock->expects($this->any())
+ ->method('performRequest')
+ ->will($this->returnValue($response));
+ $this->replaceByMock('model', 'ops/api_directlink', $directLinkMock);
+ $observer = Mage::getModel('ops/observer');
+ $this->assertTrue($this->setExpectedException('PHPUnit_Framework_ExpectationFailedException'));
+ $observer->performDirectLinkRequest($quote, array());
+ $this->assertFalse(array_key_exists('ops_response', $quote->getPayment()->getAdditionalInformation()));
+ }
+
+ public function testPerformDirectLinkRequestWithValidResponse()
+ {
+ $quote = new Varien_Object();
+ $aliasHelperMock = $this->getHelperMock('ops/alias', array('setAliasActive'));
+ $this->replaceByMock('helper', 'ops/alias', $aliasHelperMock);
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->expects($this->any())
+ ->method('save')
+ ->will($this->returnValue(null));
+ $this->replaceByMock('model', 'sales/quote_payment', $payment);
+ $quote->setPayment($payment);
+ $response = array('STATUS' => Netresearch_OPS_Model_Status::AUTHORIZED);
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkMock->expects($this->any())
+ ->method('performRequest')
+ ->will($this->returnValue($response));
+ $this->replaceByMock('model', 'ops/api_directlink', $directLinkMock);
+ $observer = Mage::getModel('ops/observer');
+ $this->assertFalse($this->setExpectedException('PHPUnit_Framework_ExpectationFailedException'));
+ $observer->performDirectLinkRequest($quote, array());
+ $this->assertTrue(array_key_exists('ops_response', $quote->getPayment()->getAdditionalInformation()));
+ }
+
+ public function testPerformDirectLinkRequestWithValidResponseButInvalidStatus()
+ {
+ $quote = new Varien_Object();
+ $aliasHelperMock = $this->getHelperMock('ops/alias', array('setAliasActive'));
+ $this->replaceByMock('helper', 'ops/alias', $aliasHelperMock);
+ $payment = $this->getModelMock('sales/quote_payment', array('save'));
+ $payment->expects($this->any())
+ ->method('save')
+ ->will($this->returnValue(null));
+ $this->replaceByMock('model', 'sales/quote_payment', $payment);
+ $quote->setPayment($payment);
+ $response = array('STATUS' => Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED);
+ $directLinkMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkMock->expects($this->any())
+ ->method('performRequest')
+ ->will($this->returnValue($response));
+ $this->replaceByMock('model', 'ops/api_directlink', $directLinkMock);
+ $observer = Mage::getModel('ops/observer');
+ $this->assertTrue($this->setExpectedException('PHPUnit_Framework_ExpectationFailedException'));
+ $observer->performDirectLinkRequest($quote, array());
+ $this->assertFalse(array_key_exists('ops_response', $quote->getPayment()->getAdditionalInformation()));
+ }
+
+ public function testShowWarningForClosedTransactions()
+ {
+ Mage::register('current_creditmemo', null);
+ $transport = new Varien_Object();
+ $transport->setHtml('Foo');
+ $observer = Mage::getModel('ops/observer');
+ $event = new Varien_Object();
+ $event->setBlock('');
+ $this->assertEquals('', $observer->showWarningForClosedTransactions($event));
+
+ $order = new Varien_Object();
+ $payment = new Varien_Object();
+ $methodInstance = Mage::getModel('ops/payment_cc');
+ $payment->setMethodInstance($methodInstance);
+ $order->setPayment($payment);
+ $invoice = new Varien_Object();
+ $invoice->setTransactionId(1);
+ $creditMemo = $this->getModelMock(
+ 'sales/order_creditmemo',
+ array('getOrder', 'getInvoice', 'canRefund', 'getOrderId')
+ );
+ $creditMemo->expects($this->any())
+ ->method('getOrder')
+ ->will($this->returnValue($order));
+ $creditMemo->expects($this->any())
+ ->method('getInvoice')
+ ->will($this->returnValue($invoice));
+ $creditMemo->expects($this->any())
+ ->method('canRefund')
+ ->will($this->returnValue(false));
+ $creditMemo->expects($this->any())
+ ->method('getOrderId')
+ ->will($this->returnValue(1));
+ Mage::register('current_creditmemo', $creditMemo);
+ $block = Mage::app()->getLayout()->getBlockSingleton('adminhtml/sales_order_creditmemo_create');
+
+ $blockMock = $this->getBlockMock(
+ 'ops/adminhtml_sales_order_creditmemo_closedTransaction_warning',
+ array('renderView')
+ );
+ $blockMock->expects($this->once())
+ ->method('renderView')
+ ->will($this->returnValue('warning '));
+ $this->replaceByMock('block', 'ops/adminhtml_sales_order_creditmemo_closedTransaction_warning', $blockMock);
+ $event->setBlock($block);
+ $event->setTransport($transport);
+ $html = $observer->showWarningForClosedTransactions($event);
+ $this->assertEquals('warning Foo', $html);
+ $this->assertNotEquals('Barwarning ', $html);
+
+ Mage::unregister('current_creditmemo');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testConfirmAliasPayment()
+ {
+ $quote = Mage::getModel('sales/quote')->load(23);
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment = $quote->getPayment();
+// $payment->expects($this->any())
+// ->method('getMethodInstance')
+// ->will($this->returnValue(Mage::getModel('ops/payment_cc')));
+ $payment->setAdditionalInformation(array('cvc' => '123', 'alias' => '99'));
+ $payment->setMethod('ops_cc');
+ $quote->setPayment($payment);
+ $requestParams = $this->getRequestParamsWithAlias($quote, $order);
+
+ $helperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $helperMock->expects($this->any())
+ ->method('isAdminSession')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+
+ $quoteHelperMock = $this->getHelperMock('ops/quote', array('getQuoteCurrency'));
+ $quoteHelperMock->expects($this->any())
+ ->method('getQuoteCurrency')
+ ->will($this->returnValue('USD'));
+ $this->replaceByMock('helper', 'ops/quote', $quoteHelperMock);
+
+ $observerMock = $this->getModelMock(
+ 'ops/observer',
+ array('performDirectLinkRequest', 'invokeRequestParamValidation')
+ );
+ $observerMock->expects($this->any())
+ ->method('performDirectLinkRequest')
+ ->will($this->returnValue('WuselDusel'));
+
+ $orderHelperMock = $this->getHelperMock('ops/order', array('checkIfAddressesAreSame'));
+ $orderHelperMock->expects($this->any())
+ ->method('checkIfAddressesAreSame')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('helper', 'ops/order', $orderHelperMock);
+
+ $customerSessionMock = $this->getModelMock('customer/session', array('isLoggedIn'));
+ $customerSessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $customerSessionMock);
+
+ $configModelMock = $this->getModelMock(
+ 'ops/config', array(
+ 'get3dSecureIsActive',
+ 'getAcceptUrl',
+ 'getDeclineUrl',
+ 'getExceptionUrl'
+ )
+ );
+
+ $configModelMock->expects($this->any())
+ ->method('get3dSecureIsActive')
+ ->will($this->returnValue(true));
+ $configModelMock->expects($this->any())
+ ->method('getAcceptUrl')
+ ->will($this->returnValue('www.abc.com'));
+ $configModelMock->expects($this->any())
+ ->method('getDeclineUrl')
+ ->will($this->returnValue('www.abcd.com'));
+ $configModelMock->expects($this->any())
+ ->method('getExceptionUrl')
+ ->will($this->returnValue('www.abcde.com'));
+ $this->replaceByMock('model', 'ops/config', $configModelMock);
+
+ $aliashelperMock = $this->getHelperMock('ops/alias', array('getAlias', 'cleanUpAdditionalInformation'));
+ $aliashelperMock->expects($this->any())
+ ->method('getAlias')
+ ->with($quote)
+ ->will($this->returnValue('99'));
+ $this->replaceByMock('helper', 'ops/alias', $aliashelperMock);
+ $this->assertEquals('WuselDusel', $observerMock->confirmAliasPayment($order, $quote));
+
+ $helperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $helperMock->expects($this->any())
+ ->method('isAdminSession')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+
+ $observerMock = $this->getModelMock(
+ 'ops/observer',
+ array('performDirectLinkRequest', 'invokeRequestParamValidation')
+ );
+
+ $requestParams = $this->getRequestParamsWithoutAlias($quote, $order);
+ $observerMock->expects($this->any())
+ ->method('performDirectLinkRequest')
+ ->will($this->returnValue('wrong'));
+ $this->assertEquals('wrong', $observerMock->confirmAliasPayment($order, $quote));
+
+
+ $observerMock = $this->getModelMock('ops/observer', array('performDirectLinkRequest'));
+ $validatorMock = $this->getModelMock('ops/validator_parameter_validator', array('isValid'));
+ $validatorMock->expects($this->once())
+ ->method('isValid')
+ ->will($this->returnValue(false));
+ $validatorFactoryMock = $this->getModelMock('ops/validator_parameter_factory', array('getValidatorFor'));
+ $validatorFactoryMock->expects($this->once())
+ ->method('getValidatorFor')
+ ->will($this->returnValue($validatorMock));
+ $this->replaceByMock('model', 'ops/validator_parameter_factory', $validatorFactoryMock);
+ try {
+ $observerMock->confirmAliasPayment($order, $quote);
+ } catch (Exception $e) {
+ $this->assertTrue($e instanceof Mage_Core_Exception);
+ }
+ }
+
+
+ private function getRequestParamsWithAlias($quote, $order)
+ {
+ return array(
+ 'ALIAS' => '99',
+ 'AMOUNT' => 0.0,
+ 'CURRENCY' => 'USD',
+ 'OPERATION' => 'RES',
+ 'ORDERID' => Mage::getSingleton('ops/config')->getConfigData('devprefix')
+ . $order->getQuoteId(),
+ 'EMAIL' => 'hubertus.von.fuerstenberg@trash-mail.com',
+ 'OWNERADDRESS' => utf8_decode('An der Tabaksmühle 3a'),
+ 'OWNERZIP' => '04229',
+ 'OWNERTELNO' => null,
+ 'OWNERCTY' => 'DE',
+ 'ADDMATCH' => 1,
+
+ 'RTIMEOUT' => 45,
+ 'CREDITDEBIT' => 'C',
+ 'ECOM_SHIPTO_POSTAL_POSTALCODE' => '04229',
+ 'ECOM_BILLTO_POSTAL_POSTALCODE' => '04229',
+ 'CVC' => '123',
+ 'REMOTE_ADDR' => 'NONE',
+ 'CUID' => null,
+ 'ECI' => Netresearch_OPS_Model_Eci_Values::MANUALLY_KEYED_FROM_MOTO,
+ 'OWNERTOWN' => 'Leipzig',
+ 'ORIG' => Mage::helper('ops/data')->getModuleVersionString(),
+ 'ECOM_SHIPTO_POSTAL_NAME_FIRST' => 'Hubertus',
+ 'ECOM_SHIPTO_POSTAL_NAME_LAST' => utf8_decode('Fürstenberg'),
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1' => utf8_decode('An der Tabaksmühle 3a'),
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE2' => '',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE3' => '',
+ 'ECOM_SHIPTO_POSTAL_COUNTRYCODE' => 'DE',
+ 'ECOM_SHIPTO_POSTAL_CITY' => 'Leipzig',
+ 'ECOM_SHIPTO_POSTAL_STATE' => '',
+ );
+ }
+
+ private function getRequestParamsWithoutAlias($quote, $order)
+ {
+ return array(
+ 'ALIAS' => '99',
+ 'AMOUNT' => 0.0,
+ 'CURRENCY' => 'USD',
+ 'OPERATION' => 'RES',
+ 'ORDERID' => Mage::getSingleton('ops/config')->getConfigData('devprefix')
+ . $order->getQuoteId(),
+ 'EMAIL' => 'hubertus.von.fuerstenberg@trash-mail.com',
+ 'OWNERADDRESS' => utf8_decode('An der Tabaksmühle 3a'),
+ 'OWNERZIP' => '04229',
+ 'OWNERTELNO' => null,
+ 'OWNERCTY' => 'DE',
+ 'ADDMATCH' => 1,
+ 'RTIMEOUT' => 45,
+ 'CREDITDEBIT' => 'C',
+ 'ECOM_SHIPTO_POSTAL_POSTALCODE' => '04229',
+ 'ECOM_BILLTO_POSTAL_POSTALCODE' => '04229',
+ 'CVC' => '123',
+ 'REMOTE_ADDR' => 'NONE',
+ 'OWNERTOWN' => 'Leipzig',
+ 'ORIG' => Mage::helper('ops/data')->getModuleVersionString(),
+ 'ECOM_SHIPTO_POSTAL_NAME_FIRST' => 'Hubertus',
+ 'ECOM_SHIPTO_POSTAL_NAME_LAST' => utf8_decode('Fürstenberg'),
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1' => utf8_decode('An der Tabaksmühle 3a'),
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE2' => '',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE3' => '',
+ 'ECOM_SHIPTO_POSTAL_COUNTRYCODE' => 'DE',
+ 'ECOM_SHIPTO_POSTAL_CITY' => 'Leipzig',
+ 'ECI' => 1,
+ 'CUID' => null,
+ 'ECOM_SHIPTO_POSTAL_STATE' => '',
+ );
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testConfirmDdPayment()
+ {
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $order = Mage::getModel('sales/order')->load(11);
+
+ $observerMock = $this->getModelMock(
+ 'ops/observer',
+ array('performDirectLinkRequest', 'invokeRequestParamValidation')
+ );
+
+ $requestParams = array(
+ 'AMOUNT' => 0.0,
+ 'CARDNO' => '12335BLZ12345566',
+ 'CN' => utf8_decode('Hubertus zu Fürstenberg'),
+ 'CURRENCY' => 'USD',
+ 'ED' => '9999',
+ 'OPERATION' => 'RES',
+ 'ORDERID' => Mage::getSingleton('ops/config')->getConfigData('devprefix')
+ . $quote->getId(),
+ 'PM' => 'Direct Debits DE',
+ 'OWNERADDRESS' => utf8_decode('An der Tabaksmühle 3a'),
+ 'OWNERZIP' => '04229',
+ 'OWNERTELNO' => null,
+ 'OWNERCTY' => 'DE',
+ 'ADDMATCH' => 1,
+ 'ECOM_SHIPTO_POSTAL_POSTALCODE' => '04229',
+ 'ECOM_BILLTO_POSTAL_POSTALCODE' => '04229',
+ 'CUID' => null,
+ 'BRAND' => 'Direct Debits DE',
+ 'ECI' => Netresearch_OPS_Model_Eci_Values::MANUALLY_KEYED_FROM_MOTO,
+ 'OWNERTOWN' => 'Leipzig',
+ );
+
+ $directDebitHelperMock = $this->getHelperMock('ops/directDebit', array('getDirectLinkRequestParams'));
+ $directDebitHelperMock->expects($this->any())
+ ->method('getDirectLinkRequestParams')
+ ->will($this->returnValue($requestParams));
+ $this->replaceByMock('helper', 'ops/directDebit', $directDebitHelperMock);
+
+ $observerMock->expects($this->any())
+ ->method('performDirectLinkRequest')
+ ->with($quote, $requestParams, 1)
+ ->will($this->returnValue('MOTO'));
+ $this->assertEquals('MOTO', $observerMock->confirmDdPayment($order, $quote));
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testConfirmDdPaymentWithNoECI()
+ {
+ $quote = Mage::getModel('sales/quote')->load(10);
+ $order = Mage::getModel('sales/order')->load(11);
+
+
+ $observerMock = $this->getModelMock(
+ 'ops/observer',
+ array('performDirectLinkRequest', 'invokeRequestParamValidation')
+ );
+
+
+ $requestParams = array(
+ 'AMOUNT' => 0.0,
+ 'CARDNO' => '12335BLZ12345566',
+ 'CN' => utf8_decode('Hubertus zu Fürstenberg'),
+ 'CURRENCY' => 'USD',
+ 'ED' => '9999',
+ 'OPERATION' => 'RES',
+ 'ORDERID' => Mage::getSingleton('ops/config')->getConfigData('devprefix')
+ . $quote->getId(),
+ 'PM' => 'Direct Debits DE',
+ 'OWNERADDRESS' => utf8_decode('An der Tabaksmühle 3a'),
+ 'OWNERZIP' => '04229',
+ 'OWNERTELNO' => null,
+ 'OWNERCTY' => 'DE',
+ 'ADDMATCH' => 1,
+ 'ECOM_SHIPTO_POSTAL_POSTALCODE' => '04229',
+ 'ECOM_BILLTO_POSTAL_POSTALCODE' => '04229',
+ 'CUID' => null,
+ 'OWNERTOWN' => 'Leipzig',
+ 'BRAND' => 'Direct Debits DE'
+ );
+
+ $directDebitHelperMock = $this->getHelperMock('ops/directDebit', array('getDirectLinkRequestParams'));
+ $directDebitHelperMock->expects($this->any())
+ ->method('getDirectLinkRequestParams')
+ ->will($this->returnValue($requestParams));
+ $this->replaceByMock('helper', 'ops/directDebit', $directDebitHelperMock);
+
+
+ $observerMock->expects($this->any())
+ ->method('performDirectLinkRequest')
+ ->with($quote, $requestParams, 1)
+ ->will($this->returnValue('ECOM'));
+
+ $this->assertEquals('ECOM', $observerMock->confirmDdPayment($order, $quote));
+ }
+
+ /**
+ * tests that the payment method is cleared before importing new data
+ * following conditions must be met in order to get the method gets cleared:
+ * 1. event must be sales_quote_payment_import_data_before
+ * 2. payment must be an instance of Mage_Sales_Quote_Payment
+ *
+ */
+ public function testClearPaymentMethodFromQuote()
+ {
+ $observer = Mage::getModel('ops/observer');
+ $event = new Varien_Event_Observer();
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setMethod('not relevant');
+ $eventData = new Varien_Event();
+ $event->setEvent($eventData);
+ $event->getEvent()->setData('payment', $payment);
+
+ // method is not cleared because of wring event
+ $observer->clearPaymentMethodFromQuote($event);
+ $this->assertEquals('not relevant', $event->getEvent()->getPayment()->getMethod());
+
+ // method is cleared
+ $event->setEventName('sales_quote_payment_import_data_before');
+ $observer->clearPaymentMethodFromQuote($event);
+ $this->assertEquals(null, $event->getEvent()->getPayment()->getMethod());
+
+ // method is not cleared because the payment is not a Mage_Sales_Quote_Payment
+ $payment = new Varien_Object();
+ $payment->setMethod('not relevant');
+ $event->getEvent()->setData('payment', $payment);
+ $observer->clearPaymentMethodFromQuote($event);
+ $this->assertEquals('not relevant', $event->getEvent()->getPayment()->getMethod());
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testaddStatusUpdateButtonToOrderView()
+ {
+ $adminSessionMock = $this->getModelMock('admin/session', array('isAllowed', 'init', 'save'));
+ $adminSessionMock->expects($this->any())
+ ->method('isAllowed')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'admin/session', $adminSessionMock);
+
+ $order = Mage::getModel('sales/order')->load(11);
+ Mage::register('sales_order', $order);
+ $block = Mage::app()->getLayout()->getBlockSingleton('adminhtml/sales_order_view');
+ $event = new Varien_Event_Observer();
+ $event->setBlock($block);
+ $observer = Mage::getModel('ops/observer');
+ $observer->addStatusUpdateButtonToOrderView($event);
+ $buttons = $block->getButtonsHtml();
+ $this->assertContains(Mage::helper('ops/data')->__('Refresh payment status'), $buttons);
+ $this->assertContains('setLocation(\'' . $block->getUrl('adminhtml/opsstatus/update') . '\')', $buttons);
+ Mage::unregister('sales_order');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testAddStatusUpdateButtonToOrderViewWillNotAddButton()
+ {
+ $adminSessionMock = $this->getModelMock('admin/session', array('isAllowed', 'init', 'save'));
+ $adminSessionMock->expects($this->any())
+ ->method('isAllowed')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('model', 'admin/session', $adminSessionMock);
+
+ $order = Mage::getModel('sales/order')->load(11);
+ Mage::register('sales_order', $order);
+ $block = Mage::app()->getLayout()->getBlockSingleton('adminhtml/sales_order_view');
+ $event = new Varien_Event_Observer();
+ $event->setBlock($block);
+ $observer = Mage::getModel('ops/observer');
+ $observer->addStatusUpdateButtonToOrderView($event);
+ $buttons = $block->getButtonsHtml();
+ $this->assertNotContains(Mage::helper('ops/data')->__('Refresh payment status'), $buttons);
+ $this->assertNotContains('setLocation(\'' . $block->getUrl('adminhtml/opsstatus/update') . '\')', $buttons);
+ Mage::unregister('sales_order');
+
+ $adminSessionMock = $this->getModelMock('admin/session', array('isAllowed', 'init', 'save'));
+ $adminSessionMock->expects($this->any())
+ ->method('isAllowed')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'admin/session', $adminSessionMock);
+
+ $order = Mage::getModel('sales/order')->load(30);
+ Mage::register('sales_order', $order);
+ $block = Mage::app()->getLayout()->getBlockSingleton('adminhtml/sales_order_view');
+ $event = new Varien_Event_Observer();
+ $event->setBlock($block);
+ $observer = Mage::getModel('ops/observer');
+ $observer->addStatusUpdateButtonToOrderView($event);
+ $buttons = $block->getButtonsHtml();
+ $this->assertNotContains(Mage::helper('ops/data')->__('Refresh payment status'), $buttons);
+ $this->assertNotContains('setLocation(\'' . $block->getUrl('adminhtml/opsstatus/update') . '\')', $buttons);
+ Mage::unregister('sales_order');
+ }
+
+ public function testAddCcPaymentMethod()
+ {
+ $observer = Mage::getModel('ops/observer');
+ $event = new Varien_Event_Observer();
+ $block = new Mage_Payment_Block_Form_Container();
+ $quote = Mage::getModel('sales/quote');
+ $block->setQuote($quote);
+ $eventData = new Varien_Event();
+ $event->setEvent($eventData);
+ $event->getEvent()->setData('block', $block);
+
+ $versionHelperMock = $this->getHelperMock('ops/version', array('canUseApplicableForQuote'));
+ $versionHelperMock->expects($this->any())
+ ->method('canUseApplicableForQuote')
+ ->will($this->returnvalue(false));
+ $this->replaceByMock('helper', 'ops/version', $versionHelperMock);
+
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('addCCForZeroAmountCheckout'));
+ $paymentHelperMock->expects($this->once())
+ ->method('addCCForZeroAmountCheckout')
+ ->will($this->returnValue($paymentHelperMock));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+ $observer->addCcPaymentMethod($event);
+ }
+
+ public function testDisableCaptureForZeroAmountInvoice()
+ {
+ $ccPaymentObject = Mage::getModel('ops/payment_cc');
+ $block = new Mage_Adminhtml_Block_Sales_Order_Invoice_Create_Items();
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethodInstance($ccPaymentObject);
+ $order = Mage::getModel('sales/order');
+ $order->setPayment($payment);
+ $invoice = Mage::getModel('sales/order_invoice');
+ $invoice->setBaseGrandTotal(0.00);
+ $invoice->setOrder($order);
+ $observer = Mage::getModel('ops/observer');
+ $event = new Varien_Event_Observer();
+ Mage::register('current_invoice', $invoice, true);
+ $eventData = new Varien_Event();
+ $event->setEvent($eventData);
+ $event->getEvent()->setData('block', $block);
+
+ $this->assertTrue($ccPaymentObject->canCapture());
+ $observer->disableCaptureForZeroAmountInvoice($event);
+ $this->assertFalse($ccPaymentObject->canCapture());
+
+ // clean up invoice from registry after test
+ Mage::unregister('current_invoice');
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testCheckoutTypeOnepageSaveOrderBefore()
+ {
+ $event = new Varien_Event_Observer();
+ $order = Mage::getModel('sales/order')->load(11);
+ $quotePayment = Mage::getModel('sales/quote_payment')->load(4);
+ $pmMock = $this->getModelMock('ops/payment_bankTransfer', array('getFormFields'));
+ $quotePayment->setMethodInstance($pmMock);
+ $quote = $this->getModelMock('sales/quote', array('getPayment'));
+ $quote->expects($this->any())
+ ->method('getPayment')
+ ->will($this->returnValue($quotePayment));
+
+ $quotePayment->setQuote($quote);
+ $quote->setPayment($quotePayment);
+ $this->replaceByMock('model', 'ops/payment_bankTransfer', $pmMock);
+ $event->setOrder($order);
+ $event->setQuote($quote);
+ $observerMock = $this->getModelMock('ops/observer', array('invokeRequestParamValidation'));
+ $observerMock->expects($this->once())
+ ->method('invokeRequestParamValidation');
+ $observerMock->checkoutTypeOnepageSaveOrderBefore($event);
+ }
+
+ /**
+ * @loadFixture ../../../var/fixtures/orders.yaml
+ */
+ public function testControllerActionCheckoutOnepagePostdispatch()
+ {
+ $fakeController = new Varien_Object();
+ $fakeResponse = new Varien_Object();
+ $quotePayment = Mage::getModel('sales/quote_payment')->load(4);
+ $pmMock = $this->getModelMock('ops/payment_bankTransfer', array('isAvailable'));
+ $pmMock->expects($this->any())
+ ->method('isAvailable')
+ ->will($this->returnValue(true));
+ $quote = $this->getModelMock('sales/quote', array('getPayment'));
+ $quote->expects($this->any())
+ ->method('getPayment')
+ ->will($this->returnValue($quotePayment));
+ $quotePayment->setQuote($quote);
+ $quote->setPayment($quotePayment);
+ $this->replaceByMock('model', 'ops/payment_bankTransfer', $pmMock);
+
+
+ $fakeOnePage = new Varien_Object();
+ $fakeOnePage->setQuote($quote);
+
+ $observerMock = $this->getModelMock('ops/observer', array('getOnepage'));
+ $observerMock->expects($this->once())
+ ->method('getOnepage')
+ ->will($this->returnValue($fakeOnePage));
+ $helperMock = $this->getHelperMock('ops/payment_request', array('getOwnerParams', 'extractShipToParameters'));
+ $helperMock->expects($this->once())
+ ->method('getOwnerParams')
+ ->will($this->returnValue(array()));
+ $helperMock->expects($this->once())
+ ->method('extractShipToParameters')
+ ->will($this->returnValue(array()));
+ $this->replaceByMock('helper', 'ops/payment_request', $helperMock);
+ $validatorMock = $this->getModelMock('ops/validator_parameter_validator', array('isValid', 'getMessages'));
+ $validatorMock->expects($this->once())
+ ->method('isValid')
+ ->will($this->returnValue(false));
+ $validatorMock->expects($this->any())
+ ->method('getMessages')
+ ->will($this->returnValue(array('Foo' => 'Not Valid')));
+ $this->replaceByMock('model', 'ops/validator_parameter_validator', $validatorMock);
+ $fakeResponse->setBody(
+ Mage::helper('core/data')->jsonEncode(array('error' => false, 'update_section' => 'foo'))
+ );
+ $fakeController->setResponse($fakeResponse);
+ $event = new Varien_Event_Observer();
+ $event->setControllerAction($fakeController);
+ $observerMock->controllerActionCheckoutOnepagePostdispatch($event);
+ $result = Mage::helper('core/data')->jsonDecode($fakeResponse->getBody());
+ $this->assertArrayHasKey('error', $result);
+ $this->assertArrayHasKey('goto_section', $result);
+ $this->assertArrayHasKey('fields', $result);
+ $this->assertArrayNotHasKey('update_section', $result);
+ }
+
+ public function testSalesOrderPaymentCapture()
+ {
+ $opsObserver = Mage::getModel('ops/observer');
+ $event = new Varien_Event_Observer();
+ $fakePayment = Mage::getModel('sales/order_payment');
+ $fakePayment->setMethod('checkmo');
+ $invoice = Mage::getModel('sales/order_invoice');
+ $event->setPayment($fakePayment);
+ $event->setInvoice($invoice);
+ $opsObserver->salesOrderPaymentCapture($event);
+ $this->assertNull($fakePayment->getInvoice());
+
+ $fakePayment = Mage::getModel('sales/order_payment');
+ $fakePayment->setMethod('ops_cc');
+ $event->setPayment($fakePayment);
+ $event->setInvoice($invoice);
+ $opsObserver->salesOrderPaymentCapture($event);
+ $this->assertEquals($invoice, $fakePayment->getInvoice());
+
+ }
+
+ public function testSetOrderStateForDirectLinkDoesNotChangeState()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests($order, 'payment/method_cc');
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getState());
+ }
+
+
+ public function testSetOrderStateForDirectLinkDoesNotChangeStateDueToHelper()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests($order, 'ops/payment_directDebit');
+ $this->registerPaymentHelperMockForDirectDebitNlTests(false);
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getState());
+ }
+
+ public function testSetOrderStateForDirectLinkDoesNotChangeStateDueToMissingInfos()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests($order, 'ops/payment_directDebit');
+ $this->registerPaymentHelperMockForDirectDebitNlTests(true);
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getState());
+ }
+
+ public function testSetOrderStateForDirectLinkDoesNotChangeStateDueToMissingPm()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests($order, 'ops/payment_directDebit', array('STATUS' => 51));
+ $this->registerPaymentHelperMockForDirectDebitNlTests(true);
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getState());
+ }
+
+ public function testSetOrderStateForDirectLinkDoesNotChangeStateDueToMissingStatus()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests(
+ $order, 'ops/payment_directDebit',
+ array('PM' => 'Direct Debits NL')
+ );
+ $this->registerPaymentHelperMockForDirectDebitNlTests(true);
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getState());
+ }
+
+ public function testSetOrderStateForDirectLinkDoesNotChangeStateDueToWrongPm()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests(
+ $order, 'ops/payment_directDebit',
+ array('PM' => 'Direct Debits DE', 'STATUS' => 51)
+ );
+ $this->registerPaymentHelperMockForDirectDebitNlTests(true);
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getState());
+ }
+
+ public function testSetOrderStateForDirectLinkDoesNotChangeStateDueToWrongStatus()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests(
+ $order, 'ops/payment_directDebit',
+ array('PM' => 'Direct Debits NL', 'STATUS' => 5)
+ );
+ $this->registerPaymentHelperMockForDirectDebitNlTests(true);
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PROCESSING, $order->getState());
+ }
+
+ public function testSetOrderStateForDirectLinkDoesChangeState()
+ {
+ $order = $this->getOrderForDirectDebitNlTest();
+ $event = $this->getEventForDirectDebitNlTests(
+ $order, 'ops/payment_directDebit',
+ array('PM' => 'Direct Debits NL',
+ 'status' => Netresearch_OPS_Model_Status::AUTHORIZED)
+ );
+ $this->registerPaymentHelperMockForDirectDebitNlTests(true);
+ $observer = Mage::getModel('ops/observer');
+ $observer->setOrderStateDirectLink($event);
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PENDING_PAYMENT, $order->getStatus());
+ $this->assertEquals(Mage_sales_Model_Order::STATE_PENDING_PAYMENT, $order->getState());
+ }
+
+ /**
+ * @return array
+ */
+ protected function getEventForDirectDebitNlTests($order, $paymentMethod, array $addInfos = array())
+ {
+ $event = new Varien_Event_Observer();
+ $payment = $this->getModelMock('payment/info', array('getMethodInstance', 'getOrder'));
+ $payment->expects($this->any())
+ ->method('getMethodInstance')
+ ->will($this->returnValue(Mage::getModel($paymentMethod)));
+ $payment->expects($this->any())
+ ->method('getOrder')
+ ->will($this->returnValue($order));
+ $payment->setAdditionalInformation($addInfos);
+ $event->setPayment($payment);
+
+ return $event;
+ }
+
+ /**
+ * @return PHPUnit_Framework_MockObject_MockObject
+ */
+ protected function getOrderForDirectDebitNlTest()
+ {
+ $order = $this->getModelMock('sales/order', array('save',));
+ $order->setStatus(Mage_sales_Model_Order::STATE_PROCESSING);
+ $order->setState(Mage_sales_Model_Order::STATE_PROCESSING);
+
+ return $order;
+ }
+
+ protected function registerPaymentHelperMockForDirectDebitNlTests($isInlinePaymentWithOrderIdRetVal = true)
+ {
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('isInlinePayment'));
+ $paymentHelperMock->expects($this->once())
+ ->method('isInlinePayment')
+ ->will($this->returnValue($isInlinePaymentWithOrderIdRetVal));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+ }
+
+ public function testUpdateRecurringProfileButtons()
+ {
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setMethodCode(Netresearch_OPS_Model_Payment_Recurring_Cc::CODE)
+ ->setState(Mage_Sales_Model_Recurring_Profile::STATE_ACTIVE)
+ ->setId(1);
+
+ $this->replaceRegistry('current_recurring_profile', $profile);
+
+ /** @var $block Mage_Sales_Block_Adminhtml_Recurring_Profile_View */
+ $block = Mage::app()->getLayout()->createBlock('sales/adminhtml_recurring_profile_view');
+ $block->setLayout(Mage::app()->getLayout());
+ $observer = new Varien_Event_Observer();
+ $event = new Varien_Event();
+ $event->setData('block', $block);
+ $observer->setEvent($event);
+
+ $subject = Mage::getModel('ops/observer');
+ $subject->updateRecurringProfileButtons($observer);
+ $html = $block->getButtonsHtml('header');
+
+ $this->assertContains(
+ 'Suspending the subscription here will not actually cancel the subscription on Ingenico ePayments side.',
+ $html
+ );
+ }
+
+ public function overrideRecurringProfileState()
+ {
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setMethodCode(Netresearch_OPS_Model_Payment_Recurring_Cc::CODE)
+ ->setState('abc')
+ ->setNewState('def')
+ ->setOverrideState(true);
+
+ $event = new Varien_Event_Observer();
+ $event->setObject($profile);
+
+ $observer = Mage::getModel('ops/observer');
+ $observer->overrideRecurringProfileState($event);
+
+ $this->assertEquals($profile->getNewState(), $profile->getState());
+ $this->assertEquals('def', $profile->getState());
+ }
+
+ /**
+ * @test
+ */
+ public function sendTransactionalEmailsNoOps()
+ {
+ // no emails on third party payments
+ $helperMock = $this->getHelperMock('ops/data', array('sendTransactionalEmail'));
+ $helperMock
+ ->expects($this->never())
+ ->method('sendTransactionalEmail')
+ ->with($this->isInstanceOf('Mage_Sales_Model_Order'));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+
+ $payment = new Varien_Object(
+ array(
+ 'method' => Mage::getModel('payment/method_checkmo')->getCode(),
+ )
+ );
+ $order = new Varien_Object(
+ array(
+ 'payment' => $payment,
+ )
+ );
+
+ $observerMock = $this->getMockBuilder('Varien_Event_Observer')
+ ->setMethods(array('getOrder'))
+ ->getMock();
+ $observerMock
+ ->expects($this->once())
+ ->method('getOrder')
+ ->willReturn($order);
+
+ Mage::getModel('ops/observer')->sendTransactionalEmails($observerMock);
+ }
+
+ /**
+ * @test
+ */
+ public function sendTransactionalEmailsGatewayPayment()
+ {
+ // no emails on ingenico redirect payments
+ $helperMock = $this->getHelperMock('ops/data', array('sendTransactionalEmail'));
+ $helperMock
+ ->expects($this->never())
+ ->method('sendTransactionalEmail')
+ ->with($this->isInstanceOf('Mage_Sales_Model_Order'));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+
+ $payment = new Varien_Object(
+ array(
+ 'method_instance' => Mage::getModel('ops/payment_bankTransfer'),
+ 'order_place_redirect_url' => 'foo',
+ )
+ );
+ $order = new Varien_Object(
+ array(
+ 'payment' => $payment,
+ )
+ );
+ $quote = new Varien_Object(
+ array(
+ 'payment' => $payment,
+ )
+ );
+
+ $observerMock = $this->getMockBuilder('Varien_Event_Observer')
+ ->setMethods(array('getOrder', 'getQuote'))
+ ->getMock();
+ $observerMock
+ ->expects($this->once())
+ ->method('getOrder')
+ ->willReturn($order);
+ $observerMock
+ ->expects($this->once())
+ ->method('getQuote')
+ ->willReturn($quote);
+
+ Mage::getModel('ops/observer')->sendTransactionalEmails($observerMock);
+ }
+
+ /**
+ * @test
+ */
+ public function sendTransactionalEmailsException()
+ {
+ // exception not really testable.
+ // just assert that second call to sendTransactionalEmail is not invoked
+ $helperMock = $this->getHelperMock('ops/data', array('sendTransactionalEmail'));
+ $helperMock
+ ->expects($this->exactly(1))
+ ->method('sendTransactionalEmail')
+ ->withConsecutive(
+ $this->isInstanceOf('Mage_Sales_Model_Order'),
+ $this->isInstanceOf('Mage_Sales_Model_Order_Invoice')
+ )
+ ->willThrowException(new Exception('no mails foo'));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+
+
+ $payment = new Varien_Object(
+ array(
+ 'method_instance' => Mage::getModel('ops/payment_bankTransfer'),
+ )
+ );
+ $quote = new Varien_Object(
+ array(
+ 'payment' => $payment,
+ )
+ );
+ $orderMock = $this->getModelMock('sales/order', array('getPayment'));
+ $orderMock
+ ->expects($this->once())
+ ->method('getPayment')
+ ->willReturn($payment);
+
+ $observerMock = $this->getMockBuilder('Varien_Event_Observer')
+ ->setMethods(array('getOrder', 'getQuote'))
+ ->getMock();
+ $observerMock
+ ->expects($this->once())
+ ->method('getOrder')
+ ->willReturn($orderMock);
+ $observerMock
+ ->expects($this->once())
+ ->method('getQuote')
+ ->willReturn($quote);
+
+ Mage::getModel('ops/observer')->sendTransactionalEmails($observerMock);
+ }
+
+ /**
+ * @test
+ */
+ public function sendTransactionalEmailsSuccess()
+ {
+ $helperMock = $this->getHelperMock('ops/data', array('sendTransactionalEmail'));
+ $helperMock
+ ->expects($this->exactly(2))
+ ->method('sendTransactionalEmail')
+ ->withConsecutive(
+ $this->isInstanceOf('Mage_Sales_Model_Order'),
+ $this->isInstanceOf('Mage_Sales_Model_Order_Invoice')
+ );
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+
+ // invoice
+ $invoice = Mage::getModel('sales/order_invoice');
+
+ // order payment
+ $payment = new Varien_Object(
+ array(
+ 'method_instance' => Mage::getModel('ops/payment_cc'),
+ 'created_invoice' => $invoice,
+ )
+ );
+
+ // order
+ $orderMock = $this->getModelMock('sales/order', array('getPayment'));
+ $orderMock
+ ->expects($this->exactly(2))
+ ->method('getPayment')
+ ->willReturn($payment);
+ $this->replaceByMock('model', 'sales/order', $orderMock);
+ $order = Mage::getModel('sales/order');
+
+ // quote
+ $quote = new Varien_Object(
+ array(
+ 'payment' => $payment,
+ )
+ );
+
+ $observerMock = $this->getMockBuilder('Varien_Event_Observer')
+ ->setMethods(array('getOrder', 'getQuote'))
+ ->getMock();
+ $observerMock->expects($this->once())->method('getOrder')->willReturn($order);
+ $observerMock->expects($this->once())->method('getQuote')->willReturn($quote);
+
+ Mage::getModel('ops/observer')->sendTransactionalEmails($observerMock);
+ }
+
+ public function testSendPayPerMailInfoSuccess()
+ {
+ // order payment
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethodInstance(Mage::getModel('ops/payment_payPerMail'));
+
+ $order = Mage::getModel('sales/order');
+ $order->setPayment($payment);
+
+ $observerMock = $this->getMockBuilder('Varien_Event_Observer')
+ ->setMethods(['getOrder'])
+ ->getMock()
+ ;
+ $observerMock->expects($this->once())->method('getOrder')->willReturn($order);
+ Mage::getModel('ops/observer')->sendPayPerMailInfo($observerMock);
+ }
+
+ public function testSendPayPerMailInfoFailure()
+ {
+ // order payment
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethodInstance(Mage::getModel('ops/payment_cc'));
+
+ $order = Mage::getModel('sales/order');
+ $order->setPayment($payment);
+
+ $observerMock = $this->getMockBuilder('Varien_Event_Observer')
+ ->setMethods(['getOrder'])
+ ->getMock()
+ ;
+ $observerMock->expects($this->once())->method('getOrder')->willReturn($order);
+ Mage::getModel('ops/observer')->sendPayPerMailInfo($observerMock);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/ObserverTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Model/ObserverTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractCaptureTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractCaptureTest.php
new file mode 100644
index 0000000..bf577a6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractCaptureTest.php
@@ -0,0 +1,276 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Model_Payment_AbstractCaptureTest
+ extends EcomDev_PHPUnit_Test_Case_Controller
+{
+
+ protected $testObject = null;
+
+ /**
+ * set up a clean environment for the tests
+ */
+ public function setUp()
+ {
+ parent::setUp();
+ $this->testObject = Mage::getModel('ops/payment_abstract');
+ }
+
+ public function tearDown()
+ {
+ parent::tearDown();
+ Mage::unregister('ops_auto_capture');
+ }
+
+ public function testCaptureWithAutoCapture()
+ {
+ Mage::register('ops_auto_capture', true);
+ $payment = new Varien_Object();
+ $amount = null;
+ $this->testObject->capture($payment, $amount);
+ }
+
+ public function testCaptureWithPreviousCaptureRequestLeadToRedirect()
+ {
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $amount = 1;
+ $captureHelperMock = $this->getHelperMock('ops/order_capture', array('prepareOperation'));
+ $this->replaceByMock('helper', 'ops/order_capture', $captureHelperMock);
+ $this->mockDirectlinkHelperCheckDirectLinkTransact(
+ $this->returnValue(true),
+ $this->equalTo(Netresearch_OPS_Model_Payment_Abstract::OPS_CAPTURE_TRANSACTION_TYPE),
+ $this->equalTo($testOrder->getId())
+ );
+
+ $message = Mage::helper('ops/data')->__(
+ 'You already sent a capture request. Please wait until the capture request is acknowledged.'
+ );
+ $this->mockDataHelperMockRedirectNoticed($testOrder->getId(), $message);
+
+ $this->testObject->capture($testPayment, $amount);
+ }
+
+ public function testCaptureWithPreviousVoidRequestLeadToRedirect()
+ {
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $amount = 1;
+ $captureHelperMock = $this->getHelperMock('ops/order_capture', array('prepareOperation'));
+ $this->replaceByMock('helper', 'ops/order_capture', $captureHelperMock);
+ $this->mockDirectlinkHelperCheckDirectLinkTransact($this->onConsecutiveCalls(false, true));
+ $message = Mage::helper('ops/data')->__(
+ 'There is one void request waiting. Please wait until this request is acknowledged.'
+ );
+ $this->mockDataHelperMockRedirectNoticed($testOrder->getId(), $message);
+
+ $this->testObject->capture($testPayment, $amount);
+ }
+
+ public function testCaptureWillPerformRequest()
+ {
+// $this->markTestIncomplete();
+
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $testPayment->setAdditionalInformation('paymentId', 'payID');
+ $amount = 10;
+ $this->mockOrderCaptureHelper();
+ $requestParams = $this->getCaptureRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->returnValue(
+ array('STATUS' => Netresearch_OPS_Model_Status::PAYMENT_PROCESSED_BY_MERCHANT)
+ );
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment'));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->capture($testPayment, $amount);
+ }
+
+
+ public function testCaptureWillPerformRequestWithPaymentProcessing()
+ {
+// $this->markTestIncomplete();
+
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $amount = 10;
+ $this->mockDirectlinkHelperCheckDirectLinkTransact($this->returnValue(false));
+
+ $this->mockOrderCaptureHelper(array('operation' => 'SAS', 'type' => 'capture'));
+ $requestParams = $this->getCaptureRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->returnValue(
+ array(
+ 'STATUS' => Netresearch_OPS_Model_Status::PAYMENT_PROCESSING,
+ 'PAYID' => 4711,
+ 'PAYIDSUB' => 1
+ )
+ );
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment'));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->capture($testPayment, $amount);
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testCaptureWillPerformRequestWithInvalidResponseLeadToException()
+ {
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $testPayment->setAdditionalInformation('paymentId', 'payID');
+ $amount = 10;
+ $this->mockOrderCaptureHelper();
+ $requestParams = $this->getCaptureRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->returnValue(array('STATUS' => 320));
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment'));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+ $statusUpdateMock = $this->getModelMock('ops/status_update', array('updateStatusFor'));
+ $this->replaceByMock('model', 'ops/status_update', $statusUpdateMock);
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->capture($testPayment, $amount);
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testCaptureWillPerformRequestWithExceptionWillThrowException()
+ {
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $amount = 10;
+ $this->mockOrderCaptureHelper();
+ $requestParams = $this->getCaptureRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->throwException(new Exception('foo'));
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment'));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+ $statusUpdateMock = $this->getModelMock('ops/status_update', array('updateStatusFor'));
+ $this->replaceByMock('model', 'ops/status_update', $statusUpdateMock);
+
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->capture($testPayment, $amount);
+ }
+
+ protected function mockOrderCaptureHelper($returnValue = array('operation' => 'SAS'))
+ {
+ $captureHelperMock = $this->getHelperMock('ops/order_capture', array('prepareOperation'));
+ $captureHelperMock->expects($this->once())
+ ->method('prepareOperation')
+ ->will($this->returnValue($returnValue));
+ $this->replaceByMock('helper', 'ops/order_capture', $captureHelperMock);
+ }
+
+ /**
+ * @param $firstArg
+ * @param $secondArg
+ */
+ protected function mockDataHelperMockRedirectNoticed($firstArg, $secondArg, $returnValue = true)
+ {
+ $dataHelperMock = $this->getHelperMock('ops/data', array('redirectNoticed'));
+ $dataHelperMock->expects($this->once())
+ ->method('redirectNoticed')
+ ->with($this->equalTo($firstArg), $this->equalTo($secondArg))
+ ->will($this->returnValue($returnValue));
+
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+ }
+
+ /**
+ * @return array
+ */
+ protected function preparePayment($order, $method = 'ops_iDeal')
+ {
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setOrder($order);
+ $payment->setMethod($method);
+ $payment->setAdditionalInformation('paymentId', 'payID');
+
+ $order->setPayment($payment);
+ return $payment;
+ }
+
+ /**
+ * @param $order
+ *
+ * @return PHPUnit_Framework_MockObject_MockObject
+ */
+ protected function getOrderMock()
+ {
+ $order = $this->getModelMock('sales/order', array('save', 'load', '_beforeSave'));
+ $order->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($order));
+ $order->setId(1);
+ $this->replaceByMock('model', 'sales/order', $order);
+
+ return $order;
+ }
+
+ /**
+ * @param $amount
+ * @param $testPayment
+ *
+ * @return array
+ */
+ protected function getCaptureRequestParams($amount, $testPayment)
+ {
+ $requestParams = array(
+ 'AMOUNT' => Mage::helper('ops/data')->getAmount($amount),
+ 'PAYID' => $testPayment->getAdditionalInformation('paymentId'),
+ 'OPERATION' => Mage::helper('ops/order_capture')->determineOperationCode($testPayment, $amount),
+ 'CURRENCY' => Mage::app()->getStore()->getBaseCurrencyCode()
+ );
+
+ return $requestParams;
+ }
+
+ /**
+ * @param $requestParams
+ * @param $testOpsResponse
+ */
+ protected function mockApiDirectLink($requestParams, $testOpsResponse)
+ {
+ $apiDirectLinkMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $apiDirectLinkMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ $this->equalTo($requestParams),
+ $this->equalTo(Mage::getModel('ops/config')->getDirectLinkGatewayPath()),
+ $this->equalTo(null)
+ )
+ ->will($testOpsResponse);
+ $this->replaceByMock('model', 'ops/api_directlink', $apiDirectLinkMock);
+ }
+
+ protected function mockDirectlinkHelperCheckDirectLinkTransact($will, $arg1 = null, $arg2 = null)
+ {
+
+ $helperMock = $this->getHelperMock('ops/directlink', array('checkExistingTransact', 'directLinkTransact'));
+ $helperMock->expects($this->any())
+ ->method('checkExistingTransact')
+ ->with($this->getConstraintForArg($arg1), $this->getConstraintForArg($arg2))
+ ->will($will);
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+ }
+
+ protected function getConstraintForArg($arg)
+ {
+ if (null === $arg) {
+ $arg = $this->anything();
+ }
+
+ return $arg;
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractRefundTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractRefundTest.php
new file mode 100644
index 0000000..d7cc4bb
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractRefundTest.php
@@ -0,0 +1,214 @@
+testObject = $this->getModelMock('ops/payment_cc', array('canRefund'));
+ $this->testObject->expects($this->any())
+ ->method('canRefund')
+ ->will($this->returnValue(true));
+ $this->mockRefundHelper();
+ $this->mockDataHelper();
+ $this->mockPaymentHelper();
+ $sessionMock = $this->getModelMockBuilder('core/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+ }
+
+ public function tearDown()
+ {
+ parent::tearDown();
+ Mage::unregister('ops_auto_creditmemo');
+ }
+
+ /**
+ *
+ */
+ public function testRefundWillPerformRequestWithRefundPending()
+ {
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $testPayment->setAdditionalInformation('paymentId', 'payID');
+ $amount = 10;
+ $requestParams = $this->getRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->returnValue(
+ array('STATUS' => Netresearch_OPS_Model_Status::REFUND_UNCERTAIN)
+ );
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->refund($testPayment, $amount);
+ }
+
+ /**
+ *
+ */
+ public function testRefundWillPerformRequestWithRefundProcessed()
+ {
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $testPayment->setAdditionalInformation('paymentId', 'payID');
+ $amount = 10;
+ $requestParams = $this->getRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->returnValue(
+ array('STATUS' => Netresearch_OPS_Model_Status::REFUND_PROCESSED_BY_MERCHANT)
+ );
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->refund($testPayment, $amount);
+
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testRefundWillPerformRequestWithInvalidResponseLeadToException()
+ {
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $testPayment->setAdditionalInformation('paymentId', 'payID');
+ $amount = 10;
+ $requestParams = $this->getRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->returnValue(
+ array('STATUS' => 500)
+ );
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+
+ $statusUpdateMock = $this->getModelMock('ops/status_update', array('updateStatusFor'));
+ $this->replaceByMock('model', 'ops/status_update', $statusUpdateMock);
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->refund($testPayment, $amount);
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testCaptureWillPerformRequestWithExceptionWillThrowException()
+ {
+ $this->mockRefundHelper();
+ $testOrder = $this->getOrderMock();
+ $testPayment = $this->preparePayment($testOrder);
+ $testPayment->setAdditionalInformation('paymentId', 'payID');
+ $amount = 10;
+ $requestParams = $this->getRequestParams($amount, $testPayment);
+ $testOpsResponse = $this->throwException(new Exception('foo'));
+ $this->mockApiDirectLink($requestParams, $testOpsResponse);
+
+ $statusUpdateMock = $this->getModelMock('ops/status_update', array('updateStatusFor'));
+ $this->replaceByMock('model', 'ops/status_update', $statusUpdateMock);
+ $this->testObject->setInfoInstance($testPayment);
+ $this->testObject->refund($testPayment, $amount);
+ }
+
+ /**
+ * @param $amount
+ * @param $testPayment
+ */
+ protected function getRequestParams($amount, $testPayment)
+ {
+ $requestParams = array(
+ 'AMOUNT' => Mage::helper('ops/data')->getAmount($amount),
+ 'PAYID' => $testPayment->getAdditionalInformation('paymentId'),
+ 'OPERATION' => Netresearch_OPS_Model_Payment_Abstract::OPS_REFUND_PARTIAL,
+ 'CURRENCY' => Mage::app()->getStore()->getBaseCurrencyCode()
+ );
+
+ return $requestParams;
+ }
+
+ /**
+ * @param $requestParams
+ * @param $testOpsResponse
+ */
+ protected function mockApiDirectLink($requestParams, $testOpsResponse)
+ {
+ $apiDirectLinkMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $apiDirectLinkMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ $this->equalTo($requestParams),
+ $this->equalTo(Mage::getModel('ops/config')->getDirectLinkGatewayPath()),
+ $this->equalTo(null)
+ )
+ ->will($testOpsResponse);
+ $this->replaceByMock('model', 'ops/api_directlink', $apiDirectLinkMock);
+ }
+
+ /**
+ * @return array
+ */
+ protected function preparePayment($order, $method = 'ops_cc')
+ {
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setOrder($order);
+ $order->setPayment($payment);
+ $payment->setAdditionalInformation('paymentId', 'payID');
+ $payment->setMethod($method);
+
+ return $payment;
+ }
+
+ /**
+ * @param $order
+ *
+ * @return PHPUnit_Framework_MockObject_MockObject
+ */
+ protected function getOrderMock()
+ {
+ $order = $this->getModelMock('sales/order', array('save', 'load', '_beforeSave'));
+ $order->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($order));
+ $order->setId(1);
+ $this->replaceByMock('model', 'sales/order', $order);
+
+ return $order;
+ }
+
+ protected function mockRefundHelper()
+ {
+ $helperMock = $this->getHelperMock('ops/order_refund', array('getCreditMemoRequestParams', 'createRefundTransaction'));
+ $params = array(
+ 'creditmemo' => array(
+ 'items' => array(
+ 1 => array(
+ 'qty' => 0
+ ),
+ 2 => array(
+ 'qty' => 0
+ )
+ ),
+ 'shipping_amount' => 0,
+ 'adjustment_positive' => 10,
+ 'adjustment_negative' => 0
+
+ )
+ );
+ $helperMock->expects($this->any())
+ ->method('getCreditMemoRequestParams')
+ ->will($this->returnValue($params));
+ $this->replaceByMock('helper', 'ops/order_refund', $helperMock);
+ }
+
+ protected function mockDataHelper()
+ {
+ $helperMock = $this->getHelperMock('ops/data', array('redirect'));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+ }
+
+ protected function mockPaymentHelper()
+ {
+ $helperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment', 'saveOpsRefundOperationCodeToPayment'));
+ $this->replaceByMock('helper', 'ops/payment', $helperMock);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest.php
new file mode 100644
index 0000000..af92dd0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest.php
@@ -0,0 +1,890 @@
+model = Mage::getModel('ops/payment_abstract');
+ }
+
+ public function testCaptureWithZeroAmount()
+ {
+ $paymentObject = new Varien_Object();
+ $directLinkHelperMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkHelperMock->expects($this->never())
+ ->method('performRequest');
+ $this->assertTrue($this->model->capture($paymentObject, 0.00) instanceof Netresearch_OPS_Model_Payment_Abstract);
+ }
+
+ /**
+ * @test
+ */
+ public function _getOrderDescriptionShorterThen100Chars()
+ {
+ $items = array(
+ new Varien_Object(
+ array(
+ 'parent_item' => false,
+ 'name' => 'abc'
+ )
+ ),
+ new Varien_Object(
+ array(
+ 'parent_item' => true,
+ 'name' => 'def'
+ )
+ ),
+ new Varien_Object(
+ array(
+ 'parent_item' => false,
+ 'name' => 'ghi'
+ )
+ ),
+ new Varien_Object(
+ array(
+ 'parent_item' => false,
+ 'name' => 'Dubbelwerkende cilinder Boring ø70 Stang ø40 3/8'
+ )
+ ),
+ new Varien_Object(
+ array(
+ 'parent_item' => false,
+ 'name' => '0123456789012345678901234567890123456789'
+ )
+ ),
+ );
+
+ $order = $this->getModelMock('sales/order', array('getAllItems'));
+ $order->expects($this->any())
+ ->method('getAllItems')
+ ->will($this->returnValue($items));
+
+ $result = Mage::getModel('ops/payment_abstract')->_getOrderDescription($order);
+ $this->assertEquals(
+ 'abc, ghi, Dubbelwerkende cilinder Boring ø70 Stang ø40 3/8, 0123456789012345678901234567890123456789',
+ $result
+ );
+ }
+
+ /**
+ * @test
+ */
+ public function _getOrderDescriptionLongerThen100Chars()
+ {
+ $items = array(
+ new Varien_Object(
+ array(
+ 'parent_item' => false,
+ 'name' => '1bcdefghij abcdefghij abcdefghij abcdefghij abcdefghi1' //54 chars
+ )
+ ),
+ new Varien_Object(
+ array(
+ 'parent_item' => false,
+ 'name' => '2bcdefghij abcdefghij abcdefghij abcdefghij' //54 chars
+ )
+ )
+ );
+
+ $order = $this->getModelMock('sales/order', array('getAllItems'));
+ $order->expects($this->any())
+ ->method('getAllItems')
+ ->will($this->returnValue($items));
+
+ $result = Mage::getModel('ops/payment_abstract')->_getOrderDescription($order);
+ $this->assertEquals(
+ '1bcdefghij abcdefghij abcdefghij abcdefghij abcdefghi1, 2bcdefghij abcdefghij abcdefghij abcdefghij',
+ $result
+ );
+ }
+
+ /**
+ * @test
+ */
+ public function _getOrderDescriptionLongerThen100CharsOneItem()
+ {
+ $items = array(
+ new Varien_Object(
+ array(
+ 'parent_item' => false,
+ 'name' => '1bcdefghij abcdefghij abcdefghij abcdefghij abcdefghi1 '.
+ '2bcdefghij abcdefghij abcdefghij abcdefghij a'
+ )
+ )
+ );
+
+ $order = $this->getModelMock('sales/order', array('getAllItems'));
+ $order->expects($this->any())
+ ->method('getAllItems')
+ ->will($this->returnValue($items));
+
+ $result = Mage::getModel('ops/payment_abstract')->_getOrderDescription($order);
+ $this->assertEquals(
+ '1bcdefghij abcdefghij abcdefghij abcdefghij abcdefghi1 2bcdefghij abcdefghij abcdefghij abcdefghij a',
+ $result
+ );
+ }
+
+ /**
+ * check if payment method BankTransfer returns correct BRAND and PM values
+ *
+ * @loadExpectation paymentMethods
+ * @test
+ */
+ public function shouldReturnCorrectBrandAndPMValuesForBankTransfer()
+ {
+ $method = Mage::getModel('ops/payment_bankTransfer');
+
+ $payment = $this->getModelMock('sales/quote_payment', array('getId'));
+ $payment->expects($this->any())
+ ->method('getId')
+ ->will($this->returnValue('1'));
+ $this->replaceByMock('model', 'sales/quote_payment', $payment);
+
+ $method = Mage::getModel('ops/payment_bankTransfer');
+ $method->setInfoInstance($payment);
+ try {
+ $method->assignData(array('country_id' => 'DE'));
+ } catch (Mage_Core_Exception $e) {
+ if ('Cannot retrieve the payment information object instance.'
+ != $e->getMessage()
+ ) {
+ throw $e;
+ }
+ }
+ $this->assertEquals(
+ $this->expected('ops_bankTransferDe')->getBrand(),
+ $method->getOpsBrand(null)
+ );
+ $reflectedMethod = new ReflectionMethod($method, 'getOpsCode');
+ $reflectedMethod->setAccessible(true);
+ $this->assertEquals(
+ $this->expected('ops_bankTransferDe')->getPm(),
+ $reflectedMethod->invoke($method)
+ );
+ }
+
+ /**
+ * @test
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testCanCancelManually()
+ {
+ $opsAbstractPayment = new Netresearch_OPS_Model_Payment_Abstract();
+
+ //Check for successful can cancel (pending_payment and payment status 0)
+ $order = Mage::getModel("sales/order")->load(11);
+ $this->assertTrue($opsAbstractPayment->canCancelManually($order));
+
+ //Check for successful cancel (pending_payment and payment status null/not existing)
+ $order = Mage::getModel("sales/order")->load(14);
+ $this->assertTrue($opsAbstractPayment->canCancelManually($order));
+
+ //Check for denied can cancel (pending_payment and payment status 5)
+ $order = Mage::getModel("sales/order")->load(12);
+ $this->assertFalse($opsAbstractPayment->canCancelManually($order));
+
+ //Check for denied can cancel (processing and payment status 0)
+ $order = Mage::getModel("sales/order")->load(13);
+ $this->assertTrue($opsAbstractPayment->canCancelManually($order));
+ }
+
+
+ public function testGetCloseTransactionFromCreditMemoData()
+ {
+ $reflection_class
+ = new ReflectionClass("Netresearch_OPS_Model_Payment_Abstract");
+
+ //Then we need to get the method we wish to test and
+ //make it accessible
+ $method = $reflection_class->getMethod(
+ "getCloseTransactionFromCreditMemoData"
+ );
+ $method->setAccessible(true);
+
+ //We need to create an empty object to pass to
+ //ReflectionMethod invoke method followed by our
+ //test parameters
+ $paymentModel = new Netresearch_OPS_Model_Payment_Abstract(null);
+
+ $this->assertFalse($method->invoke($paymentModel, array()));
+ $this->assertFalse(
+ $method->invoke(
+ $paymentModel, array('ops_close_transaction' => 'OFF')
+ )
+ );
+ $this->assertFalse(
+ $method->invoke(
+ $paymentModel, array('ops_close_transaction' => 'off')
+ )
+ );
+ $this->assertFalse(
+ $method->invoke($paymentModel, array('ops_close_transaction' => ''))
+ );
+ $this->assertFalse(
+ $method->invoke($paymentModel, array('ops_close_transaction' => 1))
+ );
+
+ $this->assertTrue(
+ $method->invoke(
+ $paymentModel, array('ops_close_transaction' => 'on')
+ )
+ );
+ $this->assertTrue(
+ $method->invoke(
+ $paymentModel, array('ops_close_transaction' => 'ON')
+ )
+ );
+ }
+
+
+ /**
+ * @test
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testGetMethodDependendFormFields()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $sessionMock = $this->getModelMock('checkout/session', array('getQuote'));
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+
+ $sessionMock = $this->getModelMock('customer/session', array('isLoggedIn'));
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+
+
+ $configMock = $this->getModelMock('ops/config', array('canSubmitExtraParameter'));
+ $configMock->expects($this->any())
+ ->method('canSubmitExtraParameter')
+ ->will($this->returnValue(true));
+ $paymentModel = Mage::getModel('ops/payment_abstract');
+ $paymentModel->setConfig($configMock);
+ $formFields = $paymentModel->getFormFields($order, array());
+
+ $this->assertTrue(array_key_exists('CN', $formFields));
+ $this->assertTrue(array_key_exists('OWNERZIP', $formFields));
+ $this->assertTrue(array_key_exists('OWNERCTY', $formFields));
+ $this->assertTrue(array_key_exists('OWNERTOWN', $formFields));
+ $this->assertTrue(array_key_exists('COM', $formFields));
+ $this->assertTrue(array_key_exists('OWNERTELNO', $formFields));
+ $this->assertTrue(array_key_exists('OWNERADDRESS', $formFields));
+ $this->assertTrue(array_key_exists('BRAND', $formFields));
+ $this->assertTrue(array_key_exists('ADDMATCH', $formFields));
+ $this->assertTrue(array_key_exists('ECOM_SHIPTO_POSTAL_POSTALCODE', $formFields));
+ $this->assertTrue(array_key_exists('ECOM_BILLTO_POSTAL_POSTALCODE', $formFields));
+ $this->assertTrue(array_key_exists('CUID', $formFields));
+
+ $order = Mage::getModel('sales/order')->load(27);
+
+ $formFields = $paymentModel->getFormFields($order, array());
+ $this->assertTrue(array_key_exists('ECOM_SHIPTO_POSTAL_POSTALCODE', $formFields));
+
+ $order = Mage::getModel('sales/order')->load(11);
+ $configMock = $this->getModelMock('ops/config', array('canSubmitExtraParameter'));
+ $configMock->expects($this->any())
+ ->method('canSubmitExtraParameter')
+ ->will($this->returnValue(false));
+ $paymentModel = Mage::getModel('ops/payment_abstract');
+ $paymentModel->setConfig($configMock);
+ $params = $paymentModel->getMethodDependendFormFields($order, array());
+ foreach ($this->getOwnerParams() as $ownerParam) {
+ if ($ownerParam == 'OWNERZIP') continue;
+ $this->assertArrayNotHasKey($ownerParam, $params);
+ }
+ foreach ($this->getShippingParams() as $shippingParam) {
+ $this->assertArrayNotHasKey($shippingParam, $params);
+ }
+
+ $order = Mage::getModel('sales/order')->load(19);
+
+ $configMock = $this->getModelMock('ops/config', array('canSubmitExtraParameter'));
+ $configMock->expects($this->any())
+ ->method('canSubmitExtraParameter')
+ ->will($this->returnValue(true));
+ $paymentModel = Mage::getModel('ops/payment_openInvoiceNl');
+ $paymentModel->setConfig($configMock);
+ $params = $paymentModel->getMethodDependendFormFields($order);
+ foreach ($this->getOwnerParams() as $ownerParam) {
+ if ($ownerParam == 'OWNERZIP' || $ownerParam == 'ADDMATCH' || $ownerParam == 'ECOM_BILLTO_POSTAL_POSTALCODE') continue;
+ $this->assertArrayHasKey($ownerParam, $params);
+ }
+ foreach ($this->getShippingParams() as $shippingParam) {
+ if ($shippingParam == 'ECOM_SHIPTO_POSTAL_STREET_LINE2') continue;
+ $this->assertArrayHasKey($shippingParam, $params);
+ }
+
+
+ }
+
+ public function testGetFormFieldsEmptyWithNonExistingOrder()
+ {
+ $paymentModel = Mage::getModel('ops/payment_abstract');
+ $this->assertTrue(
+ is_array($paymentModel->getFormFields(null, array()))
+ );
+ $this->assertEquals(
+ 0, count($paymentModel->getFormFields(null, array()))
+ );
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testGetFormFieldsWithEmptyOrderPassedButExistingOrder()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethodInstance(Mage::getModel('ops/payment_cc'));
+ $order->setPayment($payment);
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract',
+ array('getMethodDependendFormFields', 'getOrder')
+ );
+ $paymentModel->expects($this->any())
+ ->method('getOrder')
+ ->will($this->returnValue($order));
+ $formFields = $paymentModel->getFormFields($order, array());
+ $this->assertArrayHasKey('PSPID', $formFields);
+ $this->assertArrayHasKey('SHASIGN', $formFields);
+ }
+
+ public function testGetFormFields()
+ {
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract', array('getMethodDependendFormFields')
+ );
+ $configMock = $this->getModelMock('ops/config', array('getPSPID'));
+ $configMock->expects($this->once())
+ ->method('getPSPID')
+ ->will($this->returnValue('NRMAGENTO'));
+ $this->replaceByMock('singleton', 'ops/config', $configMock);
+ $this->replaceByMock('model', 'ops/config', $configMock);
+ $helperMock = $this->getHelperMock('ops/payment', array('getShaSign'));
+ $helperMock->expects($this->any())
+ ->method('getSHASign')
+ ->with(
+ $this->anything(),
+ $this->anything(),
+ null
+ )
+ ->will($this->returnValue('SHA123'));
+ $this->replaceByMock('helper', 'ops/payment', $helperMock);
+ $requestMock = $this->getHelperMock('ops/payment_request', array('getConfig'));
+ $requestMock->expects($this->any())
+ ->method('getConfig')
+ ->will($this->returnValue($configMock));
+ $this->replaceByMock('helper', 'ops/payment_request', $requestMock);
+
+ $order = Mage::getModel('sales/order');
+ $address = Mage::getModel('sales/order_address');
+ $order->setBillingAddress($address);
+ $order->setShippingAddress($address);
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethodInstance(Mage::getModel('ops/payment_cc'));
+ $order->setPayment($payment);
+ $formFields = $paymentModel->getFormFields($order, array());
+ $this->assertArrayHasKey('PSPID', $formFields);
+ $this->assertArrayHasKey('SHASIGN', $formFields);
+ $this->assertArrayHasKey('ACCEPTURL', $formFields);
+ $this->assertArrayHasKey('DECLINEURL', $formFields);
+ $this->assertArrayHasKey('EXCEPTIONURL', $formFields);
+ $this->assertArrayHasKey('CANCELURL', $formFields);
+ $this->assertEquals('NRMAGENTO', $formFields['PSPID']);
+ $this->assertEquals('2d9f92d6f3955847ab2db427be75fe7eb0cde045', $formFields['SHASIGN']);
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testGetFormFieldsWithFormDependendFormFields()
+ {
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract', array('getMethodDependendFormFields')
+ );
+ $paymentModel->expects($this->any())
+ ->method('getMethodDependendFormFields')
+ ->will($this->returnValue(array('foo' => 'bla')));
+ $configMock = $this->getModelMock('ops/config', array('getPSPID'));
+ $configMock->expects($this->once())
+ ->method('getPSPID')
+ ->with(null)
+ ->will($this->returnValue('NRMAGENTO'));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+ $helperMock = $this->getHelperMock('ops/payment', array('getShaSign'));
+ $helperMock->expects($this->any())
+ ->method('getSHASign')
+ ->with(
+ $this->anything(),
+ $this->anything(),
+ null
+ )
+ ->will($this->returnValue('SHA123'));
+ $this->replaceByMock('helper', 'ops/payment', $helperMock);
+ $requestMock = $this->getHelperMock('ops/payment_request', array('getConfig'));
+ $requestMock->expects($this->any())
+ ->method('getConfig')
+ ->will($this->returnValue($configMock));
+ $this->replaceByMock('helper', 'ops/payment_request', $requestMock);
+
+ $order = Mage::getModel('sales/order')->load(15);
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethodInstance(Mage::getModel('ops/payment_cc'));
+ $order->setPayment($payment);
+ $formFields = $paymentModel->getFormFields($order, array());
+ $this->assertArrayHasKey('PSPID', $formFields);
+ $this->assertArrayHasKey('SHASIGN', $formFields);
+ $this->assertArrayHasKey('foo', $formFields);
+ $this->assertEquals('NRMAGENTO', $formFields['PSPID']);
+ $this->assertEquals(
+ '2d9f92d6f3955847ab2db427be75fe7eb0cde045', $formFields['SHASIGN']
+ );
+ $this->assertEquals('bla', $formFields['foo']);
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testGetFormFieldsWithStoreId()
+ {
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract', array('getMethodDependendFormFields')
+ );
+ $configMock = $this->getModelMock(
+ 'ops/config', array('getPSPID', 'getSHASign')
+ );
+ $configMock->expects($this->once())
+ ->method('getPSPID')
+ ->with(1)
+ ->will($this->returnValue('NRMAGENTO5'));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+
+ $helperMock = $this->getHelperMock('ops/payment', array('getShaSign'));
+
+ $helperMock->expects($this->any())
+ ->method('getSHASign')
+ ->with(
+ $this->anything(),
+ $this->anything(),
+ 1
+ )
+ ->will($this->returnValue('SHA987'));
+ $this->replaceByMock('helper', 'ops/payment', $helperMock);
+ $requestMock = $this->getHelperMock('ops/payment_request', array('getConfig'));
+ $requestMock->expects($this->any())
+ ->method('getConfig')
+ ->will($this->returnValue($configMock));
+ $this->replaceByMock('helper', 'ops/payment_request', $requestMock);
+
+ $order = Mage::getModel('sales/order')->load(15);
+ $payment = Mage::getModel('sales/order_payment');
+ $order->setStoreId(1);
+ $payment->setMethodInstance(Mage::getModel('ops/payment_cc'));
+ $order->setPayment($payment);
+ $formFields = $paymentModel->getFormFields($order, array());
+ $this->assertArrayHasKey('PSPID', $formFields);
+ $this->assertArrayHasKey('SHASIGN', $formFields);
+ $this->assertEquals('NRMAGENTO5', $formFields['PSPID']);
+ $this->assertEquals(
+ '0f119cdea2f8ddc0c852bab4765f12d3913982fc', $formFields['SHASIGN']
+ );
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testVoidWithExistingVoidTransactionLeadsToRedirect()
+ {
+ $helperMock = $this->getHelperMock('ops/directlink', array('checkExistingTransact'));
+ $helperMock
+ ->expects($this->any())
+ ->method('checkExistingTransact')
+ ->with(Netresearch_OPS_Model_Payment_Abstract::OPS_VOID_TRANSACTION_TYPE, 11)
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->getPayment()->setAdditionalInformation('status', 5);
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract',
+ array('canVoid')
+ );
+ $paymentModel->expects($this->any())
+ ->method('canVoid')
+ ->will($this->returnValue(true));
+
+
+ $dataHelperMock = $this->getHelperMock('ops/data', array('redirect'));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+
+ Mage::getSingleton('admin/session')->getMessages(true);
+ $noticeCountBefore = sizeof(
+ Mage::getSingleton('admin/session')->getItemsByType('error')
+ );
+ $paymentModel->void($order->getPayment());
+ $notices = Mage::getSingleton('admin/session')->getMessages()->getItemsByType(
+ 'error'
+ );
+ $noticeCountAfter = sizeof($notices);
+ $this->assertGreaterThan($noticeCountBefore, $noticeCountAfter);
+ $this->assertEquals(
+ $dataHelperMock->__('You already sent a void request. Please wait until the void request will be acknowledged.'),
+ current($notices)->getText()
+ );
+
+
+
+ }
+
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testVoidFailsWhenRequestThrowsException()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Abstract $paymentModel */
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract',
+ array('canVoid')
+ );
+ $paymentModel->expects($this->any())
+ ->method('canVoid')
+ ->will($this->returnValue(true));
+ $helperMock = $this->getHelperMock('ops/directlink', array('checkExistingTransact'));
+ $helperMock
+ ->expects($this->any())
+ ->method('checkExistingTransact')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+
+ $apiClientMock = $this->getModelMock(
+ 'ops/api_directlink', array('performRequest')
+ );
+ $exception = new Exception('Fake Request failed');
+ $apiClientMock->expects($this->any())
+ ->method('performRequest')
+ ->will(
+ $this->throwException($exception)
+ );
+ $this->replaceByMock('model', 'ops/api_directlink', $apiClientMock);
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->getPayment()->setAdditionalInformation('status', 5);
+ try {
+ $paymentModel->void($order->getPayment());
+ } catch (Exception $e) {
+ $this->assertEquals('Fake Request failed', $e->getMessage());
+ }
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testVoidFailsWhenStatusIsUnknown()
+ {
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract',
+ array('canVoid')
+ );
+ $paymentModel->expects($this->any())
+ ->method('canVoid')
+ ->will($this->returnValue(true));
+ $helperMock = $this->getHelperMock('ops/directlink', array('checkExistingTransact'));
+ $helperMock
+ ->expects($this->any())
+ ->method('checkExistingTransact')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+
+ $apiClientMock = $this->getModelMock(
+ 'ops/api_directlink', array('performRequest')
+ );
+ $apiClientMock->expects($this->any())
+ ->method('performRequest')
+ ->will(
+ $this->returnValue(
+ array(
+ 'STATUS' => 666
+ )
+ )
+ );
+ $this->replaceByMock('model', 'ops/api_directlink', $apiClientMock);
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->getPayment()->setAdditionalInformation('status', 5);
+ try {
+ $paymentModel->void($order->getPayment());
+ } catch (Exception $e) {
+ $this->assertEquals(5, $order->getPayment()->getAdditionalInformation('status'));
+ $helper = Mage::helper('ops/data');
+ $this->assertEquals($helper->__('Can not handle status %s.', 666), $e->getMessage());
+ }
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testVoidWithStatusVoidWaiting()
+ {
+ $txMock = $this->getModelMock('sales/order_payment_transaction', array('save'));
+ $this->replaceByMock('model', 'sales/order_payment_transaction', $txMock);
+
+ $dataHelperMock = $this->getHelperMock('ops/data', array('redirect'));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract',
+ array('canVoid')
+ );
+
+
+ $paymentModel->expects($this->any())
+ ->method('canVoid')
+ ->will($this->returnValue(true));
+ $helperMock = $this->getHelperMock('ops/directlink', array('checkExistingTransact'));
+ $helperMock
+ ->expects($this->any())
+ ->method('checkExistingTransact')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+
+ $apiClientMock = $this->getModelMock(
+ 'ops/api_directlink', array('performRequest')
+ );
+ $apiClientMock->expects($this->any())
+ ->method('performRequest')
+ ->will(
+ $this->returnValue(
+ array(
+ 'STATUS' => Netresearch_OPS_Model_Status::DELETION_WAITING,
+ 'PAYID' => '4711',
+ 'PAYIDSUB' => '0815'
+ )
+ )
+ );
+ $this->replaceByMock('model', 'ops/api_directlink', $apiClientMock);
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->getPayment()->setAdditionalInformation('status', 5);
+
+ $paymentModel->setInfoInstance($order->getPayment());
+ $paymentModel->void($order->getPayment());
+ $this->assertTrue($order->getPayment()->hasMessage());
+ $this->assertNotEmpty($order->getPayment()->getMessage());
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testVoidWithStatusVoidAccepted()
+ {
+ $dataHelperMock = $this->getHelperMock('ops/data', array('redirect'));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+
+ $paymentModel = $this->getModelMock(
+ 'ops/payment_abstract',
+ array('canVoid')
+ );
+
+
+ $txMock = $this->getModelMock('sales/order_payment_transaction', array('save'));
+ $this->replaceByMock('model', 'sales/order_payment_transaction', $txMock);
+
+ $paymentModel->expects($this->any())
+ ->method('canVoid')
+ ->will($this->returnValue(true));
+ $helperMock = $this->getHelperMock('ops/directlink', array('checkExistingTransact'));
+ $helperMock
+ ->expects($this->any())
+ ->method('checkExistingTransact')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+
+ $apiClientMock = $this->getModelMock(
+ 'ops/api_directlink', array('performRequest')
+ );
+ $apiClientMock->expects($this->any())
+ ->method('performRequest')
+ ->will(
+ $this->returnValue(
+ array(
+ 'STATUS' => Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED,
+ 'PAYID' => '4711',
+ 'PAYIDSUB' => '0815'
+ )
+ )
+ );
+ $this->replaceByMock('model', 'ops/api_directlink', $apiClientMock);
+ $order = Mage::getModel('sales/order')->load(11);
+ $order->getPayment()->setAdditionalInformation('status', 5);
+ $paymentModel->setInfoInstance($order->getPayment());
+ $paymentModel->void($order->getPayment());
+
+ $this->assertEquals(
+ Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED,
+ $order->getPayment()->getAdditionalInformation('status')
+ );
+
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testGetOpsHtmlAnswer()
+ {
+ $fakeQuote = new Varien_Object();
+ $fakeQuote->setId(42);
+
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->setMethods(array('getQuote'))
+ ->getMock();
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($fakeQuote));
+ $this->replaceByMock('singleton', 'checkout/session', $sessionMock);
+
+ $this->assertEquals('HTML', Mage::getModel('ops/payment_abstract')->getOpsHtmlAnswer());
+
+ $fakeQuote = new Varien_Object();
+ $fakeQuote->setId(null);
+ $sessionMock = $this->getModelMockBuilder('checkout/session')
+ ->disableOriginalConstructor() // This one removes session_start and other methods usage
+ ->setMethods(array('getQuote', 'getLastRealOrderId'))
+ ->getMock();
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($fakeQuote));
+
+ $sessionMock->expects($this->any())
+ ->method('getLastRealOrderId')
+ ->will($this->returnValue('100000020'));
+
+ $this->replaceByMock('singleton', 'checkout/session', $sessionMock);
+ $this->assertEquals('HTML', Mage::getModel('ops/payment_abstract')->getOpsHtmlAnswer());
+
+ $order = Mage::getModel('sales/order')->load(20);
+ $this->assertEquals('HTML', Mage::getModel('ops/payment_abstract')->getOpsHtmlAnswer($order->getPayment()));
+ }
+
+ /**
+ * @loadFixture orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage The payment review action is unavailable.
+ */
+ public function testAcceptPaymentNotSupportedState()
+ {
+ $payment = Mage::getModel('payment/info');
+ $payment->setAdditionalInformation('status', 99);
+ Mage::getModel('ops/payment_abstract')->acceptPayment($payment);
+ }
+
+
+ /**
+ * @loadFixture orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage The order can not be accepted via Magento. For the actual status of the payment check the Ingenico ePayments backend.
+ */
+ public function testAcceptPaymentSupportedState()
+ {
+ $order = Mage::getModel('sales/order')->load(25);
+ $order->getPayment()->setAdditionalInformation('status', 57);
+
+ $result = Mage::getModel('ops/payment_abstract')->acceptPayment($order->getPayment());
+ }
+
+ /**
+ * @loadFixture orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage The payment review action is unavailable.
+ */
+ public function testDenyPaymentNotSupportedState()
+ {
+ $payment = Mage::getModel('payment/info');
+ $payment->setAdditionalInformation('status', 99);
+ Mage::getModel('ops/payment_abstract')->denyPayment($payment);
+ }
+
+
+ /**
+ * @loadFixture orders.yaml
+ */
+ public function testDenyPaymentSupportedState()
+ {
+ $order = Mage::getModel('sales/order')->load(25);
+ $order->getPayment()->setAdditionalInformation('status', 57);
+
+ $result = Mage::getModel('ops/payment_abstract')->denyPayment($order->getPayment());
+ $this->assertTrue($result);
+ }
+
+
+ /**
+ * @loadFixture orders.yaml
+ */
+ public function testCanReviewPaymentFalse()
+ {
+ $order = Mage::getModel('sales/order')->load(25);
+ $order->getPayment()->setAdditionalInformation('status', 5);
+ $this->assertFalse(Mage::getModel('ops/payment_abstract')->canReviewPayment($order->getPayment()));
+ }
+
+ /**
+ * @loadFixture orders.yaml
+ */
+ public function testCanReviewPaymentTrue()
+ {
+ $order = Mage::getModel('sales/order')->load(25);
+ $order->getPayment()->setAdditionalInformation('status', 57);
+ $this->assertTrue(Mage::getModel('ops/payment_abstract')->canReviewPayment($order->getPayment()));
+ }
+
+ public function testGetFrontendGateWay()
+ {
+ $gateway = Mage::getModel('ops/config')->getFrontendGatewayPath();
+ $payment = Mage::getModel('ops/payment_cc');
+ $url = $payment->getFrontendGateWay();
+ $this->assertTrue(strpos($url, '_utf8') >= 0);
+ $this->assertEquals($gateway, $url);
+ }
+
+ public function testSetEncoding()
+ {
+ $payment = Mage::getModel('ops/payment_cc');
+ $payment->setEncoding('test_foo');
+
+ $this->assertEquals('test_foo', $payment->getEncoding());
+ }
+
+ protected function getOwnerParams()
+ {
+ return $ownerParams = array(
+ 'OWNERADDRESS',
+ 'OWNERTOWN',
+ 'OWNERZIP',
+ 'OWNERTELNO',
+ 'OWNERCTY',
+ 'ADDMATCH',
+ 'ECOM_BILLTO_POSTAL_POSTALCODE',
+ );
+ }
+
+ protected function getShippingParams()
+ {
+ $paramValues = array(
+ 'ECOM_SHIPTO_POSTAL_NAME_FIRST',
+ 'ECOM_SHIPTO_POSTAL_NAME_LAST',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE2',
+ 'ECOM_SHIPTO_POSTAL_COUNTRYCODE',
+ 'ECOM_SHIPTO_POSTAL_CITY',
+ 'ECOM_SHIPTO_POSTAL_POSTALCODE'
+ );
+
+ return $paramValues;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/expectations/paymentMethods.yaml b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/expectations/paymentMethods.yaml
new file mode 100644
index 0000000..e35461a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/expectations/paymentMethods.yaml
@@ -0,0 +1,279 @@
+ops_3XCB:
+ pm: 3XCB
+ brand: 3XCB
+ops_CreditCard:
+ pm: CreditCard
+ brand: AIRPLUS
+ops_CreditCard:
+ pm: CreditCard
+ brand: American Express
+ops_CreditCard:
+ pm: CreditCard
+ brand: Aurore
+ops_CreditCard:
+ pm: CreditCard
+ brand: CB
+ops_CreditCard:
+ pm: CreditCard
+ brand: Cofinoga
+ops_CreditCard:
+ pm: CreditCard
+ brand: Dankort
+ops_CreditCard:
+ pm: CreditCard
+ brand: Diners
+ops_CreditCard:
+ pm: CreditCard
+ brand: JCB
+ops_Creditcard:
+ pm: Creditcard
+ brand: Laser
+ops_CreditCard:
+ pm: CreditCard
+ brand: MaestroUK
+ops_CreditCard:
+ pm: CreditCard
+ brand: MasterCard
+ops_CreditCard:
+ pm: CreditCard
+ brand: UATP
+ops_CreditCard:
+ pm: CreditCard
+ brand: VISA
+ops_BCMC:
+ pm: CreditCard
+ brand: BCMC
+ops_CreditCard:
+ pm: CreditCard
+ brand: Maestro
+ops_PostFinance:
+ pm: PostFinance Card
+ brand: PostFinance Card
+ops_CreditCard:
+ pm: CreditCard
+ brand: PRIVILEGE
+ops_UNEUROCOM:
+ pm: UNEUROCOM
+ brand: UNEUROCOM
+ops_AmazonCheckout:
+ pm: Amazon Checkout
+ brand: Amazon Checkout
+ops_Belfius:
+ pm: Belfius Direct Net
+ brand: Belfius Direct Net
+ops_cashticket:
+ pm: cashticket
+ brand: cashticket
+ops_cbcOnline:
+ pm: CBC Online
+ brand: CBC Online
+ops_directEbanking:
+ pm: DirectEbanking
+ brand: Sofort Uberweisung
+ops_directEbankingAT:
+ pm: DirectEbankingAT
+ brand: DirectEbankingAT
+ops_directEbankingBE:
+ pm: DirectEbankingBE
+ brand: DirectEbankingBE
+ops_directEbankingCH:
+ pm: DirectEbankingCH
+ brand: DirectEbankingCH
+ops_directEbankingDE:
+ pm: DirectEbankingDE
+ brand: DirectEbankingDE
+ops_directEbankingFR:
+ pm: DirectEbankingFR
+ brand: DirectEbankingFR
+ops_directEbankingGB:
+ pm: DirectEbankingGB
+ brand: DirectEbankingGB
+ops_directEbankingIT:
+ pm: DirectEbankingIT
+ brand: DirectEbankingIT
+ops_directEbankingNL:
+ pm: DirectEbankingNL
+ brand: DirectEbankingNL
+ops_EBS_AXIS:
+ pm: EBS_AXIS
+ brand: EBS_AXIS
+ops_EBS_BC:
+ pm: EBS_BC
+ brand: EBS_BC
+ops_EBS_CB:
+ pm: EBS_CB
+ brand: EBS_CB
+ops_EBS_CORP:
+ pm: EBS_CORP
+ brand: EBS_CORP
+ops_EBS_DC:
+ pm: EBS_DC
+ brand: EBS_DC
+ops_EBS_FED:
+ pm: EBS_FED
+ brand: EBS_FED
+ops_EBS_HDFC:
+ pm: EBS_HDFC
+ brand: EBS_HDFC
+ops_EBS_HYDERABAD:
+ pm: EBS_HYDERABAD
+ brand: EBS_HYDERABAD
+ops_EBS_IB:
+ pm: EBS_IB
+ brand: EBS_IB
+ops_EBS_ICASH:
+ pm: EBS_ICASH
+ brand: EBS_ICASH
+ops_EBS_ICICI:
+ pm: EBS_ICICI
+ brand: EBS_ICICI
+ops_EBS_INDIA:
+ pm: EBS_INDIA
+ brand: EBS_INDIA
+ops_EBS_ITZ:
+ pm: EBS_ITZ
+ brand: EBS_ITZ
+ops_EBS_JK:
+ pm: EBS_JK
+ brand: EBS_JK
+ops_EBS_KARNATAKA:
+ pm: EBS_KARNATAKA
+ brand: EBS_KARNATAKA
+ops_EBS_KOTAK:
+ pm: EBS_KOTAK
+ brand: EBS_KOTAK
+ops_EBS_MYSORE:
+ pm: EBS_MYSORE
+ brand: EBS_MYSORE
+ops_EBS_TRAVANCORE:
+ pm: EBS_TRAVANCORE
+ brand: EBS_TRAVANCORE
+ops_eDankort:
+ pm: eDankort
+ brand: eDankort
+ops_eps:
+ pm: EPS
+ brand: EPS
+ops_FidorPay:
+ pm: FidorPay
+ brand: FidorPay
+ops_fortisPayButton:
+ pm: Fortis Pay Button
+ brand: Fortis Pay Button
+ops_giroPay:
+ pm: giropay
+ brand: giropay
+ops_Masterpass:
+ pm: Masterpass
+ brand: Masterpass
+ops_iDeal:
+ pm: iDEAL
+ brand: iDEAL
+ops_ingHomePay:
+ pm: ING HomePay
+ brand: ING HomePay
+ops_kbcOnline:
+ pm: KBC Online
+ brand: KBC Online
+ops_paysafecard:
+ pm: paysafecard
+ brand: paysafecard
+ops_postFinanceEFinance:
+ pm: PostFinance e-finance
+ brand: PostFinance e-finance
+ops_directDebitsAt:
+ pm: Direct Debits AT
+ brand: Direct Debits AT
+ops_directDebitsDe:
+ pm: Direct Debits DE
+ brand: Direct Debits DE
+ops_directDebitsNl:
+ pm: Direct Debits NL
+ brand: Direct Debits NL
+ops_bankTransfer:
+ pm: "Bank transfer"
+ brand: "Bank transfer"
+ops_bankTransferBe:
+ pm: Bank transfer BE
+ brand: Bank transfer BE
+ops_bankTransferDe:
+ pm: Bank transfer DE
+ brand: Bank transfer DE
+ops_bankTransferFr:
+ pm: Bank transfer FR
+ brand: Bank transfer FR
+ops_bankTransferNl:
+ pm: Bank transfer NL
+ brand: Bank transfer NL
+ops_installmentsDe:
+ pm: Installments DE
+ brand: Installments DE
+ops_installmentsDk:
+ pm: Installments DK
+ brand: Installments DK
+ops_installmentsFi:
+ pm: Installments FI
+ brand: Installments FI
+ops_installmentsNl:
+ pm: Installments NL
+ brand: Installments NL
+ops_installmentsNo:
+ pm: Installments NO
+ brand: Installments NO
+ops_installmentsSe:
+ pm: Installments SE
+ brand: Installments SE
+ops_openInvoiceDe:
+ pm: Open Invoice DE
+ brand: Open Invoice DE
+ops_openInvoiceDk:
+ pm: Open Invoice DK
+ brand: Open Invoice DK
+ops_openInvoiceFi:
+ pm: Open Invoice FI
+ brand: Open Invoice FI
+ops_openInvoiceNl:
+ pm: Open Invoice NL
+ brand: Open Invoice NL
+ops_openInvoiceAT:
+ pm: Open Invoice AT
+ brand: Open Invoice AT
+ops_openInvoiceNo:
+ pm: Open Invoice NO
+ brand: Open Invoice NO
+ops_openInvoiceSe:
+ pm: Open Invoice SE
+ brand: Open Invoice SE
+ops_cod:
+ pm: Payment on Delivery
+ brand: Payment on Delivery
+ops_interSolve:
+ pm: InterSolve
+ brand: InterSolve
+ops_pingPing:
+ pm: PingPing
+ brand: PingPing
+ops_tunz:
+ pm: TUNZ
+ brand: TUNZ
+ops_cashEX:
+ pm: cashEX
+ brand: cashEX
+ops_cashU:
+ pm: cashU
+ brand: cashU
+ops_cashUDirect:
+ pm: cashU Direct
+ brand: cashU Direct
+ops_Payble:
+ pm: Payble
+ brand: Payble
+ops_paypal:
+ pm: PAYPAL
+ brand: PAYPAL
+ops_wallie:
+ pm: Wallie
+ brand: Wallie
+ops_belfiusDirectNet:
+ pm: Belfius Direct Net
+ brand: Belfius Direct Net
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/fixtures/orders.yaml
new file mode 100644
index 0000000..fc9499c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/AbstractTest/fixtures/orders.yaml
@@ -0,0 +1,135 @@
+tables:
+ sales/order:
+ - entity_id: 25
+ increment_id: 100000025
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 10
+
+ - entity_id: 26
+ increment_id: 100000026
+ shipping_address_id: 43
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'payment_review'
+ status: 'payment_review'
+ quote_id: 26
+
+ - entity_id: 27
+ increment_id: 100000027
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+
+
+ sales/quote:
+ - entity_id: 25
+ parent_id: 25
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 26
+ parent_id: 26
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 27
+ parent_id: 27
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+
+
+ sales/quote_payment:
+ - payment_id: 25
+ quote_id: 25
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+
+ - payment_id: 26
+ quote_id: 26
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+
+ - payment_id: 27
+ quote_id: 27
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:9:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+
+
+
+ sales/order_payment:
+ - entity_id: 25
+ parent_id: 25
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+ method: 'ops_iDeal'
+
+ - entity_id: 26
+ parent_id: 26
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+ method: 'ops_iDeal'
+
+ - entity_id: 27
+ parent_id: 27
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+ method: 'ops_iDeal'
+
+
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 25
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 26
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/BancontactTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/BancontactTest.php
new file mode 100644
index 0000000..01dce0c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/BancontactTest.php
@@ -0,0 +1,81 @@
+model = Mage::getModel('ops/payment_bancontact');
+ $this->model->setInfoInstance(Mage::getModel('payment/info'));
+ }
+
+ public function testCanCapturePartial()
+ {
+ $this->assertTrue($this->model->canCapturePartial());
+ }
+
+ public function testGetOpsCode()
+ {
+ $this->assertEquals('CreditCard', $this->model->getOpsCode());
+ }
+
+ public function testGetOpsBrand()
+ {
+ $this->assertEquals('BCMC', $this->model->getOpsBrand());
+ }
+
+ /**
+ * @loadFixture ../../../../var/fixtures/orders.yaml
+ */
+ public function testGetMethodDependendFormFields()
+ {
+ $order = Mage::getModel('sales/order')->load(32);
+
+ $sessionMock = $this->getModelMockBuilder('core/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'core/session', $sessionMock);
+
+ $sessionMock = $this->getModelMockBuilder('customer/session')
+ ->disableOriginalConstructor()
+ ->setMethods(null)
+ ->getMock();
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ $this->model->getInfoInstance()->setAdditionalInformation('DEVICE', Netresearch_OPS_Helper_MobileDetect::DEVICE_TYPE_MOBILE);
+ $formFields = $this->model->getMethodDependendFormFields($order, null);
+ $this->assertEquals(Netresearch_OPS_Helper_MobileDetect::DEVICE_TYPE_MOBILE, $formFields['DEVICE']);
+ }
+
+
+ public function testAssignData()
+ {
+ $infoInstance = Mage::getModel('sales/quote_payment');
+
+ $helperMock = new Varien_Object(
+ array('device_type' => Netresearch_OPS_Helper_MobileDetect::DEVICE_TYPE_MOBILE)
+ );
+
+ $paymentInstance = Mage::getModel('ops/payment_bancontact');
+ $paymentInstance->setMobileDetectHelper($helperMock)
+ ->setInfoInstance($infoInstance);
+
+ $paymentInstance->assignData(array());
+ $additionalInformation = $infoInstance->getData('additional_information');
+
+ $this->assertEquals(Netresearch_OPS_Helper_MobileDetect::DEVICE_TYPE_MOBILE, $additionalInformation['DEVICE']);
+ }
+
+ /**
+ * @Test
+ */
+ public function testGetMobileDetectHelper()
+ {
+ $this->assertTrue($this->model->getMobileDetectHelper() instanceof Netresearch_OPS_Helper_MobileDetect);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/BancontactTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Model/Payment/BancontactTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/CcTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/CcTest.php
new file mode 100644
index 0000000..1b85e06
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/CcTest.php
@@ -0,0 +1,213 @@
+_model = Mage::getModel('ops/payment_cc');
+ $this->_payment = ObjectHandler::getObject('quoteBeforeSaveOrder')->getPayment();
+ }
+
+ public function testBrand()
+ {
+ $this->_payment->setAdditionalInformation('CC_BRAND', 'VISA');
+ $this->assertEquals('VISA', $this->_model->getOpsBrand($this->_payment), 'VISA should have brand VISA');
+ $this->assertEquals('CreditCard', $this->_model->getOpsCode($this->_payment), 'VISA should be a CreditCard');
+ $this->assertTrue($this->_model->hasBrandAliasInterfaceSupport($this->_payment), 'VISA should support alias interface');
+
+ $this->_payment->setAdditionalInformation('CC_BRAND', 'UNEUROCOM');
+ $this->assertEquals('UNEUROCOM', $this->_model->getOpsBrand($this->_payment), 'UNEUROCOM should have brand UNEUROCOM');
+ $this->assertEquals('UNEUROCOM', $this->_model->getOpsCode($this->_payment), 'UNEUROCOM should have code UNEUROCOM');
+ $this->assertFalse($this->_model->hasBrandAliasInterfaceSupport($this->_payment), 'UNEUROCOM should NOT support alias interface');
+
+ $this->_payment->setAdditionalInformation('CC_BRAND', 'PostFinance card');
+ $this->assertEquals('PostFinance card', $this->_model->getOpsBrand($this->_payment), 'PostFinance Card should have brand "PostFinance card"');
+ $this->assertEquals('PostFinance Card', $this->_model->getOpsCode($this->_payment), 'PostFinance Card should have code "PostFinance Card"');
+ $this->assertFalse($this->_model->hasBrandAliasInterfaceSupport($this->_payment), 'PostFinance Card should NOT support alias interface');
+
+ $this->_payment->setAdditionalInformation('CC_BRAND', 'PRIVILEGE');
+ $this->assertEquals('PRIVILEGE', $this->_model->getOpsBrand($this->_payment), 'PRIVILEGE should have brand PRIVILEGE');
+ $this->assertEquals('CreditCard', $this->_model->getOpsCode($this->_payment), 'PRIVILEGE should be a CreditCard');
+ $this->assertFalse($this->_model->hasBrandAliasInterfaceSupport($this->_payment), 'PRIVILEGE should NOT support alias interface');
+ }
+
+ public function testOrderPlaceRedirectUrl()
+ {
+ $this->_model->setInfoInstance($this->_payment);
+ $this->_payment->setAdditionalInformation('CC_BRAND', 'VISA');
+ $this->assertFalse($this->_model->getOrderPlaceRedirectUrl($this->_payment), 'VISA should NOT require a redirect after checkout');
+
+ $this->_payment->setAdditionalInformation('CC_BRAND', 'VISA');
+ $this->_payment->setAdditionalInformation('HTML_ANSWER', 'BASE64ENCODEDSTRING');
+ $this->assertInternalType('string', $this->_model->getOrderPlaceRedirectUrl($this->_payment), 'If Brand is VIA and HTML_ANSWER isset, a redirect should happen after checkout');
+
+ $this->_payment->setAdditionalInformation('CC_BRAND', 'PRIVILEGE');
+ $this->assertInternalType('string', $this->_model->getOrderPlaceRedirectUrl($this->_payment), 'PRIVILEGE should require a redirect after checkout');
+
+ }
+
+ public function testIsZeroAmountAuthorizationAllowed()
+ {
+ $model = new Netresearch_OPS_Model_Payment_Cc();
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment_services/ops/payment_action', Netresearch_OPS_Model_Payment_Abstract::ACTION_AUTHORIZE_CAPTURE);
+ $store->setConfig('payment/ops_cc/zero_amount_checkout', 0);
+ $this->assertFalse($model->isZeroAmountAuthorizationAllowed());
+
+ $store->resetConfig();
+ $store->setConfig('payment_services/ops/payment_action', Netresearch_OPS_Model_Payment_Abstract::ACTION_AUTHORIZE_CAPTURE);
+ $store->setConfig('payment/ops_cc/zero_amount_checkout', 1);
+ $this->assertFalse($model->isZeroAmountAuthorizationAllowed());
+
+ $store->resetConfig();
+ $store->setConfig('payment_services/ops/payment_action', Netresearch_OPS_Model_Payment_Abstract::ACTION_AUTHORIZE);
+ $store->setConfig('payment/ops_cc/zero_amount_checkout', 0);
+ $this->assertFalse($model->isZeroAmountAuthorizationAllowed());
+ }
+
+ public function testZeroAmountAuthAllowed()
+ {
+ $model = new Netresearch_OPS_Model_Payment_Cc();
+ $store = Mage::app()->getStore(0)->load(0);
+ $configMock = $this->getModelMock('ops/config', array('getConfigData'));
+ $configMock->expects($this->once())
+ ->method('getConfigData')
+ ->with('payment_action')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::ACTION_AUTHORIZE));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+ $store->setConfig('payment/ops_cc/zero_amount_checkout', 1);
+ $this->assertTrue($model->isZeroAmountAuthorizationAllowed());
+ }
+
+
+
+ public function testIsApplicableToQuoteTrue()
+ {
+ $helperMock = $this->getHelperMock('ops/version', array('canUseApplicableForQuote'));
+ $helperMock->expects($this->any())
+ ->method('canUseApplicableForQuote')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/version', $helperMock);
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setBaseGrandTotal(0.0);
+ $this->assertTrue($this->_model->isApplicableToQuote($quote, 1));
+
+ }
+
+ public function testIsApplicableToQuoteTrueWithZeroAmount()
+ {
+ $versionInfo = Mage::getVersionInfo();
+ if ((array_key_exists('minor', $versionInfo))
+ && (Mage::getEdition() === Mage::EDITION_COMMUNITY && $versionInfo['minor'] > '7')
+ || (Mage::getEdition() === Mage::EDITION_ENTERPRISE && $versionInfo['minor'] > '13')
+ )
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $configMock = $this->getModelMock('ops/config', array('getConfigData'));
+ $configMock->expects($this->once())
+ ->method('getConfigData')
+ ->with('payment_action')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::ACTION_AUTHORIZE));
+ $this->replaceByMock('model', 'ops/config', $configMock);
+ $store->setConfig('payment/ops_cc/zero_amount_checkout', 1);
+
+
+ $helperMock = $this->getHelperMock('ops/version', array('canUseApplicableForQuote'));
+ $helperMock->expects($this->any())
+ ->method('canUseApplicableForQuote')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/version', $helperMock);
+
+ $quote = $this->getModelMock('sales/quote', array('getItemsCount', 'getBaseGrandTotal', 'isNominal'));
+ $quote->expects($this->once())
+ ->method('getItemsCount')
+ ->will($this->returnValue(1));
+ $quote->expects($this->any())
+ ->method('getBaseGrandTotal')
+ ->will($this->returnValue(0.0));
+ $quote->expects($this->any())
+ ->method('isNominal')
+ ->will($this->returnValue(false));
+ $this->assertTrue($this->_model->isApplicableToQuote($quote, 128));
+ }
+ }
+
+ public function testIsApplicableToQuoteFeatureModelTrue()
+ {
+ $versionInfo = Mage::getVersionInfo();
+ if ((array_key_exists('minor', $versionInfo))
+ && (Mage::getEdition() === Mage::EDITION_COMMUNITY && $versionInfo['minor'] > '7')
+ || (Mage::getEdition() === Mage::EDITION_ENTERPRISE && $versionInfo['minor'] > '13')
+ )
+ {
+ $featureModelMock = $this->getModelMock('ops/payment_features_zeroAmountAuth', array('isCCAndZeroAmountAuthAllowed'));
+ $featureModelMock->expects($this->any())
+ ->method('isCCAndZeroAmountAuthAllowed')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/payment_features_zeroAmountAuth', $featureModelMock);
+
+ $helperMock = $this->getHelperMock('ops/version', array('canUseApplicableForQuote'));
+
+ $helperMock->expects($this->any())
+ ->method('canUseApplicableForQuote')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('helper', 'ops/version', $helperMock);
+
+ $quote = Mage::getModel('sales/quote');
+ $this->assertTrue($this->_model->isApplicableToQuote($quote, '1'));
+ }
+ }
+
+ public function testGetFeatureModel()
+ {
+ $this->assertTrue($this->_model->getFeatureModel() instanceof Netresearch_OPS_Model_Payment_Features_ZeroAmountAuth);
+ }
+
+ public function testSetCanCapture()
+ {
+ $ccPaymentObject = Mage::getModel('ops/payment_cc');
+ $this->assertTrue($ccPaymentObject->canCapture());
+
+ $ccPaymentObject->setCanCapture(false);
+ $this->assertFalse($ccPaymentObject->canCapture());
+ }
+
+ public function testGetOpsBrand()
+ {
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setAdditionalInformation('CC_BRAND', 'VISA');
+ $quote = $this->getModelMock('sales/quote', array('getPayment'));
+ $quote->expects($this->any())
+ ->method('getPayment')
+ ->will($this->returnValue($payment));
+ $quote->setId(1);
+ $checkoutSessionMock = $this->getModelMock('checkout/session', array('getQuote', 'init', 'save'));
+ $checkoutSessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($quote));
+ $this->replaceByMock('singleton', 'checkout/session', $checkoutSessionMock);
+ $this->assertEquals('VISA', $this->_model->getOpsBrand(null));
+
+ }
+
+ public function testIsAvailable()
+ {
+ $helperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $helperMock->expects($this->once())
+ ->method('isAdminSession')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+ $quote = Mage::getModel('sales/quote');
+ $quote->setItemsCount(0);
+ $this->assertFalse($this->_model->isAvailable($quote));
+ $quote->setItemsCount(500);
+ $this->assertFalse($this->_model->isAvailable($quote));
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/ChinaUnionPayTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/ChinaUnionPayTest.php
new file mode 100644
index 0000000..06e8a75
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/ChinaUnionPayTest.php
@@ -0,0 +1,47 @@
+model = Mage::getModel('ops/payment_chinaUnionPay');
+ $this->model->setInfoInstance(Mage::getModel('payment/info'));
+ }
+
+ /**
+ * assure that CUP can not capture partial, because invoice is always created on feedback in this case
+ */
+ public function testCanCapturePartial()
+ {
+ $this->assertFalse($this->model->canCapturePartial());
+ }
+
+ public function testGetOpsCode()
+ {
+ $this->assertEquals('PAYDOL_UPOP', $this->model->getOpsCode());
+ }
+
+ public function testGetOpsBrand()
+ {
+ $this->assertEquals('UnionPay', $this->model->getOpsBrand());
+ }
+
+
+ public function testCanRefundPartialPerInvoice()
+ {
+ $this->assertFalse($this->model->canRefundPartialPerInvoice());
+ }
+
+ public function testGetPaymentAction()
+ {
+ $this->assertEquals(
+ Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE,
+ $this->model->getPaymentAction()
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/DebitcardTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/DebitcardTest.php
new file mode 100644
index 0000000..4b8ad20
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/DebitcardTest.php
@@ -0,0 +1,53 @@
+
+ */
+?>
+model = Mage::getModel('ops/payment_debitcard');
+ }
+
+ public function testGetOpsCode()
+ {
+ $this->assertEquals('CreditCard', $this->model->getOpsCode());
+ }
+
+ public function testGetRequestParamsHelper()
+ {
+ $this->assertTrue($this->model->getRequestParamsHelper() instanceof Netresearch_OPS_Helper_Debitcard);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectDebitTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectDebitTest.php
new file mode 100644
index 0000000..cad5875
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectDebitTest.php
@@ -0,0 +1,23 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Model_Payment_DirectDebitTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+
+ public function testGetOrderPlaceRedirectUrl()
+ {
+ $this->assertFalse(
+ Mage::getModel('ops/payment_directDebit')->getOrderPlaceRedirectUrl(
+ )
+ );
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectEbankingTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectEbankingTest.php
new file mode 100644
index 0000000..a552aa4
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectEbankingTest.php
@@ -0,0 +1,19 @@
+ 'Sofort Uberweisung',
+ );
+ $payment = Mage::getModel('sales/order_payment');
+ $infoInstance = new Varien_Object();
+
+ $method = Mage::getModel('ops/payment_directEbanking');
+ $method->setInfoInstance(Mage::getModel('sales/quote_payment'));
+ $method = $method->assignData($data);
+ $this->assertEquals($method->getOpsBrand(), 'DirectEbanking');
+ $this->assertEquals($method->getOpsCode(), 'DirectEbanking');
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectLinkTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectLinkTest.php
new file mode 100644
index 0000000..15d964f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/DirectLinkTest.php
@@ -0,0 +1,475 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Model_Payment_DirectLinkTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $testObjects = array();
+
+
+ public function setUp()
+ {
+ parent::setUp();
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setAdditionalInformation('CC_BRAND', 'VISA')
+ ->setMethod('ops_cc');
+ $this->testObjects[] = Mage::getModel('ops/payment_cc')->setInfoInstance($payment);
+ $payment2 = clone($payment);
+ $payment2->setMethod('ops_directDebit');
+ $this->testObjects[] = Mage::getModel('ops/payment_directDebit')->setInfoInstance($payment2);
+ }
+
+
+ public function testInstanceOfAbstractPayment()
+ {
+ foreach ($this->testObjects as $testObject) {
+ $this->assertTrue($testObject instanceof Netresearch_OPS_Model_Payment_Abstract);
+ }
+ }
+
+
+ public function testGetConfigPaymentActionReturnsMageAuthorizeWithOrderIdAsMerchRef()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference', 'getPaymentAction', 'getInlinePaymentCcTypes'));
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID));
+ $configMock->expects($this->any())
+ ->method('getPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE));
+ $configMock->expects($this->any())
+ ->method('getInlinePaymentCcTypes')
+ ->will($this->returnValue(array('VISA')));
+ foreach ($this->testObjects as $testObject) {
+ $testObject->setConfig($configMock);
+ $this->assertEquals(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE, $testObject->getConfigPaymentAction());
+ }
+ }
+
+ public function testGetConfigPaymentActionReturnsAuthorizeStringWithQuoteIdAsMerchRef()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference', 'getPaymentAction'));
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID));
+ $configMock->expects($this->any())
+ ->method('getPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE));
+ foreach ($this->testObjects as $testObject) {
+ $testObject->setConfig($configMock);
+ $this->assertEquals(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE, $testObject->getConfigPaymentAction());
+ }
+ }
+
+
+ public function testGetConfigPaymentActionReturnsMageAuthorizeCaptureWithOrderIdAsMerchRef()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference', 'getPaymentAction', 'getInlinePaymentCcTypes'));
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID));
+ $configMock->expects($this->any())
+ ->method('getPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE));
+ $configMock->expects($this->any())
+ ->method('getInlinePaymentCcTypes')
+ ->will($this->returnValue(array('VISA')));
+
+ foreach ($this->testObjects as $testObject) {
+ $testObject->setConfig($configMock);
+ $this->assertEquals(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE, $testObject->getConfigPaymentAction());
+ }
+ }
+
+ public function testGetConfigPaymentActionReturnsAuthorizeCaptureStringForDirectSaleWithQuoteIdAsMerchRef()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference', 'getPaymentAction'));
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID));
+ $configMock->expects($this->any())
+ ->method('getPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE));
+ foreach ($this->testObjects as $testObject) {
+ $testObject->setConfig($configMock);
+ $this->assertEquals(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE, $testObject->getConfigPaymentAction());
+ }
+ }
+
+ public function testIsInitializeNeededReturnsFalse()
+ {
+
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference'));
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID));
+ foreach ($this->testObjects as $testObject) {
+ $testObject->setConfig($configMock);
+ $this->assertFalse($testObject->isInitializeNeeded());
+ }
+ }
+
+ public function testAuthorize()
+ {
+ $configMock = $this->getConfigMockWithOrderId();
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+
+ $fakeQuote = $this->getFakeQuote();
+ $quoteHelperMock = $this->getQuoteHelperMock($fakeQuote);
+
+ $testMock = $this->getModelMock('ops/payment_directDebit', array('confirmPayment'));
+
+ $dataHelperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $dataHelperMock->expects($this->once())
+ ->method('isAdminSession')
+ ->will($this->returnValue(true));
+ $testMock->setDataHelper($dataHelperMock);
+
+ $testMock->setQuoteHelper($quoteHelperMock);
+ $testMock->expects($this->once())
+ ->method('confirmPayment')
+ ->with($fakeOrder, $fakeQuote, $payment);
+ $testMock->setConfig($configMock);
+ $testMock->authorize($payment, 100);
+ }
+
+ public function testAuthorizeWithInlineCc()
+ {
+ $configMock = $this->getConfigMockWithOrderId();
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+ $fakeCc = $this->getModelMock('ops/payment_cc', array('hasBrandAliasInterfaceSupport'));
+ $fakeCc->expects($this->once())
+ ->method('hasBrandAliasInterfaceSupport')
+ ->will($this->returnValue(true));
+// $fakeCc->expects($this->once())
+// ->method('getInfoInstance')
+// ->will($this->returnValue($payment));
+ $payment->setMethodInstance($fakeCc);
+ $fakeCc->setInfoInstance($payment);
+ $fakeQuote = $this->getFakeQuote();
+ $quoteHelperMock = $this->getQuoteHelperMock($fakeQuote);
+
+ $testMock = $this->getModelMock('ops/payment_cc', array('confirmPayment', 'hasBrandAliasInterfaceSupport'));
+ $testMock->setQuoteHelper($quoteHelperMock);
+ $testMock->expects($this->once())
+ ->method('confirmPayment')
+ ->with($fakeOrder, $fakeQuote, $payment);
+ $testMock->expects($this->any())
+ ->method('hasBrandAliasInterfaceSupport')
+ ->will($this->returnValue(true));
+ ;
+ $testMock->setInfoInstance($payment);
+ $testMock->setConfig($configMock);
+ $testMock->authorize($payment, 100);
+ }
+
+
+ public function testConfirmPaymentWithResponse()
+ {
+ $configMock = $this->getConfigMockWithOrderId();
+ /** @var Mage_Sales_Model_Order $fakeOrder */
+ $fakeOrder = $this->getFakeOrder();
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $this->getFakePayment($fakeOrder);
+
+ $fakeQuote = $this->getFakeQuote();
+ $quoteHelperMock = $this->getQuoteHelperMock($fakeQuote);
+ /** @var Netresearch_OPS_Model_Payment_DirectDebit $testMock */
+ $testMock = $this->getModelMock('ops/payment_directDebit', array('handleAdminPayment', 'performPreDirectLinkCallActions', 'performPostDirectLinkCallActions'));
+ $testMock->setInfoInstance($payment);
+ $dataHelperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $dataHelperMock->expects($this->once())
+ ->method('isAdminSession')
+ ->will($this->returnValue(true));
+ $testMock->setDataHelper($dataHelperMock);
+
+ $requestParams = array('ORDERID' => '123');
+ $requestParamsHelperMock = $this->getHelperMock('ops/directDebit', array('getDirectLinkRequestParams'));
+
+ $requestParamsHelperMock->expects($this->once())
+ ->method('getDirectLinkRequestParams')
+ ->with($fakeQuote, $fakeOrder, $payment)
+ ->will($this->returnValue($requestParams));
+ $testMock->setRequestParamsHelper($requestParamsHelperMock);
+
+ $response = array('PAYID' => 4711, 'ORDERID' => '123', 'STATUS' => 5);
+ $directLinkHelperMock = $this->getHelperMock('ops/directlink', array('performDirectLinkRequest'));
+ $directLinkHelperMock->expects($this->once())
+ ->method('performDirectLinkRequest')
+ ->with($fakeQuote, $requestParams, 0)
+ ->will($this->returnValue($response));
+ $testMock->setDirectLinkHelper($directLinkHelperMock);
+ $testMock->setQuoteHelper($quoteHelperMock);
+
+ $testMock->setConfig($configMock);
+ $testMock->authorize($payment, 100);
+
+ $this->assertEquals(5, $payment->getAdditionalInformation('status'));
+ $this->assertNotEmpty($fakeOrder->getAllStatusHistory());
+ }
+
+ public function testConfirmPaymentWithInvalidResponse()
+ {
+ $configMock = $this->getConfigMockWithOrderId();
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+
+ $fakeQuote = $this->getFakeQuote();
+ $quoteHelperMock = $this->getQuoteHelperMock($fakeQuote);
+ $testMock = $this->getModelMock('ops/payment_directDebit', array('handleAdminPayment', 'performPreDirectLinkCallActions', 'performPostDirectLinkCallActions'));
+
+ $dataHelperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $dataHelperMock->expects($this->once())
+ ->method('isAdminSession')
+ ->will($this->returnValue(true));
+ $testMock->setDataHelper($dataHelperMock);
+
+ $requestParams = array('ORDERID' => '123');
+ $requestParamsHelperMock = $this->getHelperMock('ops/directDebit', array('getDirectLinkRequestParams'));
+
+ $requestParamsHelperMock->expects($this->once())
+ ->method('getDirectLinkRequestParams')
+ ->with($fakeQuote, $fakeOrder, $payment)
+ ->will($this->returnValue($requestParams));
+ $testMock->setRequestParamsHelper($requestParamsHelperMock);
+
+ $response = array();
+ $directLinkHelperMock = $this->getHelperMock('ops/directlink', array('performDirectLinkRequest'));
+ $directLinkHelperMock->expects($this->once())
+ ->method('performDirectLinkRequest')
+ ->with($fakeQuote, $requestParams, 0)
+ ->will($this->returnValue($response));
+ $testMock->setDirectLinkHelper($directLinkHelperMock);
+ $testMock->setQuoteHelper($quoteHelperMock);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('handleUnknownStatus'));
+ $paymentHelperMock->expects($this->once())
+ ->method('handleUnknownStatus')
+ ->with($fakeOrder);
+ $testMock->setPaymentHelper($paymentHelperMock);
+ $testMock->setConfig($configMock);
+ $testMock->authorize($payment, 100);
+
+ }
+
+
+ /**
+ * @expectedException Mage_Core_Exception
+ */
+ public function testConfirmPaymentWithException()
+ {
+ $configMock = $this->getConfigMockWithOrderId();
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+
+ $fakeQuote = $this->getFakeQuote();
+ $quoteHelperMock = $this->getQuoteHelperMock($fakeQuote);
+ $testMock = $this->getModelMock('ops/payment_directDebit', array('handleAdminPayment', 'performPreDirectLinkCallActions', 'performPostDirectLinkCallActions', 'getOnepage'));
+
+ $dataHelperMock = $this->getHelperMock('ops/data', array('isAdminSession'));
+ $dataHelperMock->expects($this->once())
+ ->method('isAdminSession')
+ ->will($this->returnValue(true));
+ $testMock->setDataHelper($dataHelperMock);
+
+ $fakeOnepage = new Varien_Object();
+ $fakeOnepage->setCheckout(new Varien_Object());
+ $testMock->expects($this->once())
+ ->method('getOnepage')
+ ->will($this->returnValue($fakeOnepage));
+
+ $requestParams = array('ORDERID' => '123');
+ $requestParamsHelperMock = $this->getHelperMock('ops/directDebit', array('getDirectLinkRequestParams'));
+
+ $requestParamsHelperMock->expects($this->once())
+ ->method('getDirectLinkRequestParams')
+ ->with($fakeQuote, $fakeOrder, $payment)
+ ->will($this->returnValue($requestParams));
+ $testMock->setRequestParamsHelper($requestParamsHelperMock);
+
+ $fakeValidator = $this->getModelMock('ops/validator_parameter_length', array('isValid'));
+ $fakeValidator->expects($this->once())
+ ->method('isValid')
+ ->will($this->returnValue(false));
+
+ $validationMock = $this->getModelMock('ops/validator_parameter_factory', array('getValidatorFor'));
+ $validationMock->expects($this->once())
+ ->method('getValidatorFor')
+ ->will($this->returnValue($fakeValidator));
+
+ $testMock->setValidationFactory($validationMock);
+ $testMock->setQuoteHelper($quoteHelperMock);
+
+ $testMock->setConfig($configMock);
+ $testMock->authorize($payment, 100);
+
+ }
+
+
+ public function testGetDefaultHelpers()
+ {
+ foreach ($this->testObjects as $testObject) {
+ $this->assertTrue($testObject->getQuoteHelper() instanceof Netresearch_OPS_Helper_Quote);
+ $this->assertTrue($testObject->getDirectLinkHelper() instanceof Netresearch_OPS_Helper_Directlink);
+ $this->assertTrue($testObject->getPaymentHelper() instanceof Netresearch_OPS_Helper_Payment);
+ }
+ }
+
+
+ /**
+ * @return PHPUnit_Framework_MockObject_MockObject
+ */
+ protected function getConfigMockWithOrderId()
+ {
+ $configMock = $this->getModelMock('ops/config', array('getInlineOrderReference', 'getPaymentAction'));
+ $configMock->expects($this->any())
+ ->method('getInlineOrderReference')
+ ->will($this->returnValue(Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID));
+ $configMock->expects($this->any())
+ ->method('getPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE));
+ return $configMock;
+ }
+
+ /**
+ * @return PHPUnit_Framework_MockObject_MockObject
+ */
+ protected function getFakeOrder()
+ {
+ $fakeOrder = $this->getModelMock('sales/order', array('save', '_beforeSave'));
+ $fakeOrder->setState(Mage_Sales_Model_Order::STATE_NEW);
+ return $fakeOrder;
+ }
+
+ /**
+ * @param $fakeOrder
+ *
+ * @return Varien_Object
+ */
+ protected function getFakePayment($fakeOrder)
+ {
+ $payment = $this->getModelMock('sales/order_payment', array('save'));
+ $payment->setMethodInstance(Mage::getModel('ops/payment_directDebit'));
+ $payment->setOrder($fakeOrder);
+ $fakeOrder->setPayment($payment);
+ return $payment;
+ }
+
+ /**
+ * @return PHPUnit_Framework_MockObject_MockObject
+ */
+ protected function getFakeQuote()
+ {
+ $fakeQuote = $this->getModelMock('sales/quote', array('save'));
+ return $fakeQuote;
+ }
+
+ /**
+ * @param $fakeQuote
+ *
+ * @return PHPUnit_Framework_MockObject_MockObject
+ */
+ protected function getQuoteHelperMock($fakeQuote)
+ {
+ $quoteHelperMock = $this->getHelperMock('ops/quote', array('getQuote'));
+ $quoteHelperMock->expects($this->once())
+ ->method('getQuote')
+ ->will($this->returnValue($fakeQuote));
+ return $quoteHelperMock;
+ }
+
+ public function testCaptureDirectSaleDirectDebit()
+ {
+ $directDebitMock = $this->getModelMock('ops/payment_directDebit', array('getConfigPaymentAction', 'confirmPayment'));
+ $directDebitMock->expects($this->once())
+ ->method('getConfigPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE));
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('isInlinePayment'));
+ $paymentHelperMock->expects($this->once())
+ ->method('isInlinePayment')
+ ->with($payment)
+ ->will($this->returnValue(true));
+
+
+
+ $fakeQuote = $this->getFakeQuote();
+ $quoteHelperMock = $this->getQuoteHelperMock($fakeQuote);
+
+ $directDebitMock->expects($this->once())
+ ->method('confirmPayment')
+ ->with($fakeOrder, $fakeQuote, $payment);
+ $directDebitMock->setPaymentHelper($paymentHelperMock);
+ $directDebitMock->setQuoteHelper($quoteHelperMock);
+ $directDebitMock->capture($payment, 100);
+ }
+
+ public function testCaptureDirectSaleDirectDebitInvoice()
+ {
+ $directDebitMock = $this->getModelMock('ops/payment_directDebit', array('getConfigPaymentAction', 'confirmPayment'));
+ $directDebitMock->expects($this->once())
+ ->method('getConfigPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE));
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+ $payment->setAdditionalInformation('paymentId', 4711);
+
+ $directDebitMock->expects($this->never())
+ ->method('confirmPayment');
+ $directDebitMock->capture($payment, 0);
+ }
+
+ public function testCaptureDirectSaleCreditCard()
+ {
+ $directDebitMock = $this->getModelMock('ops/payment_cc', array('getConfigPaymentAction', 'confirmPayment'));
+ $directDebitMock->expects($this->once())
+ ->method('getConfigPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE));
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('isInlinePayment'));
+ $paymentHelperMock->expects($this->once())
+ ->method('isInlinePayment')
+ ->with($payment)
+ ->will($this->returnValue(true));
+
+ $fakeQuote = $this->getFakeQuote();
+ $quoteHelperMock = $this->getQuoteHelperMock($fakeQuote);
+
+ $directDebitMock->expects($this->once())
+ ->method('confirmPayment')
+ ->with($fakeOrder, $fakeQuote, $payment);
+ $directDebitMock->setPaymentHelper($paymentHelperMock);
+ $directDebitMock->setQuoteHelper($quoteHelperMock);
+ $directDebitMock->capture($payment, 100);
+ }
+
+ public function testCaptureDirectSaleCreditCardRedirect()
+ {
+ $directDebitMock = $this->getModelMock('ops/payment_cc', array('getConfigPaymentAction', 'confirmPayment'));
+ $directDebitMock->expects($this->once())
+ ->method('getConfigPaymentAction')
+ ->will($this->returnValue(Mage_Payment_Model_Method_Abstract::ACTION_AUTHORIZE_CAPTURE));
+ $fakeOrder = $this->getFakeOrder();
+ $payment = $this->getFakePayment($fakeOrder);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('isInlinePayment'));
+ $paymentHelperMock->expects($this->once())
+ ->method('isInlinePayment')
+ ->with($payment)
+ ->will($this->returnValue(false));
+
+
+ $directDebitMock->expects($this->never())
+ ->method('confirmPayment');
+ $directDebitMock->setPaymentHelper($paymentHelperMock);
+ $directDebitMock->capture($payment, 100);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Features/PaymentEmailTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/Features/PaymentEmailTest.php
new file mode 100644
index 0000000..af2cb0b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/Features/PaymentEmailTest.php
@@ -0,0 +1,120 @@
+testSubject = Mage::getModel('ops/payment_features_paymentEmail');
+ }
+
+ public function testIsAvailableForOrder()
+ {
+ // given object is no order model -> returns false
+ $order = new Varien_Object();
+ $this->assertFalse($this->testSubject->isAvailableForOrder($order));
+
+ // given payment has not fitting status -> returns false
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setAdditionalInformation(array('status' => 9));
+ $order = $this->getModelMock('sales/order', array('getPayment'));
+ $order->expects($this->once())
+ ->method('getPayment')
+ ->will($this->returnValue($payment));
+ $this->assertFalse($this->testSubject->isAvailableForOrder($order));
+
+ // payment has relevant status -> returns true
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setAdditionalInformation(array('status' => 1));
+ $order = $this->getModelMock('sales/order', array('getPayment'));
+ $order->expects($this->once())
+ ->method('getPayment')
+ ->will($this->returnValue($payment));
+ $this->assertTrue($this->testSubject->isAvailableForOrder($order));
+ }
+
+ public function testResendPaymentInfo()
+ {
+ $mailMock = $this->getMockBuilder('Zend_Mail')
+ ->setMethods(array('send'))
+ ->getMock();
+ $mailMock
+ ->expects($this->once())
+ ->method('send')
+ ->willReturnSelf();
+
+ $templateMock = $this->getModelMock('core/email_template', array('getMail'));
+ $templateMock
+ ->expects($this->any())
+ ->method('getMail')
+ ->willReturn($mailMock);
+ $this->replaceByMock('model', 'core/email_template', $templateMock);
+
+ $payment = $this->getModelMock('sales/order_payment', array('save'));
+ $payment->expects($this->once())
+ ->method('save')
+ ->will($this->returnValue(null));
+
+ $payment->setMethod(Netresearch_OPS_Model_Payment_Flex::CODE);
+
+ $order = Mage::getModel('sales/order');
+ $order->setData('customer_email', 'a@bc.de')
+ ->setData('customer_firstname', 'Hans')
+ ->setData('customer_lastname', 'Wurst')
+ ->setStoreId(0)
+ ->setPayment($payment);
+
+ $this->assertTrue($this->testSubject->resendPaymentInfo($order));
+ $this->assertNotEquals($order->getPayment()->getMethod(), 'foobar');
+ $this->assertEquals($order->getPayment()->getMethod(), Netresearch_OPS_Model_Payment_Flex::CODE);
+ }
+
+ /**
+ * @expectedException Exception
+ * @expectedExceptionMessage Could not send mail due to internal error!
+ */
+ public function testSendSuspendSubscriptionMailWithException()
+ {
+ $this->testSubject->sendSuspendSubscriptionMail(null, null);
+ }
+
+ public function testSendSuspendSubscriptionMail()
+ {
+ $mailMock = $this->getMockBuilder('Zend_Mail')
+ ->setMethods(array('send'))
+ ->getMock();
+ $mailMock
+ ->expects($this->once())
+ ->method('send')
+ ->willReturnSelf();
+
+ $templateMock = $this->getModelMock('core/email_template', array('getMail'));
+ $templateMock
+ ->expects($this->any())
+ ->method('getMail')
+ ->willReturn($mailMock);
+ $this->replaceByMock('model', 'core/email_template', $templateMock);
+
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setReferenceId('SUB-123')
+ ->setStoreId(0);
+
+ $customer = Mage::getModel('customer/customer');
+ $customer->setEmail('a@bc.de')
+ ->setFirstName('Hans')
+ ->setLastName('Wurst');
+
+ $this->assertTrue($this->testSubject->sendSuspendSubscriptionMail($profile, $customer));
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Features/ZeroAmountAuthTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/Features/ZeroAmountAuthTest.php
new file mode 100644
index 0000000..4ba47e6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/Features/ZeroAmountAuthTest.php
@@ -0,0 +1,58 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Model_Payment_Features_ZeroAmountAuthTest extends EcomDev_PHPUnit_Test_Case
+{
+ protected $featureModel = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->featureModel = Mage::getModel('ops/payment_features_zeroAmountAuth');
+ }
+
+ public function testIsCCAndZeroAmountAuthAllowedNoCC()
+ {
+ $payment = Mage::getModel('ops/payment_iDeal');
+ $quote = Mage::getModel('sales/quote');
+ $this->assertFalse($this->featureModel->isCCAndZeroAmountAuthAllowed($payment, $quote));
+ }
+
+
+ public function testIsCCAndZeroAmountAuthAllowedFalse()
+ {
+ $ccModelMock = $this->getCCMock();
+ $quote = Mage::getModel('sales/quote');
+ $this->assertFalse($this->featureModel->isCCAndZeroAmountAuthAllowed($ccModelMock, $quote));
+ }
+
+
+ public function testIsCCAndZeroAmountAuthAllowedTrue()
+ {
+ $ccModelMock = $this->getCCMock(true);
+ $quote = $this->getModelMock('sales/quote', array('getItemsCount', 'isNominal'));
+ $quote->expects($this->once())
+ ->method('getItemsCount')
+ ->will($this->returnValue(1));
+ $quote->expects($this->once())
+ ->method('isNominal')
+ ->will($this->returnValue(false));
+ $this->assertTrue($this->featureModel->isCCAndZeroAmountAuthAllowed($ccModelMock, $quote));
+ }
+
+ protected function getCCMock($returnValue = false)
+ {
+ $ccModelMock = $this->getModelMock('ops/payment_cc', array('isZeroAmountAuthorizationAllowed'));
+ $ccModelMock->expects($this->once())
+ ->method('isZeroAmountAuthorizationAllowed')
+ ->will($this->returnValue($returnValue));
+
+ return $ccModelMock;
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/FlexTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/FlexTest.php
new file mode 100644
index 0000000..bc42fc6
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/FlexTest.php
@@ -0,0 +1,77 @@
+
+ */
+?>
+ 'Foobar',
+ Netresearch_OPS_Model_Payment_Flex::INFO_KEY_PM => 'foo',
+ Netresearch_OPS_Model_Payment_Flex::INFO_KEY_BRAND => 'bar'
+ );
+ }
+
+ public function testGetOpsCode()
+ {
+ $payment = Mage::getModel('sales/order_payment');
+ $additionalInfo = $this->getAdditionalInfo();
+ $payment->setMethod(Netresearch_OPS_Model_Payment_Flex::CODE)
+ ->setAdditionalInformation(
+ $additionalInfo
+ );
+ /** @var Netresearch_OPS_Model_Payment_Flex $subject */
+ $subject = $payment->getMethodInstance();
+
+ $this->assertEquals($additionalInfo[Netresearch_OPS_Model_Payment_Flex::INFO_KEY_PM], $subject->getOpsCode());
+ }
+
+ public function testGetOpsBrand()
+ {
+ $payment = Mage::getModel('sales/order_payment');
+ $additionalInfo = $this->getAdditionalInfo();
+ $payment->setMethod(Netresearch_OPS_Model_Payment_Flex::CODE)
+ ->setAdditionalInformation(
+ $additionalInfo
+ );
+ /** @var Netresearch_OPS_Model_Payment_Flex $subject */
+ $subject = $payment->getMethodInstance();
+
+ $this->assertEquals(
+ $additionalInfo[Netresearch_OPS_Model_Payment_Flex::INFO_KEY_BRAND], $subject->getOpsBrand()
+ );
+
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest.php
new file mode 100644
index 0000000..66e6874
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest.php
@@ -0,0 +1,145 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Model_Payment_IDealTest extends EcomDev_PHPUnit_Test_Case
+{
+
+
+ public function testGetIdealIssuers()
+ {
+ $issuers = Mage::getModel('ops/payment_iDeal')->getIDealIssuers();
+ $this->assertTrue(is_array($issuers));
+ $this->assertTrue(array_key_exists('ABNANL2A', $issuers));
+ $this->assertEquals('ABN AMRO', $issuers['ABNANL2A']);
+
+ $this->assertTrue(array_key_exists('RABONL2U', $issuers));
+ $this->assertEquals('Rabobank', $issuers['RABONL2U']);
+
+ $this->assertTrue(array_key_exists('INGBNL2A', $issuers));
+ $this->assertEquals('ING', $issuers['INGBNL2A']);
+
+ $this->assertTrue(array_key_exists('SNSBNL2A', $issuers));
+ $this->assertEquals('SNS Bank', $issuers['SNSBNL2A']);
+
+ $this->assertTrue(array_key_exists('RBRBNL21', $issuers));
+ $this->assertEquals('Regio Bank', $issuers['RBRBNL21']);
+
+ $this->assertTrue(array_key_exists('ASNBNL21', $issuers));
+ $this->assertEquals('ASN Bank', $issuers['ASNBNL21']);
+
+ $this->assertTrue(array_key_exists('TRIONL2U', $issuers));
+ $this->assertEquals('Triodos Bank', $issuers['TRIONL2U']);
+
+ $this->assertTrue(array_key_exists('FVLBNL22', $issuers));
+ $this->assertEquals('Van Lanschot Bankiers', $issuers['FVLBNL22']);
+
+ $this->assertTrue(array_key_exists('KNABNL2H', $issuers));
+ $this->assertEquals('Knab Bank', $issuers['KNABNL2H']);
+
+ }
+
+
+ public function testAssignData()
+ {
+ $payment = Mage::getModel('sales/quote_payment')->setMethod('ops_iDeal');
+ $quote = Mage::getModel('sales/quote')->setPayment($payment);
+
+ $data = array('iDeal_issuer_id' => 'RBRBNL21');
+ $this->assertEquals('iDEAL', $payment->getMethodInstance()->getOpsCode());
+
+ $method = $payment->getMethodInstance()->assignData($data);
+ $this->assertInstanceOf('Netresearch_OPS_Model_Payment_IDeal', $method);
+
+ $this->assertEquals('RBRBNL21', $payment->getAdditionalInformation('iDeal_issuer_id'));
+ }
+
+ public function testAssignDataWithVarienObject()
+ {
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setMethod('ops_iDeal');
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setPayment($payment);
+
+ $data = new Varien_object(array('iDeal_issuer_id' => 'ABNAMRO'));
+ $this->assertEquals('iDEAL', $payment->getMethodInstance()->getOpsCode());
+
+ $method = $payment->getMethodInstance()->assignData($data);
+ $this->assertInstanceOf('Netresearch_OPS_Model_Payment_IDeal', $method);
+
+ $this->assertEquals('ABNAMRO', $payment->getAdditionalInformation('iDeal_issuer_id'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testGetMethodDependentFormFieldsWithIssuerId()
+ {
+ $order = Mage::getModel('sales/order')->load(25);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote', 'init', 'save')
+ );
+
+ $order->getPayment()->setAdditionalInformation('iDeal_issuer_id', 'ideal_123');
+
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn', 'init', 'save')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+
+ $formFields = Mage::getModel('ops/payment_iDeal')
+ ->getMethodDependendFormFields($order, array());
+
+ $this->assertTrue(array_key_exists('ISSUERID', $formFields));
+ $this->assertEquals('ideal_123', $formFields['ISSUERID']);
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testGetMethodDependentFormFieldsWithoutIssuerId()
+ {
+ $order = Mage::getModel('sales/order')->load(25);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote', 'init', 'save')
+ );
+
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn', 'init', 'save')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+
+ $formFields = Mage::getModel('ops/payment_iDeal')
+ ->getMethodDependendFormFields($order);
+
+ $this->assertFalse(array_key_exists('ISSUERID', $formFields));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest/fixtures/orders.yaml
new file mode 100644
index 0000000..9e96867
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/IDealTest/fixtures/orders.yaml
@@ -0,0 +1,58 @@
+tables:
+ sales/order:
+ - entity_id: 25
+ increment_id: 100000025
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 10
+
+
+
+ sales/quote:
+ - entity_id: 25
+ parent_id: 25
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+
+
+ sales/quote_payment:
+ - payment_id: 25
+ quote_id: 25
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+
+
+ sales/order_payment:
+ - entity_id: 25
+ parent_id: 25
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 25
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/InterSolveTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/InterSolveTest.php
new file mode 100644
index 0000000..07e958b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/InterSolveTest.php
@@ -0,0 +1,78 @@
+
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_Test_Model_Payment_InterSolveTest
+ * @author Thomas Birke
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Model_Payment_InterSolveTest extends EcomDev_PHPUnit_Test_Case_Config
+{
+ public function testClassExists()
+ {
+ $this->assertModelAlias('ops/payment_interSolve', 'Netresearch_OPS_Model_Payment_InterSolve');
+ $this->assertTrue(Mage::getModel('ops/payment_interSolve') instanceof Netresearch_OPS_Model_Payment_InterSolve);
+ $this->assertTrue(Mage::getModel('ops/payment_interSolve') instanceof Netresearch_OPS_Model_Payment_Abstract);
+ }
+
+ public function testMethodConfig()
+ {
+ $this->assertConfigNodeValue('default/payment/ops_interSolve/model', 'ops/payment_interSolve');
+ }
+
+ public function testPm()
+ {
+ $payment = Mage::getModel('payment/info');
+ $this->assertEquals('InterSolve', Mage::getModel('ops/payment_interSolve')->getOpsCode($payment));
+ }
+
+ public function testBrand()
+ {
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setAdditionalInformation('BRAND', 'InterSolve');
+ $this->assertEquals('InterSolve', Mage::getModel('ops/payment_interSolve')->getOpsBrand($payment));
+ }
+
+ public function testAssignDataWithBrand()
+ {
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setMethod('ops_interSolve');
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setPayment($payment);
+
+ $data = array('intersolve_brand' => 'FooBar');
+ $this->assertEquals('InterSolve', $payment->getMethodInstance()->getOpsCode());
+
+ $method = $payment->getMethodInstance()->assignData($data);
+ $this->assertInstanceOf('Netresearch_OPS_Model_Payment_InterSolve', $method);
+
+ $this->assertEquals('FooBar', $payment->getAdditionalInformation('BRAND'));
+ }
+
+ public function testAssignDataWithoutBrand()
+ {
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setMethod('ops_interSolve');
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setPayment($payment);
+
+ $this->assertEquals('InterSolve', $payment->getMethodInstance()->getOpsCode());
+
+ /** @var Netresearch_OPS_Model_Payment_InterSolve $method */
+ $method = $payment->getMethodInstance();
+ $this->assertInstanceOf('Netresearch_OPS_Model_Payment_InterSolve', $method);
+
+ $method->assignData(array());
+ $this->assertEquals('InterSolve', $payment->getAdditionalInformation('BRAND'));
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest.php
new file mode 100644
index 0000000..5c1482d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest.php
@@ -0,0 +1,768 @@
+load(11);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote')
+ );
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getMethodDependendFormFields($order);
+
+
+ $this->assertTrue(array_key_exists('CN', $formFields));
+ $this->assertTrue(array_key_exists('OWNERZIP', $formFields));
+ $this->assertTrue(array_key_exists('OWNERCTY', $formFields));
+ $this->assertTrue(array_key_exists('OWNERTOWN', $formFields));
+ $this->assertTrue(array_key_exists('COM', $formFields));
+ $this->assertTrue(array_key_exists('OWNERTELNO', $formFields));
+ $this->assertTrue(array_key_exists('OWNERADDRESS', $formFields));
+ $this->assertTrue(array_key_exists('BRAND', $formFields));
+ $this->assertTrue(array_key_exists('ADDMATCH', $formFields));
+ $this->assertTrue(
+ array_key_exists('ECOM_BILLTO_POSTAL_POSTALCODE', $formFields)
+ );
+ $this->assertTrue(array_key_exists('CUID', $formFields));
+ $this->assertTrue(
+ array_key_exists('ECOM_ESTIMATEDELIVERYDATE', $formFields)
+ );
+ $this->assertTrue(array_key_exists('RNPOFFERT', $formFields));
+ $this->assertTrue(array_key_exists('ECOM_SHIPMETHODTYPE', $formFields));
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPMETHODSPEED', $formFields)
+ );
+ $this->assertTrue(array_key_exists('ORDERID', $formFields));
+ $this->assertEquals(Mage::getModel('ops/config')->getConfigData('devprefix') . $order->getQuoteId(), $formFields['ORDERID']);
+ }
+
+ /**
+ *
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetMethodDependendFormFieldsWithShipmentDetails()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote')
+ );
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+ $modelMock = $this->getModelMock(
+ 'ops/payment_kwixo_abstract', array('getShippingMethodDetails')
+ );
+ $modelMock->expects($this->any())
+ ->method('getShippingMethodDetails')
+ ->will($this->returnValue('shipping method details'));
+ $formFields = $modelMock->getMethodDependendFormFields($order);
+ $this->assertArrayHasKey('ECOM_SHIPMETHODDETAILS', $formFields);
+ $this->assertEquals(
+ 'shipping method details', $formFields['ECOM_SHIPMETHODDETAILS']
+ );
+ }
+
+ /**
+ *
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetMethodDependendFormFieldsWithShipmentDetailsFromAddress(
+ )
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote')
+ );
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+
+
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+ $modelMock = $this->getModelMock(
+ 'ops/payment_kwixo_abstract',
+ array('getShippingMethodDetails', 'getShippingMethodType')
+ );
+ $modelMock->expects($this->any())
+ ->method('getShippingMethodDetails')
+ ->will($this->returnValue(''));
+ $modelMock->expects($this->any())
+ ->method('getShippingMethodType')
+ ->will($this->returnValue(4));
+ $formFields = $modelMock->getMethodDependendFormFields($order);
+ $this->assertArrayHasKey('ECOM_SHIPMETHODDETAILS', $formFields);
+ }
+
+ /**
+ * @test
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetMethodDependendFormFieldsCheckItemProductCateg()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote')
+ );
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+ $itemProductCategories = array(
+ array(
+ 'value' => 1,
+ 'label' => 'Food & gastronomy'
+ ),
+ array(
+ 'value' => 2,
+ 'label' => 'Car & Motorbike'
+ )
+ );
+ $kwixoAbstractModelMock = $this->getModelMock(
+ 'ops/payment_kwixo_abstract', array(
+ 'getItemFmdProductCateg'
+ )
+ );
+ $kwixoAbstractModelMock->expects($this->any())
+ ->method('getItemFmdProductCateg')
+ ->will($this->returnValue($itemProductCategories));
+ $this->replaceByMock(
+ 'model', 'ops/payment_kwixo_abstract', $kwixoAbstractModelMock
+ );
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getMethodDependendFormFields($order);
+ $this->assertTrue(
+ array_key_exists('ITEMFDMPRODUCTCATEG1', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ITEMFDMPRODUCTCATEG2', $formFields)
+ );
+ }
+
+ /**
+ * @test
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetKwixoShipToParams()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote')
+ );
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+ $shippingMethodTypeValues = array(1, 2, 3, 4);
+ $kwixoAbstractModelMock = $this->getModelMock(
+ 'ops/payment_kwixo_abstract', array(
+ 'getShippingMethodTypeValues',
+ 'getShippingMethodType',
+ )
+ );
+ $kwixoAbstractModelMock->expects($this->any())
+ ->method('getShippingMethodTypeValues')
+ ->will($this->returnValue($shippingMethodTypeValues));
+
+ $kwixoAbstractModelMock->expects($this->any())
+ ->method('getShippingMethodType')
+ ->will($this->returnValue(4));
+
+
+ $this->replaceByMock(
+ 'model', 'ops/payment_kwixo_abstract', $kwixoAbstractModelMock
+ );
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getKwixoShipToParams($order);
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_NAME_FIRST', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_NAME_LAST', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_NAME_PREFIX', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_TELECOM_PHONE_NUMBER', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_STREET_LINE1', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_STREET_NUMBER', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_POSTALCODE', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_CITY', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_COUNTRYCODE', $formFields)
+ );
+
+
+ $order->getShippingAddress()->setStreet(
+ array('An der Tabaksmühle 3a', 'Etage 4')
+ );
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getKwixoShipToParams($order);
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_STREET_LINE2', $formFields)
+ );
+ $this->assertEquals(
+ 'Etage 4', $formFields['ECOM_SHIPTO_POSTAL_STREET_LINE2']
+ );
+
+ $order->getShippingAddress()->setCompany('My great company');
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getKwixoShipToParams($order);
+ $this->assertTrue(array_key_exists('ECOM_SHIPTO_COMPANY', $formFields));
+ $this->assertEquals(
+ 'My great company', $formFields['ECOM_SHIPTO_COMPANY']
+ );
+
+ $order->getShippingAddress()->setFax('4711');
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getKwixoShipToParams($order);
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_TELECOM_FAX_NUMBER', $formFields)
+ );
+ $this->assertEquals(
+ '4711', $formFields['ECOM_SHIPTO_TELECOM_FAX_NUMBER']
+ );
+
+
+ $order->getShippingAddress()->setAddressType('shipping2');
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getKwixoShipToParams($order);
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_NAME_FIRST', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_NAME_LAST', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_NAME_PREFIX', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_TELECOM_PHONE_NUMBER', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_STREET_LINE1', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_STREET_NUMBER', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_POSTALCODE', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_CITY', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_SHIPTO_POSTAL_COUNTRYCODE', $formFields)
+ );
+
+ }
+
+ /**
+ * @test
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetKwixoBillToParams()
+ {
+ $order = Mage::getModel('sales/order')->load(11);
+ $sessionMock = $this->getModelMock(
+ 'checkout/session', array('getQuote')
+ );
+ $sessionMock->expects($this->any())
+ ->method('getQuote')
+ ->will($this->returnValue($order));
+ $this->replaceByMock('model', 'checkout/session', $sessionMock);
+ $sessionMock = $this->getModelMock(
+ 'customer/session', array('isLoggedIn')
+ );
+ $sessionMock->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(1));
+ $this->replaceByMock('model', 'customer/session', $sessionMock);
+
+ $addressData = array(
+ 'housenumber' => 44,
+ 'street' => 'teststreet'
+ );
+
+
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getKwixoBillToParams($order);
+
+ $this->assertTrue(
+ array_key_exists('ECOM_BILLTO_POSTAL_NAME_FIRST', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_BILLTO_POSTAL_NAME_LAST', $formFields)
+ );
+ $this->assertTrue(
+ array_key_exists('ECOM_BILLTO_POSTAL_STREET_NUMBER', $formFields)
+ );
+ $order->getBillingAddress()->setStreet(
+ array('An der Tabaksmühle 3a', 'Etage 4')
+ );
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getKwixoBillToParams($order);
+ $this->assertTrue(array_key_exists('OWNERADDRESS2', $formFields));
+ $this->assertEquals('Etage 4', $formFields['OWNERADDRESS2']);
+ }
+
+ public function testGetRnpFee()
+ {
+
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment/ops_kwixoCredit/rnp_fee', 1);
+ $this->assertEquals(
+ 1, Mage::getModel('ops/payment_kwixo_abstract')->getRnpFee(
+ 'ops_kwixoCredit', 0
+ )
+ );
+ $store->setConfig('payment/ops_kwixoCredit/rnp_fee', 0);
+ $this->assertEquals(
+ 0, Mage::getModel('ops/payment_kwixo_abstract')->getRnpFee(
+ 'ops_kwixoCredit', 0
+ )
+ );
+ $store->resetConfig();
+ $store->setConfig('payment/ops_kwixoApresReception/rnp_fee', 1);
+ $this->assertEquals(
+ 1, Mage::getModel('ops/payment_kwixo_abstract')->getRnpFee(
+ 'ops_kwixoApresReception', 0
+ )
+ );
+ $store->setConfig('payment/ops_kwixoApresReception/rnp_fee', 0);
+ $this->assertEquals(
+ 0, Mage::getModel('ops/payment_kwixo_abstract')->getRnpFee(
+ 'ops_kwixoApresReception', 0
+ )
+ );
+ $store->resetConfig();
+ $store->setConfig('payment/ops_kwixoComptant/rnp_fee', 1);
+ $this->assertEquals(
+ 1, Mage::getModel('ops/payment_kwixo_abstract')->getRnpFee(
+ 'ops_kwixoComptant', 0
+ )
+ );
+ $store->setConfig('payment/ops_kwixoComptant/rnp_fee', 0);
+ $this->assertEquals(
+ 0, Mage::getModel('ops/payment_kwixo_abstract')->getRnpFee(
+ 'ops_kwixoComptant', 0
+ )
+ );
+ }
+
+ public function testGetShippingMethodType()
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoCredit/ecom_shipMethodType', 'Test'
+ );
+ $this->assertEquals(
+ 'Test',
+ Mage::getModel('ops/payment_kwixo_abstract')->getShippingMethodType(
+ 'ops_kwixoCredit', 0
+ )
+ );
+
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoApresReception/ecom_shipMethodType', 'Test1'
+ );
+ $this->assertEquals(
+ 'Test1',
+ Mage::getModel('ops/payment_kwixo_abstract')->getShippingMethodType(
+ 'ops_kwixoApresReception', 0
+ )
+ );
+
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoComptant/ecom_shipMethodType', 'Test2'
+ );
+ $this->assertEquals(
+ 'Test2',
+ Mage::getModel('ops/payment_kwixo_abstract')->getShippingMethodType(
+ 'ops_kwixoComptant', 0
+ )
+ );
+
+ $this->assertEquals(
+ Netresearch_OPS_Model_Source_Kwixo_ShipMethodType::DOWNLOAD,
+ Mage::getModel('ops/payment_kwixo_abstract')->getShippingMethodType(
+ 'ops_kwixoComptant', 0, true
+ )
+ );
+
+ $kwixoShippingMock = $this->getModelMock(
+ 'ops/kwixo_shipping_setting', array('getKwixoShippingType')
+ );
+ $kwixoShippingMock->expects($this->any())
+ ->method('getKwixoShippingType')
+ ->will($this->returnValue(123));
+ $model = Mage::getModel('ops/payment_kwixo_abstract');
+ $model->setKwixoShippingModel($kwixoShippingMock);
+ $this->assertEquals(
+ 123, $model->getShippingMethodType(
+ 'ops_kwixoComptant'
+ )
+ );
+ }
+
+ public function testGetShippingMethodSpeed()
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment/ops_kwixoCredit/ecom_shipMethodSpeed', 25);
+ $this->assertEquals(
+ 25, Mage::getModel('ops/payment_kwixo_abstract')
+ ->getShippingMethodSpeed('ops_kwixoCredit', 0)
+ );
+
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoApresReception/ecom_shipMethodSpeed', 28
+ );
+ $this->assertEquals(
+ 28, Mage::getModel('ops/payment_kwixo_abstract')
+ ->getShippingMethodSpeed('ops_kwixoApresReception', 0)
+ );
+
+ $store->resetConfig();
+ $store->setConfig('payment/ops_kwixoComptant/ecom_shipMethodSpeed', 32);
+ $this->assertEquals(
+ 32, Mage::getModel('ops/payment_kwixo_abstract')
+ ->getShippingMethodSpeed('ops_kwixoComptant', 0)
+ );
+
+ $kwixoShippingMock = $this->getModelMock(
+ 'ops/kwixo_shipping_setting', array('getKwixoShippingMethodSpeed')
+ );
+ $kwixoShippingMock->expects($this->any())
+ ->method('getKwixoShippingMethodSpeed')
+ ->will($this->returnValue(123));
+ $model = Mage::getModel('ops/payment_kwixo_abstract');
+ $model->setKwixoShippingModel($kwixoShippingMock);
+ $this->assertEquals(
+ 123, $model->getShippingMethodSpeed(
+ 'ops_kwixoComptant'
+ )
+ );
+ }
+
+ public function testGetItemFmdProductCateg()
+ {
+ $itemProductCategories = array(
+ array(
+ 'value' => 1,
+ 'label' => 'Food & gastronomy'
+ ),
+ array(
+ 'value' => 2,
+ 'label' => 'Car & Motorbike'
+ )
+ );
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment/ops_kwixoCredit/product_categories', 'Cat1');
+ $this->assertTrue(
+ in_array(
+ 'Cat1', Mage::getModel('ops/payment_kwixo_abstract')
+ ->getItemFmdProductCateg('ops_kwixoCredit', 0)
+ )
+ );
+
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoApresReception/product_categories', 'Cat2'
+ );
+ $this->assertTrue(
+ in_array(
+ 'Cat2', Mage::getModel('ops/payment_kwixo_abstract')
+ ->getItemFmdProductCateg('ops_kwixoApresReception', 0)
+ )
+ );
+
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoComptant/product_categories', 'Cat3'
+ );
+ $this->assertTrue(
+ in_array(
+ 'Cat3', Mage::getModel('ops/payment_kwixo_abstract')
+ ->getItemFmdProductCateg('ops_kwixoComptant', 0)
+ )
+ );
+ }
+
+ public function testGetShippingMethodDetails()
+ {
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoCredit/shiping_method_details', 'Cat1'
+ );
+ $this->assertEquals(
+ 'Cat1', Mage::getModel('ops/payment_kwixo_abstract')
+ ->getShippingMethodDetails('ops_kwixoCredit', 0)
+ );
+
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoApresReception/shiping_method_details', 'Cat2'
+ );
+ $this->assertEquals(
+ 'Cat2', Mage::getModel('ops/payment_kwixo_abstract')
+ ->getShippingMethodDetails('ops_kwixoApresReception', 0)
+ );
+
+ $store->resetConfig();
+ $store->setConfig(
+ 'payment/ops_kwixoComptant/shiping_method_details', 'Cat3'
+ );
+ $this->assertEquals(
+ 'Cat3', Mage::getModel('ops/payment_kwixo_abstract')
+ ->getShippingMethodDetails('ops_kwixoComptant', 0)
+ );
+
+ $kwixoShippingMock = $this->getModelMock(
+ 'ops/kwixo_shipping_setting', array('getKwixoShippingDetails')
+ );
+ $kwixoShippingMock->expects($this->any())
+ ->method('getKwixoShippingDetails')
+ ->will($this->returnValue('shipping details'));
+ $model = Mage::getModel('ops/payment_kwixo_abstract');
+ $model->setKwixoShippingModel($kwixoShippingMock);
+ $this->assertEquals(
+ 'shipping details', $model->getShippingMethodDetails(
+ 'ops_kwixoComptant'
+ )
+ );
+ }
+
+ public function testGetQuestion()
+ {
+ $order = new Varien_Object();
+ $params = array();
+ $this->assertEquals(
+ 'Please make sure that the displayed data is correct.',
+ Mage::getModel('ops/payment_kwixo_abstract')->getQuestion());
+ }
+
+ public function testGetQuestionedFormFields()
+ {
+ $order = new Varien_Object();
+ $params = array();
+ $fields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getQuestionedFormFields($order);
+ $this->assertTrue(in_array('OWNERADDRESS', $fields));
+ $this->assertTrue(
+ in_array('ECOM_BILLTO_POSTAL_STREET_NUMBER', $fields)
+ );
+ }
+
+ public function testGetQuestionedFormFieldsForAddrFields()
+ {
+ $order = $this->getModelMock('sales/order');
+ $params = array();
+ $modelMock = $this->getModelMock(
+ 'ops/payment_kwixo_abstract',
+ array('getShippingMethodTypeValues', 'getShippingMethodType')
+ );
+ $modelMock->expects($this->any())
+ ->method('getShippingMethodTypeValues')
+ ->will($this->returnValue(array(4)));
+ $modelMock->expects($this->any())
+ ->method('getShippingMethodType')
+ ->will($this->returnValue(4));
+
+ $fields = $modelMock->getQuestionedFormFields($order, $params);
+ $this->assertTrue(in_array('OWNERADDRESS', $fields));
+ $this->assertTrue(
+ in_array('ECOM_BILLTO_POSTAL_STREET_NUMBER', $fields)
+ );
+ $this->assertTrue(
+ in_array('ECOM_SHIPTO_POSTAL_STREET_NUMBER', $fields)
+ );
+ $this->assertTrue(
+ in_array('ECOM_SHIPTO_TELECOM_PHONE_NUMBER', $fields)
+ );
+ }
+
+
+ public function testPopulateFromArray()
+ {
+ $kwixoMock = $this->getModelMock(
+ 'ops/payment_kwixo_abstract', array('getQuestionedFormFields')
+ );
+ $kwixoMock->expects($this->any())
+ ->method('getQuestionedFormFields')
+ ->will(
+ $this->returnValue(
+ array('OWNERADDRESS', 'ECOM_BILLTO_POSTAL_STREET_NUMBER')
+ )
+ );
+ $reflectionClass = new ReflectionClass(get_class($kwixoMock));
+ $method = $reflectionClass->getMethod("populateFromArray");
+ $method->setAccessible(true);
+ $formFields = array(
+ 'OWNERADDRESS' => 'bla',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER' => 'blub'
+ );
+ $order = Mage::getModel('sales/order');
+ $this->assertEquals(
+ $formFields, $method->invoke($kwixoMock, $formFields, null, $order)
+ );
+ $this->assertEquals(
+ $formFields,
+ $method->invoke($kwixoMock, $formFields, array(), $order)
+ );
+ // $this->assertEquals($formFields, $method->invoke($kwixoMock, $formFields , array('wusel', 'dusel')));
+
+ $questionedFields = array(
+ 'OWNERADDRESS' => 'blub',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER' => 'bla'
+ );
+ $order = Mage::getModel('sales/order');
+ $this->assertEquals(
+ $questionedFields,
+ $method->invoke($kwixoMock, $formFields, $questionedFields, $order)
+ );
+ }
+
+ /**
+ * @test
+ * @loadFixture ../../../../../var/fixtures/orders.yaml
+ */
+ public function testGetItemParams()
+ {
+ $fakeProduct = Mage::getModel('catalog/product');
+ $fakeProduct->setCategoryIds(array(1, 2));
+ $productMock = $this->getModelMock('catalog/product', array('load'));
+ $productMock->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($fakeProduct));
+ $this->replaceByMock('model', 'catalog/product', $productMock);
+ $fakeKwixoCategory = new Varien_Object();
+ $fakeKwixoCategory->setId(1);
+ $fakeKwixoCategory->setKwixoCategoryId(123);
+ $kwixoMapping = $this->getModelMock(
+ 'ops/kwixo_category_mapping', array('loadByCategoryId')
+ );
+ $kwixoMapping->expects($this->any())
+ ->method('loadByCategoryId')
+ ->will($this->returnValue($fakeKwixoCategory));
+ $this->replaceByMock(
+ 'model', 'ops/kwixo_category_mapping', $kwixoMapping
+ );
+ $order = Mage::getModel('sales/order')->load(11);
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getItemParams($order);
+ $orderItems = $order->getAllItems();
+ $i = 1;
+
+
+ foreach ($orderItems as $orderItem) {
+ $this->assertTrue(array_key_exists('ITEMID' . $i, $formFields));
+ $this->assertEquals(
+ $orderItem->getId(), $formFields['ITEMID' . $i]
+ );
+
+ $this->assertTrue(array_key_exists('ITEMNAME' . $i, $formFields));
+ $this->assertEquals(
+ $orderItem->getName(), $formFields['ITEMNAME' . $i]
+ );
+
+ $this->assertTrue(array_key_exists('ITEMPRICE' . $i, $formFields));
+ $this->assertEquals(
+ $orderItem->getBasePrice(), $formFields['ITEMPRICE' . $i]
+ );
+
+ $this->assertTrue(array_key_exists('ITEMQUANT' . $i, $formFields));
+ $this->assertEquals(
+ $orderItem->getQtyOrdered(), $formFields['ITEMQUANT' . $i]
+ );
+
+ $this->assertTrue(array_key_exists('ITEMVAT' . $i, $formFields));
+ $this->assertEquals(
+ $orderItem->getBaseTaxAmount(), $formFields['ITEMVAT' . $i]
+ );
+
+ $i++;
+ }
+
+
+ $fakeItem = new Varien_Object();
+ $fakeItem->setParentItemId(1);
+ $fakeOrder = $this->getModelMock('sales/order', array('getAllItems'));
+ $fakeOrder->expects($this->any())
+ ->method('getAllItems')
+ ->will($this->returnValue(array($fakeItem)));
+ $formFields = Mage::getModel('ops/payment_kwixo_abstract')
+ ->getItemParams($fakeOrder);
+ $this->assertArrayNotHasKey('ITEMID0', $formFields);
+
+
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/expectations/paymentMethods.yaml b/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/expectations/paymentMethods.yaml
new file mode 100644
index 0000000..e35461a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/expectations/paymentMethods.yaml
@@ -0,0 +1,279 @@
+ops_3XCB:
+ pm: 3XCB
+ brand: 3XCB
+ops_CreditCard:
+ pm: CreditCard
+ brand: AIRPLUS
+ops_CreditCard:
+ pm: CreditCard
+ brand: American Express
+ops_CreditCard:
+ pm: CreditCard
+ brand: Aurore
+ops_CreditCard:
+ pm: CreditCard
+ brand: CB
+ops_CreditCard:
+ pm: CreditCard
+ brand: Cofinoga
+ops_CreditCard:
+ pm: CreditCard
+ brand: Dankort
+ops_CreditCard:
+ pm: CreditCard
+ brand: Diners
+ops_CreditCard:
+ pm: CreditCard
+ brand: JCB
+ops_Creditcard:
+ pm: Creditcard
+ brand: Laser
+ops_CreditCard:
+ pm: CreditCard
+ brand: MaestroUK
+ops_CreditCard:
+ pm: CreditCard
+ brand: MasterCard
+ops_CreditCard:
+ pm: CreditCard
+ brand: UATP
+ops_CreditCard:
+ pm: CreditCard
+ brand: VISA
+ops_BCMC:
+ pm: CreditCard
+ brand: BCMC
+ops_CreditCard:
+ pm: CreditCard
+ brand: Maestro
+ops_PostFinance:
+ pm: PostFinance Card
+ brand: PostFinance Card
+ops_CreditCard:
+ pm: CreditCard
+ brand: PRIVILEGE
+ops_UNEUROCOM:
+ pm: UNEUROCOM
+ brand: UNEUROCOM
+ops_AmazonCheckout:
+ pm: Amazon Checkout
+ brand: Amazon Checkout
+ops_Belfius:
+ pm: Belfius Direct Net
+ brand: Belfius Direct Net
+ops_cashticket:
+ pm: cashticket
+ brand: cashticket
+ops_cbcOnline:
+ pm: CBC Online
+ brand: CBC Online
+ops_directEbanking:
+ pm: DirectEbanking
+ brand: Sofort Uberweisung
+ops_directEbankingAT:
+ pm: DirectEbankingAT
+ brand: DirectEbankingAT
+ops_directEbankingBE:
+ pm: DirectEbankingBE
+ brand: DirectEbankingBE
+ops_directEbankingCH:
+ pm: DirectEbankingCH
+ brand: DirectEbankingCH
+ops_directEbankingDE:
+ pm: DirectEbankingDE
+ brand: DirectEbankingDE
+ops_directEbankingFR:
+ pm: DirectEbankingFR
+ brand: DirectEbankingFR
+ops_directEbankingGB:
+ pm: DirectEbankingGB
+ brand: DirectEbankingGB
+ops_directEbankingIT:
+ pm: DirectEbankingIT
+ brand: DirectEbankingIT
+ops_directEbankingNL:
+ pm: DirectEbankingNL
+ brand: DirectEbankingNL
+ops_EBS_AXIS:
+ pm: EBS_AXIS
+ brand: EBS_AXIS
+ops_EBS_BC:
+ pm: EBS_BC
+ brand: EBS_BC
+ops_EBS_CB:
+ pm: EBS_CB
+ brand: EBS_CB
+ops_EBS_CORP:
+ pm: EBS_CORP
+ brand: EBS_CORP
+ops_EBS_DC:
+ pm: EBS_DC
+ brand: EBS_DC
+ops_EBS_FED:
+ pm: EBS_FED
+ brand: EBS_FED
+ops_EBS_HDFC:
+ pm: EBS_HDFC
+ brand: EBS_HDFC
+ops_EBS_HYDERABAD:
+ pm: EBS_HYDERABAD
+ brand: EBS_HYDERABAD
+ops_EBS_IB:
+ pm: EBS_IB
+ brand: EBS_IB
+ops_EBS_ICASH:
+ pm: EBS_ICASH
+ brand: EBS_ICASH
+ops_EBS_ICICI:
+ pm: EBS_ICICI
+ brand: EBS_ICICI
+ops_EBS_INDIA:
+ pm: EBS_INDIA
+ brand: EBS_INDIA
+ops_EBS_ITZ:
+ pm: EBS_ITZ
+ brand: EBS_ITZ
+ops_EBS_JK:
+ pm: EBS_JK
+ brand: EBS_JK
+ops_EBS_KARNATAKA:
+ pm: EBS_KARNATAKA
+ brand: EBS_KARNATAKA
+ops_EBS_KOTAK:
+ pm: EBS_KOTAK
+ brand: EBS_KOTAK
+ops_EBS_MYSORE:
+ pm: EBS_MYSORE
+ brand: EBS_MYSORE
+ops_EBS_TRAVANCORE:
+ pm: EBS_TRAVANCORE
+ brand: EBS_TRAVANCORE
+ops_eDankort:
+ pm: eDankort
+ brand: eDankort
+ops_eps:
+ pm: EPS
+ brand: EPS
+ops_FidorPay:
+ pm: FidorPay
+ brand: FidorPay
+ops_fortisPayButton:
+ pm: Fortis Pay Button
+ brand: Fortis Pay Button
+ops_giroPay:
+ pm: giropay
+ brand: giropay
+ops_Masterpass:
+ pm: Masterpass
+ brand: Masterpass
+ops_iDeal:
+ pm: iDEAL
+ brand: iDEAL
+ops_ingHomePay:
+ pm: ING HomePay
+ brand: ING HomePay
+ops_kbcOnline:
+ pm: KBC Online
+ brand: KBC Online
+ops_paysafecard:
+ pm: paysafecard
+ brand: paysafecard
+ops_postFinanceEFinance:
+ pm: PostFinance e-finance
+ brand: PostFinance e-finance
+ops_directDebitsAt:
+ pm: Direct Debits AT
+ brand: Direct Debits AT
+ops_directDebitsDe:
+ pm: Direct Debits DE
+ brand: Direct Debits DE
+ops_directDebitsNl:
+ pm: Direct Debits NL
+ brand: Direct Debits NL
+ops_bankTransfer:
+ pm: "Bank transfer"
+ brand: "Bank transfer"
+ops_bankTransferBe:
+ pm: Bank transfer BE
+ brand: Bank transfer BE
+ops_bankTransferDe:
+ pm: Bank transfer DE
+ brand: Bank transfer DE
+ops_bankTransferFr:
+ pm: Bank transfer FR
+ brand: Bank transfer FR
+ops_bankTransferNl:
+ pm: Bank transfer NL
+ brand: Bank transfer NL
+ops_installmentsDe:
+ pm: Installments DE
+ brand: Installments DE
+ops_installmentsDk:
+ pm: Installments DK
+ brand: Installments DK
+ops_installmentsFi:
+ pm: Installments FI
+ brand: Installments FI
+ops_installmentsNl:
+ pm: Installments NL
+ brand: Installments NL
+ops_installmentsNo:
+ pm: Installments NO
+ brand: Installments NO
+ops_installmentsSe:
+ pm: Installments SE
+ brand: Installments SE
+ops_openInvoiceDe:
+ pm: Open Invoice DE
+ brand: Open Invoice DE
+ops_openInvoiceDk:
+ pm: Open Invoice DK
+ brand: Open Invoice DK
+ops_openInvoiceFi:
+ pm: Open Invoice FI
+ brand: Open Invoice FI
+ops_openInvoiceNl:
+ pm: Open Invoice NL
+ brand: Open Invoice NL
+ops_openInvoiceAT:
+ pm: Open Invoice AT
+ brand: Open Invoice AT
+ops_openInvoiceNo:
+ pm: Open Invoice NO
+ brand: Open Invoice NO
+ops_openInvoiceSe:
+ pm: Open Invoice SE
+ brand: Open Invoice SE
+ops_cod:
+ pm: Payment on Delivery
+ brand: Payment on Delivery
+ops_interSolve:
+ pm: InterSolve
+ brand: InterSolve
+ops_pingPing:
+ pm: PingPing
+ brand: PingPing
+ops_tunz:
+ pm: TUNZ
+ brand: TUNZ
+ops_cashEX:
+ pm: cashEX
+ brand: cashEX
+ops_cashU:
+ pm: cashU
+ brand: cashU
+ops_cashUDirect:
+ pm: cashU Direct
+ brand: cashU Direct
+ops_Payble:
+ pm: Payble
+ brand: Payble
+ops_paypal:
+ pm: PAYPAL
+ brand: PAYPAL
+ops_wallie:
+ pm: Wallie
+ brand: Wallie
+ops_belfiusDirectNet:
+ pm: Belfius Direct Net
+ brand: Belfius Direct Net
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/fixtures/.gitkeep b/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/fixtures/.gitkeep
new file mode 100644
index 0000000..e69de29
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/fixtures/orders.yaml
new file mode 100644
index 0000000..2f9a07f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/Kwixo/AbstractTest/fixtures/orders.yaml
@@ -0,0 +1,633 @@
+config:
+ default/payment_services/ops/submitExtraParameters: 1
+
+tables:
+ sales/order:
+ - entity_id: 11
+ increment_id: 100000011
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 23
+ store_id: 0
+
+ - entity_id: 12
+ increment_id: 100000012
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 24
+
+ - entity_id: 13
+ increment_id: 100000013
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'processing'
+ status: 'processing'
+ quote_id: 25
+ store_id: 0
+
+ - entity_id: 14
+ increment_id: 100000014
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 26
+
+ - entity_id: 15
+ increment_id: 100000015
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 200.00
+ currency: '$'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+ - entity_id: 16
+ increment_id: 100000016
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 28
+
+ - entity_id: 17
+ increment_id: 100000017
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 29
+
+ - entity_id: 18
+ increment_id: 100000018
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 30
+
+ - entity_id: 19
+ increment_id: 100000019
+ shipping_address_id: 50
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 43
+
+ - entity_id: 20
+ increment_id: 100000020
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 42#
+
+ - entity_id: 21
+ increment_id: 100000021
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 22
+ increment_id: 100000022
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 23
+ increment_id: 100000023
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 24
+ increment_id: 100000024
+ store_id: 1
+ shipping_address_id: 46
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 24
+ increment_id: 100000024
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 25
+ increment_id: 100000025
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 26
+ increment_id: 100000026
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 27
+ increment_id: 100000027
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 28
+ increment_id: 100000028
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 29
+ increment_id: 100000029
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 30
+ increment_id: 100000030
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ sales/quote:
+ - entity_id: 1
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ - entity_id: 2
+ base_grand_total: 119.00
+ grand_total: 200.00
+ currency: '$'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ - entity_id: 10
+ store_id: 0
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+ store_id: 0
+
+ - entity_id: 11
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 23
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 12
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ sales/quote_payment:
+ - payment_id: 1
+ quote_id: 10
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 2
+ quote_id: 11
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ quote_id: 11
+
+ - payment_id: 3
+ quote_id: 10
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ additional_information: a:7:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:3:"cvc";s:3:"123";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 4
+ quote_id: 12
+ updated_at: '1970-01-01'
+ method: 'ops_paypal'
+ additional_information: a:7:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:3:"cvc";s:3:"123";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ sales/order_payment:
+ - entity_id: 1
+ parent_id: 11
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_bankTransfer'
+
+ - entity_id: 2
+ parent_id: 12
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:1:"5";}
+
+ - entity_id: 3
+ parent_id: 13
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:1:"0";}
+ method: 'ops_bankTransfer'
+
+ - entity_id: 4
+ parent_id: 14
+ additional_information: a:2:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";}
+
+ - entity_id: 5
+ parent_id: 15
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFD";}
+ method: 'ops_cc'
+
+ - entity_id: 6
+ parent_id: 16
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFS";}
+
+ - entity_id: 7
+ parent_id: 17
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFS";s:9:"canRefund";b:0;}
+
+ - entity_id: 8
+ parent_id: 18
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFD";s:9:"canRefund";b:1;}
+
+ - entity_id: 9
+ parent_id: 19
+ method: 'ops_openInvoiceDe'
+
+ - entity_id: 11
+ parent_id: 20
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 12
+ parent_id: 21
+ additional_information: a:4:{s:2:"PM";s:16:"Direct Debits DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+ method: 'ops_directDebit'
+
+ - entity_id: 13
+ parent_id: 22
+ additional_information: a:4:{s:2:"PM";s:16:"Direct Debits NL";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 14
+ parent_id: 23
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 42
+ parent_id: 20
+
+ - entity_id: 15
+ parent_id: 24
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_cc'
+
+ - entity_id: 16
+ parent_id: 25
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_cc'
+
+ - entity_id: 17
+ parent_id: 26
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_paypal'
+
+ - entity_id: 18
+ parent_id: 27
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoApresReception'
+
+ - entity_id: 19
+ parent_id: 28
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoComptant'
+
+ - entity_id: 20
+ parent_id: 29
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoCredit'
+
+ - entity_id: 21
+ parent_id: 30
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'checkmo'
+
+ sales/shipment:
+ - entity_id: 1
+ increment_id: 100000077
+ order_id: 11
+ shipping_address_id: 42
+
+ - entity_id: 2
+ increment_id: 100000078
+ order_id: 12
+ shipping_address_id: 43
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 11
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 11
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 44
+ parent_id: 12
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 45
+ parent_id: 12
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 46
+ parent_id: 24
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 47
+ parent_id: 27
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_shipping: 1
+
+ - entity_id: 147
+ parent_id: 27
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+
+ - entity_id: 48
+ parent_id: 28
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 49
+ parent_id: 19
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 50
+ parent_id: 19
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 51
+ parent_id: 15
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ sales/order_item:
+ - item_id: 11
+ order_id: 11
+ qty_ordered: 2.0000
+ qty_shipped: 2.0000
+ sku: 4711
+ name: 'some great test item'
+ price: 19.99
+ tax_amount: 1.99
+
+ - item_id: 12
+ order_id: 11
+ qty_ordered: 2.0000
+ qty_shipped: 2.0000
+ sku: 4711
+ name: 'some great test item 2'
+ price: 19.99
+ tax_amount: 1.99
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoApresReceptionTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoApresReceptionTest.php
new file mode 100644
index 0000000..3fc3426
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoApresReceptionTest.php
@@ -0,0 +1,55 @@
+kwixoApresReceptionModel = Mage::getModel('ops/payment_kwixoApresReception');
+ $this->kwixoApresReceptionModel->setInfoInstance($payment);
+ $this->store = Mage::app()->getStore(0)->load(0);
+ }
+
+ public function testGetOpsCode()
+ {
+ $this->assertEquals('KWIXO_RNP', $this->kwixoApresReceptionModel->getOpsCode());
+ }
+
+ public function testGetCode()
+ {
+ $this->assertEquals('ops_kwixoApresReception', $this->kwixoApresReceptionModel->getCode());
+ }
+
+ public function testGetDeliveryDate()
+ {
+ $this->setUp();
+ $dateNow = date("Y-m-d");
+ $path = 'payment/ops_kwixoApresReception/delivery_date';
+ $this->store->setConfig($path, "0");
+ $this->assertEquals($dateNow, $this->kwixoApresReceptionModel->getEstimatedDeliveryDate('ops_kwixoApresReception'));
+ $dateNowPlusFiveDays = strtotime($dateNow ."+ 5 days");
+ $this->store->setConfig($path, "5");
+ $this->assertEquals(date("Y-m-d", $dateNowPlusFiveDays), $this->kwixoApresReceptionModel->getEstimatedDeliveryDate('ops_kwixoApresReception'));
+ }
+
+ public function testGetFormBlockType()
+ {
+ $this->assertEquals('ops/form_kwixo_apresReception', $this->kwixoApresReceptionModel->getFormBlockType());
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoComptantTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoComptantTest.php
new file mode 100644
index 0000000..5ae0c2d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoComptantTest.php
@@ -0,0 +1,56 @@
+kwixoComptantModel = Mage::getModel('ops/payment_kwixoComptant');
+ $this->kwixoComptantModel->setInfoInstance($payment);
+ $this->store = Mage::app()->getStore(0)->load(0);
+ }
+
+ public function testGetOpsCode()
+ {
+ $this->assertEquals('KWIXO_STANDARD', $this->kwixoComptantModel->getOpsCode());
+ }
+
+ public function testGetCode()
+ {
+ $this->assertEquals('ops_kwixoComptant', $this->kwixoComptantModel->getCode());
+ }
+
+ public function testGetDeliveryDate()
+ {
+ $this->setUp();
+ $dateNow = date("Y-m-d");
+ $path = 'payment/ops_kwixoComptant/delivery_date';
+ $this->store->setConfig($path, "0");
+ $this->assertEquals($dateNow, $this->kwixoComptantModel->getEstimatedDeliveryDate('ops_kwixoComptant'));
+ $dateNowPlusFiveDays = strtotime($dateNow ."+ 5 days");
+ $this->store->setConfig($path, "5");
+ $this->assertEquals(date("Y-m-d", $dateNowPlusFiveDays), $this->kwixoComptantModel->getEstimatedDeliveryDate('ops_kwixoComptant'));
+ }
+
+ public function testGetFormBlockType()
+ {
+ $this->assertEquals('ops/form_kwixo_comptant', $this->kwixoComptantModel->getFormBlockType());
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoCreditTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoCreditTest.php
new file mode 100644
index 0000000..c422004
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/KwixoCreditTest.php
@@ -0,0 +1,59 @@
+kwixoCreditModel = Mage::getModel('ops/payment_KwixoCredit');
+ $this->kwixoCreditModel->setInfoInstance(Mage::getModel('payment/info'));
+ $this->store = Mage::app()->getStore(0)->load(0);
+ }
+
+
+ public function testGetOpsCode()
+ {
+ $this->assertEquals('KWIXO_CREDIT', $this->kwixoCreditModel->getOpsCode());
+ }
+
+ public function testGetCode()
+ {
+ $this->assertEquals('ops_kwixoCredit', $this->kwixoCreditModel->getCode());
+ }
+
+
+ public function testGetDeliveryDate()
+ {
+ $this->setUp();
+ $dateNow = date("Y-m-d");
+ $path = 'payment/ops_kwixoCredit/delivery_date';
+ $this->store->setConfig($path, "0");
+ $this->assertEquals($dateNow, $this->kwixoCreditModel->getEstimatedDeliveryDate('ops_kwixoCredit'));
+ $dateNowPlusFiveDays = strtotime($dateNow . "+ 5 days");
+ $this->store->setConfig($path, "5");
+ $this->assertEquals(
+ date("Y-m-d", $dateNowPlusFiveDays),
+ $this->kwixoCreditModel->getEstimatedDeliveryDate('ops_kwixoCredit')
+ );
+ }
+
+ public function testGetFormBlockType()
+ {
+ $this->assertEquals('ops/form_kwixo_credit', $this->kwixoCreditModel->getFormBlockType());
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/ObjectHandler.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/ObjectHandler.php
new file mode 100644
index 0000000..24b6b8b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/ObjectHandler.php
@@ -0,0 +1,14 @@
+$key) {
+ throw new Exception(sprintf('No serialized object "%s" available in %s', $key, $objectsFile));
+ }
+
+ return unserialize(base64_decode(current($objects->$key)));
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceAtTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceAtTest.php
new file mode 100644
index 0000000..36d1fa0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceAtTest.php
@@ -0,0 +1,87 @@
+
+ * @category Netresearch
+ * @package Netresearch/OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Model_Payment_OpenInvoiceAtTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $model = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->model = Mage::getModel('ops/payment_openInvoiceAt');
+ }
+
+ /**
+ * assure that openInvoiceAT can not capture partial, because invoice is always created on feedback in this case
+ */
+ public function testCanCapturePartial()
+ {
+ $this->assertFalse($this->model->canCapturePartial());
+ }
+
+ public function testIsAvailableNoQuoteGiven()
+ {
+ $quote = new Varien_Object();
+ $this->assertFalse($this->model->isAvailable($quote));
+ }
+
+ public function testIsAvailableNoDiscountAllowed()
+ {
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setSubtotal(5);
+ $quote->setSubtotalWithDiscount(10);
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment/ops_openInvoiceAt/allow_discounted_carts', 0);
+
+ $this->assertFalse($this->model->isAvailable($quote));
+ }
+
+ public function testIsAvailableNoGender()
+ {
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setSubtotal(10);
+ $quote->setSubtotalWithDiscount(10);
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment/ops_openInvoiceAt/allow_discounted_carts', 1);
+
+ $this->assertFalse($this->model->isAvailable($quote));
+ }
+
+ public function testGetMethodDependendFormFields()
+ {
+ $customerHelper = $this->getHelperMock('customer/data', array('isLoggedIn'));
+ $customerHelper->expects($this->any())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('helper', 'customer/data', $customerHelper);
+
+ $order = Mage::getModel('sales/order');
+ $order->setCustomerDob('01/10/1970')
+ ->setCustomerGender(1);
+ $billingAddress = Mage::getModel('sales/order_address');
+ $billingAddress->setAddressType(Mage_Sales_Model_Order_Address::TYPE_BILLING)
+ ->setStreet('Klarna-Straße 1/2/3');
+ $order->setBillingAddress($billingAddress);
+ $payment = Mage::getModel('sales/order_payment');
+ $model = Mage::getModel('ops/payment_openInvoiceAt');
+ $payment->setMethod($model->getCode());
+ $model->setInfoInstance($payment);
+ $payment->setMethodInstance($model);
+ $order->setPayment($payment);
+ $params = $model->getMethodDependendFormFields($order);
+
+ $this->assertEquals(' ', $params['ECOM_BILLTO_POSTAL_STREET_NUMBER']);
+ $this->assertEquals('Klarna-Straße 1/2/3', $params['OWNERADDRESS']);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceDeTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceDeTest.php
new file mode 100644
index 0000000..1fba35f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceDeTest.php
@@ -0,0 +1,60 @@
+
+ * @category Netresearch
+ * @package Netresearch/OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Model_Payment_OpenInvoiceDeTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $model = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->model = Mage::getModel('ops/payment_openInvoiceDe');
+ }
+
+ /**
+ * assure that openInvoiceNL can not capture partial, because invoice is always created on feedback in this case
+ */
+ public function testCanCapturePartial()
+ {
+ $this->assertFalse($this->model->canCapturePartial());
+ }
+
+ public function testIsAvailableNoQuoteGiven()
+ {
+ $quote = new Varien_Object();
+ $this->assertFalse($this->model->isAvailable($quote));
+ }
+
+ public function testIsAvailableNoDiscountAllowed()
+ {
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setSubtotal(5);
+ $quote->setSubtotalWithDiscount(10);
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment/ops_openInvoiceDe/allow_discounted_carts', 0);
+
+ $this->assertFalse($this->model->isAvailable($quote));
+ }
+
+ public function testIsAvailableNoGender()
+ {
+
+ $quote = Mage::getModel('sales/quote');
+ $quote->setSubtotal(10);
+ $quote->setSubtotalWithDiscount(10);
+ $store = Mage::app()->getStore(0)->load(0);
+ $store->resetConfig();
+ $store->setConfig('payment/ops_openInvoiceDe/allow_discounted_carts', 1);
+
+ $this->assertFalse($this->model->isAvailable($quote));
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceNlTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceNlTest.php
new file mode 100644
index 0000000..08b352b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/OpenInvoiceNlTest.php
@@ -0,0 +1,94 @@
+model = Mage::getModel('ops/payment_openInvoiceNl');
+ }
+
+ public function testQuestionRequired()
+ {
+ $order = new Varien_Object();
+ $requestParams = array(
+ 'foo' => 'bar',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER' => '14'
+ );
+ $requestParams = array();
+ $formFields = array(
+ 'OWNERADDRESS' => '',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER' => '',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1' => '',
+ 'ECOM_SHIPTO_POSTAL_STREET_NUMBER' => ''
+ );
+
+ $method = $this->getModelMock(
+ 'ops/payment_openInvoiceNl', array(
+ 'getFormFields'
+ )
+ );
+ $method->expects($this->any())
+ ->method('getFormFields')
+ ->will($this->returnValue($formFields));
+
+ $this->assertTrue($method->hasFormMissingParams($order, $requestParams, $formFields), 'expected missing params');
+ $this->assertTrue(is_string($method->getQuestion()));
+ $this->assertEquals(
+ array(
+ 'OWNERADDRESS',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1',
+ 'ECOM_SHIPTO_POSTAL_STREET_NUMBER'
+ ),
+ $method->getQuestionedFormFields($order, $requestParams)
+ );
+ }
+
+ public function testQuestionNotRequired()
+ {
+ $order = new Varien_Object();
+ $requestParams = array(
+ 'foo' => 'bar',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER' => '14'
+ );
+ $formFields = array(
+ 'OWNERADDRESS' => 'Nowhere',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER' => '14',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1' => 'Somewhere',
+ 'ECOM_SHIPTO_POSTAL_STREET_NUMBER' => '1'
+ );
+
+ $method = $this->getModelMock(
+ 'ops/payment_openInvoiceNl', array(
+ 'getFormFields'
+ )
+ );
+ $method->expects($this->any())
+ ->method('getFormFields')
+ ->will($this->returnValue($formFields));
+
+ $this->assertFalse($method->hasFormMissingParams($order, $requestParams, $formFields), 'expected no missing params');
+
+ /* independent from that we expect to get question and questioned params when calling these methods directly */
+ $this->assertTrue(is_string($method->getQuestion()));
+ $this->assertEquals(
+ array(
+ 'OWNERADDRESS',
+ 'ECOM_BILLTO_POSTAL_STREET_NUMBER',
+ 'ECOM_SHIPTO_POSTAL_STREET_LINE1',
+ 'ECOM_SHIPTO_POSTAL_STREET_NUMBER'
+ ),
+ $method->getQuestionedFormFields($order, $requestParams)
+ );
+ }
+
+ /**
+ * assure that openInvoiceNL can capture partial
+ */
+ public function testCanCapturePartial()
+ {
+ $this->assertTrue($this->model->canCapturePartial());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/PayPerMailTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/PayPerMailTest.php
new file mode 100644
index 0000000..8b6d320
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/PayPerMailTest.php
@@ -0,0 +1,77 @@
+
+ */
+?>
+ 'Foobar',
+ Netresearch_OPS_Model_Payment_PayPerMail::INFO_KEY_PM => 'foo',
+ Netresearch_OPS_Model_Payment_PayPerMail::INFO_KEY_BRAND => 'bar'
+ );
+ }
+
+ public function testGetOpsCode()
+ {
+ $payment = Mage::getModel('sales/order_payment');
+ $additionalInfo = $this->getAdditionalInfo();
+ $payment->setMethod(Netresearch_OPS_Model_Payment_PayPerMail::CODE)
+ ->setAdditionalInformation(
+ $additionalInfo
+ );
+ /** @var Netresearch_OPS_Model_Payment_PayPerMail $subject */
+ $subject = $payment->getMethodInstance();
+
+ $this->assertEquals($additionalInfo[Netresearch_OPS_Model_Payment_PayPerMail::INFO_KEY_PM], $subject->getOpsCode());
+ }
+
+ public function testGetOpsBrand()
+ {
+ $payment = Mage::getModel('sales/order_payment');
+ $additionalInfo = $this->getAdditionalInfo();
+ $payment->setMethod(Netresearch_OPS_Model_Payment_PayPerMail::CODE)
+ ->setAdditionalInformation(
+ $additionalInfo
+ );
+ /** @var Netresearch_OPS_Model_Payment_Flex $subject */
+ $subject = $payment->getMethodInstance();
+
+ $this->assertEquals(
+ $additionalInfo[Netresearch_OPS_Model_Payment_PayPerMail::INFO_KEY_BRAND], $subject->getOpsBrand()
+ );
+
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/Cc/ParameterBagTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/Cc/ParameterBagTest.php
new file mode 100644
index 0000000..319a8fc
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/Cc/ParameterBagTest.php
@@ -0,0 +1,396 @@
+
+ */
+?>
+calculateEndDate($startDate, $periodUnit, $frequency, $maxCycles);
+ $startDate = new DateTime('03.01.2015');
+ $this->assertEquals($startDate->format('d.M.Y'), $endDate->format('d.M.Y'));
+
+ $startDate = new DateTime('01.01.2015');
+ $periodUnit = Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_MONTH;
+ $frequency = 1;
+ $maxCycles = 2;
+
+ $endDate = $subject->calculateEndDate($startDate, $periodUnit, $frequency, $maxCycles);
+ $startDate = new DateTime('01.03.2015');
+ $this->assertEquals($startDate->format('d.M.Y'), $endDate->format('d.M.Y'));
+
+ $startDate = new DateTime('31.01.2015');
+ $periodUnit = Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_MONTH;
+ $frequency = 1;
+ $maxCycles = 2;
+
+ $endDate = $subject->calculateEndDate($startDate, $periodUnit, $frequency, $maxCycles);
+ $startDate = new DateTime('28.03.2015');
+ $this->assertEquals($startDate->format('d.M.Y'), $endDate->format('d.M.Y'));
+
+ $startDate = new DateTime('01.01.2015');
+ $periodUnit = Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_WEEK;
+ $frequency = 1;
+ $maxCycles = 2;
+
+ $endDate = $subject->calculateEndDate($startDate, $periodUnit, $frequency, $maxCycles);
+ $startDate = new DateTime('15.01.2015');
+ $this->assertEquals($startDate->format('d.M.Y'), $endDate->format('d.M.Y'));
+
+ $endDate = $subject->calculateEndDate($startDate, $periodUnit, $frequency, '');
+ $this->assertNull($endDate);
+ }
+
+ public function testHelperFunctions()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ $testString = 'abc';
+ $this->assertTrue($subject->getSubscriptionHelper() instanceof Netresearch_OPS_Helper_Subscription);
+ $subject->setSubscriptionHelper($testString);
+ $this->assertEquals($subject->getSubscriptionHelper(), $testString);
+
+ $this->assertTrue($subject->getQuoteHelper() instanceof Netresearch_OPS_Helper_Quote);
+ $subject->setQuoteHelper($testString);
+ $this->assertEquals($subject->getQuoteHelper(), $testString);
+
+ $this->assertTrue($subject->getDataHelper() instanceof Netresearch_OPS_Helper_Data);
+ $subject->setDataHelper($testString);
+ $this->assertEquals($subject->getDataHelper(), $testString);
+
+ $this->assertTrue($subject->getRequestHelper() instanceof Netresearch_OPS_Helper_Payment_Request);
+ $subject->setRequestHelper($testString);
+ $this->assertEquals($subject->getRequestHelper(), $testString);
+
+ $this->assertTrue($subject->getConfig() instanceof Netresearch_OPS_Model_Config);
+ $subject->setConfig($testString);
+ $this->assertEquals($subject->getConfig(), $testString);
+ }
+
+ /**
+ * @return Mage_Sales_Model_Recurring_Profile
+ */
+ protected function getTestProfile($withTrial = false)
+ {
+ $profile = Mage::getModel('sales/recurring_profile');
+ $address = Mage::getModel('sales/quote_address');
+ $address->setCity('Leipzig');
+ $address->setStreet('Test 123');
+ $quote = Mage::getModel('sales/quote');
+ $quote->setShippingAddress($address);
+ $quote->setBillingAddress($address);
+
+ $profile->setScheduleDescription('abc')
+ ->setPeriodFrequency(1)
+ ->setPeriodMaxCycles(1)
+ ->setPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_WEEK)
+ ->setInitAmount(10)
+ ->setBillingAmount(15)
+ ->setTaxAmount(5)
+ ->setShippingAmount(5)
+ ->setStartDatetime('')
+ ->setQuote($quote)
+ ->setId(0);
+
+ if ($withTrial) {
+ $profile->setTrialPeriodMaxCycles(1)
+ ->setTrialPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_DAY)
+ ->setTrialPeriodFrequency(1)
+ ->setTrialBillingAmount(15);
+ }
+ return $profile;
+ }
+
+ public function testCollectProfileParameters()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ $profile = $this->getTestProfile();
+ $profile->setPeriodMaxCycles(0);
+
+ $params = $subject->collectProfileParameters($profile)->toArray();
+
+ $startDate = new DateTime();
+ $this->assertArrayHasKey('SUB_STARTDATE', $params);
+ $this->assertEquals($params['SUB_STARTDATE'], $startDate->format('d/m/Y'));
+
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . $profile->getId();
+ $this->assertArrayHasKey('SUBSCRIPTION_ID', $params);
+ $this->assertEquals($id, $params['SUBSCRIPTION_ID']);
+
+ $this->assertArrayHasKey('SUB_ORDERID', $params);
+ $this->assertEquals($id, $params['SUB_ORDERID']);
+
+ $this->assertArrayHasKey('ORDERID', $params);
+ $this->assertEquals($id, $params['ORDERID']);
+
+ $this->assertArrayHasKey('SUB_COM', $params);
+ $this->assertEquals($params['SUB_COM'], 'abc');
+
+ $this->assertEquals(0, $params['AMOUNT']);
+ $subAmount = $profile->getBillingAmount() + $profile->getTaxAmount() + $profile->getShippingAmount();
+ $this->assertEquals($subAmount, $params['SUB_AMOUNT'] / 100);
+
+ $this->assertArrayHasKey('ECOM_SHIPTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_SHIPTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('ECOM_BILLTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_BILLTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('OWNERTOWN', $params);
+ $this->assertEquals('Leipzig', $params['OWNERTOWN']);
+
+ $this->assertArrayHasKey('SUB_ENDDATE', $params);
+ $this->assertEquals('', $params['SUB_ENDDATE']);
+
+
+ // test map unit and adjust frequency:
+
+ $profile->setPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_YEAR)
+ ->setPeriodFrequency(1);
+ $params = $subject->collectProfileParameters($profile);
+
+ $this->assertEquals(12, $params['SUB_PERIOD_NUMBER']);
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_MONTH, $params['SUB_PERIOD_UNIT']
+ );
+
+ $profile->setPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_SEMI_MONTH);
+
+ $params = $subject->collectProfileParameters($profile);
+ $this->assertEquals(2, $params['SUB_PERIOD_NUMBER']);
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_WEEK, $params['SUB_PERIOD_UNIT']
+ );
+
+ $profile->setPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_MONTH);
+
+ $params = $subject->collectProfileParameters($profile);
+ $this->assertEquals(1, $params['SUB_PERIOD_NUMBER']);
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_MONTH, $params['SUB_PERIOD_UNIT']
+ );
+
+ $profile->setPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_DAY);
+
+ $params = $subject->collectProfileParameters($profile);
+ $this->assertEquals(1, $params['SUB_PERIOD_NUMBER']);
+ $this->assertEquals(
+ Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_DAY, $params['SUB_PERIOD_UNIT']
+ );
+
+
+ //test trial use-cases
+
+ $profile = $this->getTestProfile(true);
+
+ $params = $subject->collectProfileParameters($profile, true);
+
+ $this->assertEquals(Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag::PERIOD_UNIT_DAY, $params['SUB_PERIOD_UNIT']);
+
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . $profile->getId() . Netresearch_OPS_Helper_Subscription::TRIAL_SUFFIX ;
+ $this->assertArrayHasKey('SUBSCRIPTION_ID', $params);
+ $this->assertEquals($id, $params['SUBSCRIPTION_ID']);
+
+ $this->assertArrayHasKey('SUB_ORDERID', $params);
+ $this->assertEquals($id, $params['SUB_ORDERID']);
+
+ $this->assertArrayHasKey('ORDERID', $params);
+ $this->assertEquals($id, $params['ORDERID']);
+
+ $this->assertEquals($profile->getTrialBillingAmount()+$profile->getShippingAmount(), $params['SUB_AMOUNT']/100);
+ }
+
+ public function testCollectPaymentParameters()
+ {
+ $subject = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+
+ $payment = $this->getTestPayment();
+
+ $params = $subject->collectPaymentParameters($payment)->toArray();
+
+ $this->assertEquals($params['CN'], 'Olaf');
+ $this->assertEquals($params['ALIAS'], '123');
+ $this->assertEquals($params['OPERATION'], Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION);
+ $this->assertEquals($params['FLAG3D'], 'Y');
+ }
+
+ /**
+ * @return Mage_Sales_Model_Quote_Payment
+ */
+ protected function getTestPayment()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $quote->setRemoteIp('127.0.0.1');
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setAdditionalInformation('alias', '123')
+ ->setAdditionalInformation('CC_CN', 'Olaf')
+ ->setAdditionalInformation('CC_BRAND', 'VISA')
+ ->setMethod(Netresearch_OPS_Model_Payment_Recurring_Cc::CODE)
+ ->setQuote($quote);
+ Mage::app()->getStore()->setConfig('payment/ops_recurring_cc/enabled_3dsecure', 1);
+ return $payment;
+ }
+
+ public function testCollectAllParameters()
+ {
+ $subject = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ $payment = $this->getTestPayment();
+ $profile = $this->getTestProfile();
+
+ $params = $subject->collectAllParameters($payment, $profile);
+
+ $startDate = new DateTime();
+ $this->assertArrayHasKey('SUB_STARTDATE', $params);
+ $this->assertEquals($startDate->format('d/m/Y'), $params['SUB_STARTDATE']);
+
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . $profile->getId();
+ $this->assertArrayHasKey('SUBSCRIPTION_ID', $params);
+ $this->assertEquals($id, $params['SUBSCRIPTION_ID']);
+
+ $this->assertArrayHasKey('SUB_ORDERID', $params);
+ $this->assertEquals($id, $params['SUB_ORDERID']);
+
+ $this->assertArrayHasKey('SUB_COM', $params);
+ $this->assertEquals($params['SUB_COM'], 'abc');
+
+ $this->assertEquals(0, $params['AMOUNT']);
+ $subAmount = $profile->getBillingAmount() + $profile->getTaxAmount() + $profile->getShippingAmount();
+ $this->assertEquals($subAmount, $params['SUB_AMOUNT'] / 100);
+
+ $this->assertArrayHasKey('ECOM_SHIPTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_SHIPTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('ECOM_BILLTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_BILLTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('OWNERTOWN', $params);
+ $this->assertEquals('Leipzig', $params['OWNERTOWN']);
+ $this->assertEquals($params['CN'], 'Olaf');
+ $this->assertEquals($params['ALIAS'], '123');
+ $this->assertEquals($params['ORDERID'], $id);
+ $this->assertEquals($params['OPERATION'], Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION);
+ $this->assertEquals($params['FLAG3D'], 'Y');
+ }
+
+ public function testCollectAllParametersWithTrial()
+ {
+ $subject = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ // test dry run with trial data
+ $payment = $this->getTestPayment();
+ $profile = $this->getTestProfile(true);
+
+ $params = $subject->collectAllParameters($payment, $profile);
+
+ $startDate = new DateTime();
+ $startDate->add(new DateInterval('P1D'));
+ $this->assertArrayHasKey('SUB_STARTDATE', $params);
+ $this->assertEquals($params['SUB_STARTDATE'], $startDate->format('d/m/Y'));
+
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . $profile->getId();
+ $this->assertArrayHasKey('SUBSCRIPTION_ID', $params);
+ $this->assertEquals($id, $params['SUBSCRIPTION_ID']);
+
+ $this->assertArrayHasKey('SUB_ORDERID', $params);
+ $this->assertEquals($id, $params['SUB_ORDERID']);
+
+ $this->assertArrayHasKey('SUB_COM', $params);
+ $this->assertEquals($params['SUB_COM'], 'abc');
+
+ $this->assertEquals(0, $params['AMOUNT']);
+ $subAmount = $profile->getBillingAmount() + $profile->getTaxAmount() + $profile->getShippingAmount();
+ $this->assertEquals($subAmount, $params['SUB_AMOUNT'] / 100);
+
+ $this->assertArrayHasKey('ECOM_SHIPTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_SHIPTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('ECOM_BILLTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_BILLTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('OWNERTOWN', $params);
+ $this->assertEquals('Leipzig', $params['OWNERTOWN']);
+ $this->assertEquals($params['CN'], 'Olaf');
+ $this->assertEquals($params['ALIAS'], '123');
+ $this->assertEquals($params['ORDERID'], $id);
+ $this->assertEquals($params['OPERATION'], Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION);
+ $this->assertEquals($params['FLAG3D'], 'Y');
+ }
+
+ public function testCollectAllParametersForTrial()
+ {
+ $subject = Mage::getModel('ops/payment_recurring_cc_parameterBag');
+ $payment = $this->getTestPayment();
+ $profile = $this->getTestProfile(true);
+
+ $params = $subject->collectAllParametersForTrial($payment, $profile);
+
+ $startDate = new DateTime();
+ $this->assertArrayHasKey('SUB_STARTDATE', $params);
+ $this->assertEquals($params['SUB_STARTDATE'], $startDate->format('d/m/Y'));
+
+ $id = Netresearch_OPS_Helper_Subscription::SUBSCRIPTION_PREFIX . $profile->getId() . Netresearch_OPS_Helper_Subscription::TRIAL_SUFFIX;
+ $this->assertArrayHasKey('SUBSCRIPTION_ID', $params);
+ $this->assertEquals($id, $params['SUBSCRIPTION_ID']);
+
+ $this->assertArrayHasKey('SUB_ORDERID', $params);
+ $this->assertEquals($id, $params['SUB_ORDERID']);
+
+ $this->assertArrayHasKey('SUB_COM', $params);
+ $this->assertEquals($params['SUB_COM'], 'abc');
+
+ $this->assertEquals(0, $params['AMOUNT']);
+ $subAmount = $profile->getTrialBillingAmount() + $profile->getShippingAmount();
+ $this->assertEquals($subAmount, $params['SUB_AMOUNT'] / 100);
+
+ $this->assertArrayHasKey('ECOM_SHIPTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_SHIPTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('ECOM_BILLTO_POSTAL_CITY', $params);
+ $this->assertEquals('Leipzig', $params['ECOM_BILLTO_POSTAL_CITY']);
+
+ $this->assertArrayHasKey('OWNERTOWN', $params);
+ $this->assertEquals('Leipzig', $params['OWNERTOWN']);
+ $this->assertEquals($params['CN'], 'Olaf');
+ $this->assertEquals($params['ALIAS'], '123');
+ $this->assertEquals($params['ORDERID'], $id);
+ $this->assertEquals($params['OPERATION'], Netresearch_OPS_Model_Payment_Abstract::OPS_AUTHORIZE_CAPTURE_ACTION);
+ $this->assertEquals($params['FLAG3D'], 'Y');
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/CcTest.php b/app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/CcTest.php
new file mode 100644
index 0000000..1e8eb15
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/Recurring/CcTest.php
@@ -0,0 +1,582 @@
+
+ */
+class Netresearch_OPS_Test_Model_Payment_Recurring_CcTest extends EcomDev_PHPUnit_Test_Case
+{
+ /**
+ * @return Mage_Sales_Model_Recurring_Profile
+ */
+ protected function getTestProfile()
+ {
+ /** @var Mage_Sales_Model_Recurring_Profile $profile */
+ $profile = Mage::getModel('sales/recurring_profile');
+ $address = Mage::getModel('sales/quote_address');
+ $address->setCity('Leipzig');
+ $quote = Mage::getModel('sales/quote');
+ $quote->setShippingAddress($address);
+ $quote->setBillingAddress($address);
+ $quote->setPayment($this->getTestPayment());
+
+ $profile->setScheduleDescription('abc')
+ ->setPeriodFrequency(1)
+ ->setPeriodMaxCycles(1)
+ ->setMethodCode('ops_recurring_cc')
+ ->setPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_WEEK)
+ ->setOrderItemInfo(array())
+ ->setInitAmount(10)
+ ->setBillingAmount(15)
+ ->setTaxAmount(5)
+ ->setShippingAmount(5)
+ ->setStartDatetime('')
+ ->setQuote($quote)
+ ->setCurrencyCode('EUR')
+ ->setState(Mage_Sales_Model_Recurring_Profile::STATE_UNKNOWN)
+ ->setId(0);
+
+ return $profile;
+ }
+
+ protected function getResponseParams($success)
+ {
+ $params = array(
+ 'subscription_id' => 'SUB-0',
+ 'orderID' => 'SUB-0',
+ 'PAYID' => 12345,
+ 'currency' => 'EUR',
+ 'amount' => 1000
+ );
+ if ($success) {
+ $params['STATUS'] = 9;
+ $params['creation_status'] = Netresearch_OPS_Model_Subscription_Manager::CREATION_SUCCEEDED;
+ } else {
+ $params['STATUS'] = 2;
+ $params['creation_status'] = Netresearch_OPS_Model_Subscription_Manager::CREATION_FAILED;
+ }
+
+ return $params;
+ }
+
+ /**
+ * @return Mage_Sales_Model_Quote_Payment
+ */
+ protected function getTestPayment()
+ {
+ $quote = Mage::getModel('sales/quote');
+ $quote->setRemoteIp('127.0.0.1');
+ $payment = Mage::getModel('sales/quote_payment');
+ $payment->setAdditionalInformation('alias', '123')
+ ->setAdditionalInformation('CC_CN', 'Olaf')
+ ->setAdditionalInformation('CC_BRAND', 'VISA')
+ ->setMethod(Netresearch_OPS_Model_Payment_Recurring_Cc::CODE)
+ ->setQuote($quote);
+ Mage::app()->getStore()->setConfig('payment/ops_recurring_cc/enabled_3dsecure', 1);
+
+ return $payment;
+ }
+
+ public function testValidateRecurringProfile()
+ {
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+
+ $profile = $this->getTestProfile();
+
+ $subject->validateRecurringProfile($profile);
+ }
+
+
+ public function testSubmitRecurringProfileOnlyRegular()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+
+ $params = $this->getResponseParams(true);
+ $this->mockDirectLinkRequest($params);
+
+ $profile = $this->getTestProfile();
+
+ $profile->setInitAmount(0);
+ $paymentInfo = $this->getTestPayment();
+ $subject->submitRecurringProfile($profile, $paymentInfo);
+
+ $this->assertEquals($profile->getReferenceId(), 'SUB-0');
+ $this->assertEquals(serialize($params), $profile->getProfileVendorInfo());
+ }
+
+ /**
+ * @test
+ * @expectedException Exception
+ */
+ public function testSubmitRecurringProfileOnlyRegularWithException()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+
+ $params = $this->getResponseParams(false);
+ $this->mockDirectLinkRequest($params);
+
+ $profile = $this->getTestProfile();
+
+ $profile->setInitAmount(0);
+ $paymentInfo = $this->getTestPayment();
+ $subject->submitRecurringProfile($profile, $paymentInfo);
+
+ $this->assertEquals($profile->getReferenceId(), 'SUB-0');
+ $this->assertEquals(serialize($params), $profile->getProfileVendorInfo());
+ }
+
+ public function testSubmitRecurringProfileWithTrial()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+
+ $params = $this->getResponseParams(true);
+ $this->mockDirectLinkRequest($params);
+
+ $profile = $this->getTestProfile();
+ $profile->setInitAmount(0)
+ ->setTrialBillingAmount(1)
+ ->setTrialPeriodFrequency(5)
+ ->setTrialPeriodMaxCycles(10)
+ ->setTrialPeriodMaxCycles(5)
+ ->setTrialPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_DAY);
+
+ $paymentInfo = $this->getTestPayment();
+ $subject->submitRecurringProfile($profile, $paymentInfo);
+
+ $this->assertEquals($profile->getReferenceId(), 'SUB-0');
+ $this->assertEquals(serialize($params), $profile->getProfileVendorInfo());
+ }
+
+ /**
+ * @test
+ * @expectedException Exception
+ */
+ public function testSubmitRecurringProfileWithTrialWithException()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+
+ $params = $this->getResponseParams(false);
+ $this->mockTwoDirectLinkRequests($this->getResponseParams(true), $params);
+
+ $profile = $this->getTestProfile();
+ $profile->setInitAmount(0)
+ ->setTrialBillingAmount(1)
+ ->setTrialPeriodFrequency(5)
+ ->setTrialPeriodMaxCycles(10)
+ ->setTrialPeriodMaxCycles(5)
+ ->setTrialPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_DAY);
+
+ $paymentInfo = $this->getTestPayment();
+ $subject->submitRecurringProfile($profile, $paymentInfo);
+
+ $this->assertEquals($profile->getReferenceId(), 'SUB-0');
+ $this->assertEquals(serialize($params), $profile->getProfileVendorInfo());
+ }
+
+ public function testSubmitRecurringProfileWithInitialFee()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+
+ $profileMock = $this->getModelMock('sales/recurring_profile', array('getChildOrderIds', 'addOrderRelation'));
+ $profileMock->expects($this->any())
+ ->method('getChildOrderIds')
+ ->will($this->returnSelf());
+ $profileMock->expects($this->any())
+ ->method('addOrderRelation')
+ ->will($this->returnSelf());
+ $this->replaceByMock('model', 'sales/recurring_profile', $profileMock);
+
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('applyStateForOrder'));
+ $paymentHelperMock->expects($this->any())
+ ->method('applyStateForOrder')
+ ->will($this->returnSelf());
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+ $params = $this->getResponseParams(true);
+ $this->mockDirectLinkRequest($params);
+
+ $profile = $this->getTestProfile();
+ $profile->setTrialBillingAmount(1)
+ ->setTrialPeriodFrequency(5)
+ ->setTrialPeriodMaxCycles(10)
+ ->setTrialPeriodMaxCycles(5);
+
+ $paymentInfo = $this->getTestPayment();
+ $subject->submitRecurringProfile($profile, $paymentInfo);
+
+ $this->assertEquals($profile->getReferenceId(), 'SUB-0');
+ $this->assertEquals(serialize($params), $profile->getProfileVendorInfo());
+ }
+
+ /**
+ * @test
+ * @expectedException Exception
+ */
+ public function testGetRecurringProfileDetails()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $subject->getRecurringProfileDetails('abc', new Varien_Object());
+ }
+
+ public function testCanGetRecurringProfileDetails()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $this->assertFalse($subject->canGetRecurringProfileDetails());
+ }
+
+ /**
+ * @test
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Function not supported
+ */
+ public function testUpdateRecurringProfile()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $subject->updateRecurringProfile($this->getTestProfile());
+ }
+
+ /**
+ * @test
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Automatic activation not possible. Please contact our support team.
+ */
+ public function testUpdateRecurringProfileStatusWithActivateException()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_ACTIVE);
+ $subject->updateRecurringProfileStatus($profile);
+
+ }
+
+ public function testUpdateRecurringProfileStatusWithActivate()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $adminMock->expects($this->once())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $adminHtmlMock = $this->getModelMock('adminhtml/session', array('addNotice', 'init'));
+ $adminHtmlMock->expects($this->once())
+ ->method('addNotice');
+ $this->replaceByMock('singleton', 'adminhtml/session', $adminHtmlMock);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_ACTIVE);
+ $subject->updateRecurringProfileStatus($profile);
+ }
+
+ /**
+ * @test
+ */
+ public function testUpdateRecurringProfileStatusWithCancelAsCustomer()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $sessionMock = $this->getModelMock('customer/session', array('getCustomer', 'init'));
+ $customer = new Varien_Object(array('id' => 1));
+ $sessionMock->expects($this->once())
+ ->method('getCustomer')
+ ->will($this->returnValue($customer));
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ $mailModelMock = $this->getModelMock('ops/payment_features_paymentEmail', array('sendSuspendSubscriptionMail'));
+ $mailModelMock->expects($this->once())
+ ->method('sendSuspendSubscriptionMail')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/payment_features_paymentEmail', $mailModelMock);
+
+
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_CANCELED);
+ $profile->setCustomerId(1);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $subject->updateRecurringProfileStatus($profile);
+
+ $this->assertTrue($profile->getOverrideState());
+ $this->assertEquals(Mage_Sales_Model_Recurring_Profile::STATE_PENDING, $profile->getNewState());
+ $this->assertNotNull($sessionMock->getMessages()->getLastAddedMessage());
+ }
+
+ public function testUpdateRecurringProfileStatusWithCancel()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $adminMock->expects($this->once())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $adminHtmlMock = $this->getModelMock('adminhtml/session', array('addNotice', 'init'));
+ $adminHtmlMock->expects($this->once())
+ ->method('addNotice');
+ $this->replaceByMock('singleton', 'adminhtml/session', $adminHtmlMock);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_CANCELED);
+ $subject->updateRecurringProfileStatus($profile);
+ }
+
+ public function testUpdateRecurringProfileStatusWithSuspendAsCustomer()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $sessionMock = $this->getModelMock('customer/session', array('getCustomer', 'init'));
+ $customer = new Varien_Object(array('id' => 1));
+ $sessionMock->expects($this->once())
+ ->method('getCustomer')
+ ->will($this->returnValue($customer));
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ $mailModelMock = $this->getModelMock('ops/payment_features_paymentEmail', array('sendSuspendSubscriptionMail'));
+ $mailModelMock->expects($this->once())
+ ->method('sendSuspendSubscriptionMail')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('model', 'ops/payment_features_paymentEmail', $mailModelMock);
+
+
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_SUSPENDED);
+ $profile->setCustomerId(1);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $subject->updateRecurringProfileStatus($profile);
+
+ $this->assertTrue($profile->getOverrideState());
+ $this->assertEquals(Mage_Sales_Model_Recurring_Profile::STATE_PENDING, $profile->getNewState());
+ $this->assertNotNull($sessionMock->getMessages()->getLastAddedMessage());
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage You are not allowed to suspend this subscription!
+ */
+ public function testUpdateRecurringProfileStatusWithSuspendAsCustomerWithUnAllowedException()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $sessionMock = $this->getModelMock('customer/session', array('getCustomer', 'init'));
+ $customer = new Varien_Object(array('id' => 2));
+ $sessionMock->expects($this->once())
+ ->method('getCustomer')
+ ->will($this->returnValue($customer));
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_SUSPENDED);
+ $profile->setCustomerId(1);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $subject->updateRecurringProfileStatus($profile);
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Could not send suspend mail, please try again or contact our support directly.
+ */
+ public function testUpdateRecurringProfileStatusWithSuspendAsCustomerWithFailedException()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $sessionMock = $this->getModelMock('customer/session', array('getCustomer', 'init'));
+ $customer = new Varien_Object(array('id' => 1));
+ $sessionMock->expects($this->once())
+ ->method('getCustomer')
+ ->will($this->returnValue($customer));
+ $this->replaceByMock('singleton', 'customer/session', $sessionMock);
+
+ $mailModelMock = $this->getModelMock('ops/payment_features_paymentEmail', array('sendSuspendSubscriptionMail'));
+ $mailModelMock->expects($this->once())
+ ->method('sendSuspendSubscriptionMail')
+ ->will($this->returnValue(false));
+ $this->replaceByMock('model', 'ops/payment_features_paymentEmail', $mailModelMock);
+
+
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_SUSPENDED);
+ $profile->setCustomerId(1);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $subject->updateRecurringProfileStatus($profile);
+ }
+
+ public function testUpdateRecurringProfileStatusWithSuspendAsAdmin()
+ {
+ $adminMock = $this->getModelMock('admin/session', array('isLoggedIn', 'init'));
+ $adminMock->expects($this->once())
+ ->method('isLoggedIn')
+ ->will($this->returnValue(true));
+ $this->replaceByMock('singleton', 'admin/session', $adminMock);
+
+ $adminHtmlMock = $this->getModelMock('adminhtml/session', array('addNotice', 'init'));
+ $adminHtmlMock->expects($this->once())
+ ->method('addNotice');
+ $this->replaceByMock('singleton', 'adminhtml/session', $adminHtmlMock);
+
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_SUSPENDED);
+ $subject->updateRecurringProfileStatus($profile);
+ }
+
+ /**
+ * @test
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Expire function not implemented!
+ */
+ public function testUpdateRecurringProfileStatusWithExpireException()
+ {
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState(Mage_Sales_Model_Recurring_Profile::STATE_EXPIRED);
+ $subject->updateRecurringProfileStatus($profile);
+ }
+
+ /**
+ * @test
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage Action for state abc not supported
+ */
+ public function testUpdateRecurringProfileStatusWithNotSupportedException()
+ {
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setNewState('abc');
+ $subject->updateRecurringProfileStatus($profile);
+ }
+
+ public function testIsAvailable()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $items = array();
+ $item1 = Mage::getModel('sales/quote_item');
+ $item1->setData('is_nominal', false);
+ $items[] = $item1;
+ $quote2 = $this->getModelMock('sales/quote', array('getAllVisibleItems'));
+ $quote2->expects($this->any())
+ ->method('getAllVisibleItems')
+ ->will($this->returnValue($items));
+
+ $this->assertFalse($subject->isAvailable($quote2));
+ }
+
+ public function testHasBrandAliasInterfaceSupport()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $this->assertTrue($subject->hasBrandAliasInterfaceSupport());
+ }
+
+ public function testGetOrderPlaceRedirectUrl()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $payment = Mage::getModel('payment/info');
+ $payment->setAdditionalInformation('HTML_ANSWER', 'abc');
+ $this->assertEquals(
+ $subject->getOrderPlaceRedirectUrl($payment),
+ Mage::getModel('ops/config')->get3dSecureRedirectUrl()
+ );
+
+ $payment->setAdditionalInformation('HTML_ANSWER', '');
+ $this->assertFalse($subject->getOrderPlaceRedirectUrl($payment));
+ }
+
+ public function testIsZeroAmountAuthorizationAllowed()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $this->assertFalse($subject->isZeroAmountAuthorizationAllowed());
+ }
+
+ public function testGetBrandsForAliasInterface()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+ $this->assertEquals(
+ $subject->getBrandsForAliasInterface(),
+ 'American Express,Diners Club,MaestroUK,MasterCard,VISA,JCB'
+ );
+ }
+
+ public function testGetterSetters()
+ {
+ /** @var Netresearch_OPS_Model_Payment_Recurring_Cc $subject */
+ $subject = Mage::getModel('ops/payment_recurring_cc');
+
+ $this->assertTrue($subject->getSubscriptionManager() instanceof Netresearch_OPS_Model_Subscription_Manager);
+ $subject->setSubscriptionManager('abc');
+ $this->assertTrue($subject->getSubscriptionManager() === 'abc');
+
+ $this->assertTrue(
+ $subject->getParameterModel() instanceof
+ Netresearch_OPS_Model_Payment_Recurring_Cc_ParameterBag
+ );
+ $subject->setParameterModel('abc');
+ $this->assertTrue($subject->getParameterModel() === 'abc');
+ }
+
+ /**
+ * @param $params
+ */
+ protected function mockDirectLinkRequest($params)
+ {
+ $helperMock = $this->getHelperMock('ops/directlink', array('performDirectLinkRequest'));
+ $helperMock->expects($this->any())
+ ->method('performDirectLinkRequest')
+ ->will($this->returnValue($params));
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+ }
+
+
+ protected function mockTwoDirectLinkRequests($params1, $params2)
+ {
+ $helperMock = $this->getHelperMock('ops/directlink', array('performDirectLinkRequest'));
+ $helperMock->expects($this->any())
+ ->method('performDirectLinkRequest')
+ ->will($this->onConsecutiveCalls($params1, $params2));
+ $this->replaceByMock('helper', 'ops/directlink', $helperMock);
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Payment/objects.xml b/app/code/community/Netresearch/OPS/Test/Model/Payment/objects.xml
new file mode 100644
index 0000000..f1aa46d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Payment/objects.xml
@@ -0,0 +1,4 @@
+
+
+ TzoyMjoiTWFnZV9TYWxlc19Nb2RlbF9RdW90ZSI6MTc6e3M6MTU6IgAqAF9ldmVudFByZWZpeCI7czoxMToic2FsZXNfcXVvdGUiO3M6MTU6IgAqAF9ldmVudE9iamVjdCI7czo1OiJxdW90ZSI7czoxMjoiACoAX2N1c3RvbWVyIjtPOjI4OiJNYWdlX0N1c3RvbWVyX01vZGVsX0N1c3RvbWVyIjoxOTp7czoxNToiACoAX2V2ZW50UHJlZml4IjtzOjg6ImN1c3RvbWVyIjtzOjE1OiIAKgBfZXZlbnRPYmplY3QiO3M6ODoiY3VzdG9tZXIiO3M6MTA6IgAqAF9lcnJvcnMiO2E6MDp7fXM6MTQ6IgAqAF9hdHRyaWJ1dGVzIjtOO3M6MTM6IgAqAF9hZGRyZXNzZXMiO047czoyMzoiACoAX2FkZHJlc3Nlc0NvbGxlY3Rpb24iO047czoxNjoiACoAX2lzRGVsZXRlYWJsZSI7YjoxO3M6MTQ6IgAqAF9pc1JlYWRvbmx5IjtiOjA7czoxNjoiACoAX3Jlc291cmNlTmFtZSI7czoxNzoiY3VzdG9tZXIvY3VzdG9tZXIiO3M6MTI6IgAqAF9yZXNvdXJjZSI7TjtzOjI2OiIAKgBfcmVzb3VyY2VDb2xsZWN0aW9uTmFtZSI7czoyODoiY3VzdG9tZXIvY3VzdG9tZXJfY29sbGVjdGlvbiI7czoxMjoiACoAX2NhY2hlVGFnIjtiOjA7czoxOToiACoAX2RhdGFTYXZlQWxsb3dlZCI7YjoxO3M6MTU6IgAqAF9pc09iamVjdE5ldyI7TjtzOjg6IgAqAF9kYXRhIjthOjE4OntzOjEwOiJ3ZWJzaXRlX2lkIjtzOjE6IjEiO3M6OToiZW50aXR5X2lkIjtzOjE6IjIiO3M6MTQ6ImVudGl0eV90eXBlX2lkIjtzOjE6IjEiO3M6MTY6ImF0dHJpYnV0ZV9zZXRfaWQiO3M6MToiMCI7czo1OiJlbWFpbCI7czoyOToibWFyaW8uYmVocmVuZHRAbmV0cmVzZWFyY2guZGUiO3M6ODoiZ3JvdXBfaWQiO3M6MToiMSI7czoxMjoiaW5jcmVtZW50X2lkIjtzOjA6IiI7czo4OiJzdG9yZV9pZCI7czoxOiIxIjtzOjEwOiJjcmVhdGVkX2F0IjtzOjE5OiIyMDExLTA4LTE2IDEyOjIwOjI4IjtzOjEwOiJ1cGRhdGVkX2F0IjtzOjE5OiIyMDExLTA4LTIyIDA2OjUyOjAxIjtzOjk6ImlzX2FjdGl2ZSI7czoxOiIxIjtzOjk6ImZpcnN0bmFtZSI7czo1OiJNYXJpbyI7czo4OiJsYXN0bmFtZSI7czo4OiJCZWhyZW5kdCI7czoxMzoicGFzc3dvcmRfaGFzaCI7czozNToiZmMwZDZiYzdjZWU1ZmNmMTQwM2VhNGMyYjhmYjAxYjA6WHEiO3M6MTA6ImNyZWF0ZWRfaW4iO3M6NzoiRW5nbGlzaCI7czoxNToiZGVmYXVsdF9iaWxsaW5nIjtzOjE6IjEiO3M6MTY6ImRlZmF1bHRfc2hpcHBpbmciO3M6MToiMSI7czoxMjoidGF4X2NsYXNzX2lkIjtzOjE6IjMiO31zOjE4OiIAKgBfaGFzRGF0YUNoYW5nZXMiO2I6MTtzOjEyOiIAKgBfb3JpZ0RhdGEiO2E6MTc6e3M6MTA6IndlYnNpdGVfaWQiO3M6MToiMSI7czo5OiJlbnRpdHlfaWQiO3M6MToiMiI7czoxNDoiZW50aXR5X3R5cGVfaWQiO3M6MToiMSI7czoxNjoiYXR0cmlidXRlX3NldF9pZCI7czoxOiIwIjtzOjU6ImVtYWlsIjtzOjI5OiJtYXJpby5iZWhyZW5kdEBuZXRyZXNlYXJjaC5kZSI7czo4OiJncm91cF9pZCI7czoxOiIxIjtzOjEyOiJpbmNyZW1lbnRfaWQiO3M6MDoiIjtzOjg6InN0b3JlX2lkIjtzOjE6IjEiO3M6MTA6ImNyZWF0ZWRfYXQiO3M6MTk6IjIwMTEtMDgtMTYgMTI6MjA6MjgiO3M6MTA6InVwZGF0ZWRfYXQiO3M6MTk6IjIwMTEtMDgtMjIgMDY6NTI6MDEiO3M6OToiaXNfYWN0aXZlIjtzOjE6IjEiO3M6OToiZmlyc3RuYW1lIjtzOjU6Ik1hcmlvIjtzOjg6Imxhc3RuYW1lIjtzOjg6IkJlaHJlbmR0IjtzOjEzOiJwYXNzd29yZF9oYXNoIjtzOjM1OiJmYzBkNmJjN2NlZTVmY2YxNDAzZWE0YzJiOGZiMDFiMDpYcSI7czoxMDoiY3JlYXRlZF9pbiI7czo3OiJFbmdsaXNoIjtzOjE1OiJkZWZhdWx0X2JpbGxpbmciO3M6MToiMSI7czoxNjoiZGVmYXVsdF9zaGlwcGluZyI7czoxOiIxIjt9czoxNToiACoAX2lkRmllbGROYW1lIjtzOjk6ImVudGl0eV9pZCI7czoxMzoiACoAX2lzRGVsZXRlZCI7YjowO31zOjEzOiIAKgBfYWRkcmVzc2VzIjtOO3M6OToiACoAX2l0ZW1zIjtOO3M6MTI6IgAqAF9wYXltZW50cyI7TjtzOjE2OiIAKgBfcmVzb3VyY2VOYW1lIjtzOjExOiJzYWxlcy9xdW90ZSI7czoxMjoiACoAX3Jlc291cmNlIjtOO3M6MjY6IgAqAF9yZXNvdXJjZUNvbGxlY3Rpb25OYW1lIjtzOjIyOiJzYWxlcy9xdW90ZV9jb2xsZWN0aW9uIjtzOjEyOiIAKgBfY2FjaGVUYWciO2I6MDtzOjE5OiIAKgBfZGF0YVNhdmVBbGxvd2VkIjtiOjE7czoxNToiACoAX2lzT2JqZWN0TmV3IjtOO3M6ODoiACoAX2RhdGEiO2E6NTE6e3M6OToiZW50aXR5X2lkIjtzOjI6Ijk4IjtzOjg6InN0b3JlX2lkIjtzOjE6IjEiO3M6MTA6ImNyZWF0ZWRfYXQiO3M6MTk6IjIwMTEtMDgtMjIgMTE6MzM6MzMiO3M6MTA6InVwZGF0ZWRfYXQiO3M6MTk6IjIwMTEtMDgtMjIgMTE6MzU6MjYiO3M6MTI6ImNvbnZlcnRlZF9hdCI7czoxOToiMDAwMC0wMC0wMCAwMDowMDowMCI7czo5OiJpc19hY3RpdmUiO3M6MToiMSI7czoxMDoiaXNfdmlydHVhbCI7czoxOiIwIjtzOjE3OiJpc19tdWx0aV9zaGlwcGluZyI7czoxOiIwIjtzOjExOiJpdGVtc19jb3VudCI7czoxOiIxIjtzOjk6Iml0ZW1zX3F0eSI7czo2OiIxLjAwMDAiO3M6MTM6Im9yaWdfb3JkZXJfaWQiO3M6MToiMCI7czoxODoic3RvcmVfdG9fYmFzZV9yYXRlIjtzOjY6IjEuMDAwMCI7czoxOToic3RvcmVfdG9fcXVvdGVfcmF0ZSI7czo2OiIxLjAwMDAiO3M6MTk6ImJhc2VfdG9fZ2xvYmFsX3JhdGUiO3M6NjoiMS4wMDAwIjtzOjE4OiJiYXNlX3RvX3F1b3RlX3JhdGUiO3M6NjoiMS4wMDAwIjtzOjIwOiJnbG9iYWxfY3VycmVuY3lfY29kZSI7czozOiJFVVIiO3M6MTg6ImJhc2VfY3VycmVuY3lfY29kZSI7czozOiJFVVIiO3M6MTk6InN0b3JlX2N1cnJlbmN5X2NvZGUiO3M6MzoiRVVSIjtzOjE5OiJxdW90ZV9jdXJyZW5jeV9jb2RlIjtzOjM6IkVVUiI7czoxMToiZ3JhbmRfdG90YWwiO3M6ODoiMzkwLjcwMDAiO3M6MTY6ImJhc2VfZ3JhbmRfdG90YWwiO3M6ODoiMzkwLjcwMDAiO3M6MTU6ImNoZWNrb3V0X21ldGhvZCI7czowOiIiO3M6MTE6ImN1c3RvbWVyX2lkIjtzOjE6IjIiO3M6MjE6ImN1c3RvbWVyX3RheF9jbGFzc19pZCI7czoxOiIzIjtzOjE3OiJjdXN0b21lcl9ncm91cF9pZCI7czoxOiIxIjtzOjE0OiJjdXN0b21lcl9lbWFpbCI7czoyOToibWFyaW8uYmVocmVuZHRAbmV0cmVzZWFyY2guZGUiO3M6MTU6ImN1c3RvbWVyX3ByZWZpeCI7TjtzOjE4OiJjdXN0b21lcl9maXJzdG5hbWUiO3M6NToiTWFyaW8iO3M6MTk6ImN1c3RvbWVyX21pZGRsZW5hbWUiO047czoxNzoiY3VzdG9tZXJfbGFzdG5hbWUiO3M6ODoiQmVocmVuZHQiO3M6MTU6ImN1c3RvbWVyX3N1ZmZpeCI7TjtzOjEyOiJjdXN0b21lcl9kb2IiO047czoxMzoiY3VzdG9tZXJfbm90ZSI7TjtzOjIwOiJjdXN0b21lcl9ub3RlX25vdGlmeSI7czoxOiIxIjtzOjE3OiJjdXN0b21lcl9pc19ndWVzdCI7czoxOiIwIjtzOjE1OiJjdXN0b21lcl90YXh2YXQiO047czo5OiJyZW1vdGVfaXAiO3M6MTM6IjE5Mi4xNjguMS4xNDgiO3M6MTY6ImFwcGxpZWRfcnVsZV9pZHMiO3M6MDoiIjtzOjE3OiJyZXNlcnZlZF9vcmRlcl9pZCI7czowOiIiO3M6MTM6InBhc3N3b3JkX2hhc2giO047czoxMToiY291cG9uX2NvZGUiO047czo4OiJzdWJ0b3RhbCI7czo4OiIzMjMuMzIwMCI7czoxMzoiYmFzZV9zdWJ0b3RhbCI7czo4OiIzMjMuMzIwMCI7czoyMjoic3VidG90YWxfd2l0aF9kaXNjb3VudCI7czo4OiIzMjMuMzIwMCI7czoyNzoiYmFzZV9zdWJ0b3RhbF93aXRoX2Rpc2NvdW50IjtzOjg6IjMyMy4zMjAwIjtzOjE1OiJnaWZ0X21lc3NhZ2VfaWQiO047czoxMDoiaXNfY2hhbmdlZCI7czoxOiIxIjtzOjE3OiJ0cmlnZ2VyX3JlY29sbGVjdCI7czoxOiIwIjtzOjE3OiJleHRfc2hpcHBpbmdfaW5mbyI7TjtzOjE1OiJjdXN0b21lcl9nZW5kZXIiO047czoxNToieF9mb3J3YXJkZWRfZm9yIjtOO31zOjE4OiIAKgBfaGFzRGF0YUNoYW5nZXMiO2I6MTtzOjEyOiIAKgBfb3JpZ0RhdGEiO047czoxNToiACoAX2lkRmllbGROYW1lIjtzOjk6ImVudGl0eV9pZCI7czoxMzoiACoAX2lzRGVsZXRlZCI7YjowO30=
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Response/TestCase.php b/app/code/community/Netresearch/OPS/Test/Model/Response/TestCase.php
new file mode 100644
index 0000000..0b72848
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Response/TestCase.php
@@ -0,0 +1,62 @@
+
+ * @copyright 2016 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+
+/**
+ * Netresearch_OPS_Test_Model_Response_TestCase
+ *
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @author Christoph Aßmann
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+abstract class Netresearch_OPS_Test_Model_Response_TestCase extends EcomDev_PHPUnit_Test_Case
+{
+ protected function mockOrderConfig()
+ {
+ $configMock = $this->getModelMock('sales/order_config', array('getDefaultStatus'));
+ $configMock
+ ->expects($this->any())
+ ->method('getDefaultStatus')
+ ->will($this->returnArgument(0));
+ $this->replaceByMock('singleton', 'sales/order_config', $configMock);
+ }
+
+ /**
+ * Assert order confirmation email being (not) sent.
+ *
+ * @param PHPUnit_Framework_MockObject_Matcher_Invocation $matcher
+ */
+ protected function mockEmailHelper(PHPUnit_Framework_MockObject_Matcher_Invocation $matcher)
+ {
+ $helperMock = $this->getHelperMock('ops/data', array('sendTransactionalEmail'));
+ $helperMock
+ ->expects($matcher)
+ ->method('sendTransactionalEmail')
+ ->with($this->isInstanceOf('Mage_Sales_Model_Order'));
+ $this->replaceByMock('helper', 'ops/data', $helperMock);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest.php b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest.php
new file mode 100644
index 0000000..30dcb62
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest.php
@@ -0,0 +1,267 @@
+mockEmailHelper($this->never());
+
+ $order = Mage::getModel('sales/order')->load(25);
+ $response = array(
+ 'status' => 2,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Type_Capture $handler */
+ $handler = Mage::getModel('ops/response_type_authorize');
+ $handler->handleResponse($response, $order->getPayment()->getMethodInstance(), false);
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage 500 is not a authorize status!
+ */
+ public function testExceptionThrownForNoAuthorizeStatus()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $order = Mage::getModel('sales/order')->load(25);
+ $response = array(
+ 'status' => 500,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Type_Capture $handler */
+ $handler = Mage::getModel('ops/response_type_authorize');
+ $handler->handleResponse($response, $order->getPayment()->getMethodInstance(), false);
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPendingPaymentAndIntermediate()
+ {
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(28);
+
+ $response = array(
+ 'status' => 51,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPaymentReviewAndFinal()
+ {
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(26);
+
+ $response = array(
+ 'status' => 5,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $payment = $order->getPayment()->getMethodInstance();
+ $handler->processResponse($response, $payment);
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPaymentReviewAndIntermediate()
+ {
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(26);
+
+ $response = array(
+ 'status' => 51,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPaymentReviewAndFinalDeclined()
+ {
+ $this->mockEmailHelper($this->never());
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(26);
+
+ $response = array(
+ 'status' => 2,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ $order->getPayment()->setAdditionalInformation('status', 46);
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_CANCELED, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPendingPaymentAndFinal()
+ {
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(29);
+ $response = array(
+ 'status' => 5,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPendingPaymentAndSuspectedFraudStatus()
+ {
+ $this->mockEmailHelper($this->once());
+ $order = Mage::getModel('sales/order')->load(30);
+
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT,
+ 'payid' => 12345678,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW, $order->getState());
+ $this->assertEquals(Mage_Sales_Model_Order::STATUS_FRAUD, $order->getStatus());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPaymentReviewAndSuspectedFraudStatus()
+ {
+ $this->mockEmailHelper($this->once());
+
+ $order = Mage::getModel('sales/order')->load(31);
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT,
+ 'payid' => 1234567897,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW, $order->getState());
+ $this->assertEquals(Mage_Sales_Model_Order::STATUS_FRAUD, $order->getStatus());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ public function testStatusAuthorizationUnclear()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $order = Mage::getModel('sales/order')->setState(Mage_Sales_Model_Order::STATE_NEW);
+ $payment = Mage::getModel('sales/order_payment')->setMethod('ops_cc');
+ $order->setPayment($payment);
+
+ $response = array(
+ 'status' => 52,
+ 'payid' => 12345678,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance(), false);
+
+ $this->assertEquals(true, $payment->getIsTransactionPending());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest/fixtures/orders.yaml
new file mode 100644
index 0000000..b25d4fe
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/AuthorizeTest/fixtures/orders.yaml
@@ -0,0 +1,239 @@
+tables:
+ sales/order:
+ - entity_id: 25
+ increment_id: 100000025
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 10
+
+ - entity_id: 26
+ increment_id: 100000026
+ shipping_address_id: 43
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'payment_review'
+ status: 'payment_review'
+ quote_id: 26
+
+ - entity_id: 27
+ increment_id: 100000027
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+
+ - entity_id: 28
+ increment_id: 100000028
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 28
+
+ - entity_id: 29
+ increment_id: 100000029
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 29
+
+ - entity_id: 30
+ increment_id: 100000030
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 30
+
+ - entity_id: 31
+ increment_id: 100000031
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'payment_review'
+ status: 'payment_review'
+ quote_id: 31
+
+
+
+ sales/quote:
+ - entity_id: 25
+ parent_id: 25
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 26
+ parent_id: 26
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 27
+ parent_id: 27
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 28
+ parent_id: 28
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 29
+ parent_id: 29
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 30
+ parent_id: 30
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 31
+ parent_id: 31
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+
+
+
+
+
+ sales/quote_payment:
+ - payment_id: 25
+ quote_id: 25
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 26
+ quote_id: 26
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+
+ - payment_id: 27
+ quote_id: 27
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:9:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 30
+ quote_id: 30
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:9:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 31
+ quote_id: 31
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:9:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+
+
+ sales/order_payment:
+ - entity_id: 25
+ parent_id: 25
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 26
+ parent_id: 26
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 27
+ parent_id: 27
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 28
+ parent_id: 28
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 29
+ parent_id: 29
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 30
+ parent_id: 30
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 31
+ parent_id: 31
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 25
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 26
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest.php b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest.php
new file mode 100644
index 0000000..154478e
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest.php
@@ -0,0 +1,188 @@
+
+ */
+class Netresearch_OPS_Test_Model_Response_Type_CaptureTest
+ extends Netresearch_OPS_Test_Model_Response_TestCase
+{
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPaymentReviewAndIntermediate()
+ {
+ $this->mockEmailHelper($this->once());
+
+ $order = Mage::getModel('sales/order')->load(26);
+
+ $response = array(
+ 'status' => 91,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPendingPaymentAndIntermediate()
+ {
+ $this->mockEmailHelper($this->once());
+
+ $order = Mage::getModel('sales/order')->load(25);
+
+ $response = array(
+ 'status' => 91,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PAYMENT_REVIEW, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPaymentReviewAndFinal()
+ {
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(26);
+
+ $response = array(
+ 'status' => 9,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PROCESSING, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testHandleResponseWithPendingPaymentAndFinal()
+ {
+ $this->mockEmailHelper($this->once());
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(25);
+ $order->setBaseGrandTotal(33.33);
+
+ $response = array(
+ 'status' => 9,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PROCESSING, $order->getState());
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertNotEmpty($order->getInvoiceCollection());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ * @expectedException Mage_Core_Exception
+ */
+ public function testExceptionThrown()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $order = Mage::getModel('sales/order')->load(25);
+
+ $response = array(
+ 'status' => 43,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Type_Capture $handler */
+ $handler = Mage::getModel('ops/response_type_capture');
+ $handler->handleResponse($response, $order->getPayment()->getMethodInstance());
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testAbortBecauseSameStatus()
+ {
+ $this->mockEmailHelper($this->never());
+
+ $order = Mage::getModel('sales/order')->load(27);
+ $order->getPayment()->setAdditionalInformation('status', 9);
+
+ $response = array(
+ 'status' => 9,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ $order->getPayment()->setLastTransId($response['payid'].'/'.$response['payidsub']);
+
+ /** @var Netresearch_OPS_Model_Response_Type_Capture $handler */
+ $handler = Mage::getModel('ops/response_type_capture');
+ $handler->handleResponse($response, $order->getPayment()->getMethodInstance());
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, $order->getState());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest/fixtures/orders.yaml
new file mode 100644
index 0000000..b85e560
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/CaptureTest/fixtures/orders.yaml
@@ -0,0 +1,135 @@
+tables:
+ sales/order:
+ - entity_id: 25
+ increment_id: 100000025
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 10
+
+ - entity_id: 26
+ increment_id: 100000026
+ shipping_address_id: 43
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'payment_review'
+ status: 'payment_review'
+ quote_id: 26
+
+ - entity_id: 27
+ increment_id: 100000027
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+
+
+ sales/quote:
+ - entity_id: 25
+ parent_id: 25
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 26
+ parent_id: 26
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 27
+ parent_id: 27
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+
+
+ sales/quote_payment:
+ - payment_id: 25
+ quote_id: 25
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 26
+ quote_id: 26
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 27
+ quote_id: 27
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:9:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+
+
+ sales/order_payment:
+ - entity_id: 25
+ parent_id: 25
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 26
+ parent_id: 26
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 27
+ parent_id: 27
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 25
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 26
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest.php b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest.php
new file mode 100644
index 0000000..b0861bc
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest.php
@@ -0,0 +1,274 @@
+
+ */
+?>
+load(25);
+ $response = array(
+ 'status' => 43,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Type_Capture $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage 2 is not a refund status!
+ */
+ public function testExceptionThrownDueToNoRefundStatus()
+ {
+ /** @var Netresearch_OPS_Model_Payment_IDeal $instance */
+
+ $order = Mage::getModel('sales/order')->load(25);
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Netresearch_OPS_Model_Response_Type_Capture $handler */
+ $handler = Mage::getModel('ops/response_type_refund');
+ $handler->handleResponse($response, $order->getPayment()->getMethodInstance());
+ }
+
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testAbortBecauseSameStatus()
+ {
+ $order = Mage::getModel('sales/order')->load(27);
+ $order->getPayment()->setAdditionalInformation('status', 8);
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::REFUNDED,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+ $order->getPayment()->setLastTransId($response['payid'].'/'.$response['payidsub']);
+ /** @var Netresearch_OPS_Model_Response_Type_Capture $handler */
+ $handler = Mage::getModel('ops/response_type_refund');
+ $handler->handleResponse($response, $order->getPayment()->getMethodInstance());
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PENDING_PAYMENT, $order->getState());
+ }
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testCreditMemoStateOpenRefundSuccess()
+ {
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(27);
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::REFUNDED,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+ $order->setBillingAddress(Mage::getModel('sales/order_address'));
+ $invoice = Mage::getModel('sales/order_invoice');
+ $invoice->setOrder($order);
+ $creditMemo = Mage::getModel('sales/order_creditmemo');
+ $creditMemo->setInvoice($invoice);
+ $creditMemo->setId('1234567/3');
+ $creditMemo->setOrder($order);
+ $creditMemo->setState(Mage_Sales_Model_Order_Creditmemo::STATE_OPEN);
+ $creditMemoMock = $this->getModelMock('sales/order_creditmemo', array('load'));
+ $creditMemoMock->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($creditMemo));
+ $order->getPayment()->setOrder($order);
+
+ $this->replaceByMock('model', 'sales/order_creditmemo', $creditMemoMock);
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order_Creditmemo::STATE_REFUNDED, $creditMemo->getState());
+
+ }
+
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testCreditMemoStateOpenRefundRefused()
+ {
+ $this->mockOrderConfig();
+
+ $creditMemo = Mage::getModel('sales/order_creditmemo')->load(122);
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::REFUND_REFUSED,
+ 'payid' => 1234567,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ $creditMemoMock = $this->getModelMock('sales/order_creditmemo', array('save', 'cancel', 'load'));
+ $creditMemoMock->expects($this->any())
+ ->method('save')
+ ->will($this->returnSelf());
+ $creditMemoMock->expects($this->any())
+ ->method('cancel')
+ ->will($this->returnSelf());
+ $creditMemoMock->expects($this->any())
+ ->method('load')
+ ->will($this->returnValue($creditMemo));
+ $this->replaceByMock('model', 'sales/order_creditmemo', $creditMemoMock);
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $creditMemo->getOrder()->getPayment()->getMethodInstance());
+
+ $this->assertEquals(Mage_Sales_Model_Order::STATE_PROCESSING, $creditMemo->getOrder()->getState());
+ $this->assertEquals(Mage_Sales_Model_Order_Creditmemo::STATE_CANCELED, $creditMemo->getState());
+ }
+
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testCreditMemoRefundFinalState()
+ {
+ $this->mockOrderConfig();
+
+ $order = Mage::getModel('sales/order')->load(25);
+
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::REFUNDED,
+ 'payid' => 12345679,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Mage_Sales_Model_Order_Invoice $invoice */
+ $invoice = $order->getInvoiceCollection()->getFirstItem();
+ $creditMemoMock = $this->getModelMock('sales/order_creditmemo', array('getInvoice'));
+ $creditMemoMock->expects($this->any())
+ ->method('getInvoice')
+ ->will($this->returnValue($invoice));
+
+ $this->replaceByMock('model', 'sales/order_creditmemo', $creditMemoMock);
+
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $order->getPayment()->getMethodInstance());
+
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertNotEmpty($order->getInvoiceCollection());
+ $this->assertEquals($response['status'], $order->getPayment()->getAdditionalInformation('status'));
+
+ }
+
+
+ /**
+ * @test
+ * @loadFixture orders.yaml
+ */
+ public function testCreditMemoRefundPendingState()
+ {
+ $this->mockOrderConfig();
+
+ $creditMemo = Mage::getModel('sales/order_creditmemo');
+
+ $paymentMock = $this->getModelMock('sales/order_payment', array('getCreatedCreditMemo'));
+ $paymentMock->expects($this->any())
+ ->method('getCreatedCreditMemo')
+ ->will($this->returnValue($creditMemo));
+ $this->replaceByMock('model', 'sales/order_payment', $paymentMock);
+
+
+ $payment = Mage::getModel('sales/order_payment')->load(25);
+ $order = Mage::getModel('sales/order')->load(25);
+ $payment->setOrder($order);
+
+ $response = array(
+ 'status' => Netresearch_OPS_Model_Status::REFUND_PENDING,
+ 'payid' => 1234567534,
+ 'payidsub' => 3,
+ 'amount' => 33.33
+ );
+
+ /** @var Mage_Sales_Model_Order_Invoice $invoice */
+ $invoice = Mage::getModel('sales/order_invoice');
+ $creditMemoMock = $this->getModelMock('sales/order_creditmemo', array('getInvoice'));
+ $creditMemoMock->expects($this->any())
+ ->method('getInvoice')
+ ->will($this->returnValue($invoice));
+
+ $this->replaceByMock('model', 'sales/order_creditmemo', $creditMemoMock);
+
+
+ $transactionMock = $this->getModelMock('core/resource_transaction', array('save'));
+ $transactionMock->expects($this->any())
+ ->method('save')
+ ->will($this->returnSelf());
+ $this->replaceByMock('model', 'core/resource_transaction', $transactionMock);
+
+
+
+ /** @var Netresearch_OPS_Model_Response_Handler $handler */
+ $handler = Mage::getModel('ops/response_handler');
+ $handler->processResponse($response, $payment->getMethodInstance());
+
+
+ $this->assertNotEmpty($order->getAllStatusHistory());
+ $this->assertNotEmpty($order->getInvoiceCollection());
+ $this->assertEquals($response['status'], $payment->getAdditionalInformation('status'));
+ $this->assertEquals(Mage_Sales_Model_Order_Creditmemo::STATE_OPEN, $creditMemo->getState());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest/fixtures/orders.yaml
new file mode 100644
index 0000000..724662a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Response/Type/RefundTest/fixtures/orders.yaml
@@ -0,0 +1,157 @@
+tables:
+ sales/order:
+ - entity_id: 25
+ increment_id: 100000025
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 10
+
+ - entity_id: 26
+ increment_id: 100000026
+ shipping_address_id: 43
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'payment_review'
+ status: 'payment_review'
+ quote_id: 26
+
+ - entity_id: 27
+ increment_id: 100000027
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+
+
+ sales/quote:
+ - entity_id: 25
+ parent_id: 25
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 26
+ parent_id: 26
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 27
+ parent_id: 27
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+
+
+ sales/quote_payment:
+ - payment_id: 25
+ quote_id: 25
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 26
+ quote_id: 26
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 27
+ quote_id: 27
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:9:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+
+
+ sales/order_payment:
+ - entity_id: 25
+ parent_id: 25
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 26
+ parent_id: 26
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+ - entity_id: 27
+ parent_id: 27
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_iDeal'
+
+
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 25
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 26
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ sales/order_item:
+ - item_id: 1
+ order_id: 27
+ qty_ordered: 1
+
+ sales/invoice:
+ - entity_id: 27
+ order_id: 27
+
+ - entity_id: 25
+ order_id: 25
+
+ sales/creditmemo:
+ - entity_id: 122
+ order_id: 27
+ state: 'open'
+ transaction_id: '1234567/3'
+ invoice_id: 27
+
+ sales/creditmemo_item:
+ - entity_id: 1
+ parent_id: 122
+ order_item_id: 1
+ qty: 1
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Source/Cc/AliasInterfaceEnabledTypesTest.php b/app/code/community/Netresearch/OPS/Test/Model/Source/Cc/AliasInterfaceEnabledTypesTest.php
new file mode 100644
index 0000000..8c9f20b
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Source/Cc/AliasInterfaceEnabledTypesTest.php
@@ -0,0 +1,20 @@
+
+ */
+?>
+assertArrayHasKey('VISA', $subject->toOptionArray());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Source/DirectEbanking/BrandsTest.php b/app/code/community/Netresearch/OPS/Test/Model/Source/DirectEbanking/BrandsTest.php
new file mode 100644
index 0000000..3e160c8
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Source/DirectEbanking/BrandsTest.php
@@ -0,0 +1,19 @@
+toOptionArray();
+ $this->assertTrue(is_array($options));
+ $this->assertEquals($options[0]['value'], 'DirectEbanking');
+ $this->assertEquals($options[1]['value'], 'DirectEbankingAT');
+ $this->assertEquals($options[2]['value'], 'DirectEbankingBE');
+ $this->assertEquals($options[3]['value'], 'DirectEbankingCH');
+ $this->assertEquals($options[4]['value'], 'DirectEbankingDE');
+ $this->assertEquals($options[5]['value'], 'DirectEbankingFR');
+ $this->assertEquals($options[6]['value'], 'DirectEbankingGB');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ProductCategoriesTest.php b/app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ProductCategoriesTest.php
new file mode 100644
index 0000000..421e8a7
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ProductCategoriesTest.php
@@ -0,0 +1,51 @@
+toOptionArray();
+ $this->assertTrue(is_array($options));
+ // check for the existence of the keys for order or quote id
+ $this->assertEquals($options[0]['label'], 'Food & gastronomy');
+ $this->assertEquals($options[1]['label'], 'Car & Motorbike');
+ $this->assertEquals($options[2]['label'], 'Culture & leisure');
+ $this->assertEquals($options[3]['label'], 'Home & garden');
+ $this->assertEquals($options[4]['label'], 'Appliances');
+ $this->assertEquals($options[5]['label'], 'Auctions and bulk purchases');
+ $this->assertEquals($options[6]['label'], 'Flowers & gifts');
+ $this->assertEquals($options[7]['label'], 'Computer & software');
+ $this->assertEquals($options[8]['label'], 'Health & beauty');
+ $this->assertEquals($options[9]['label'], 'Services for individuals');
+ $this->assertEquals($options[10]['label'], 'Services for professionals');
+ $this->assertEquals($options[11]['label'], 'Sports');
+ $this->assertEquals($options[12]['label'], 'Clothing & accessories');
+ $this->assertEquals($options[13]['label'], 'Travel & tourism');
+ $this->assertEquals($options[14]['label'], 'Hifi, photo & video');
+ $this->assertEquals($options[15]['label'], 'Telephony & communication');
+ $this->assertEquals($options[16]['label'], 'Jewelry & precious metals');
+ $this->assertEquals($options[17]['label'], 'Baby articles and accessories');
+ $this->assertEquals($options[18]['label'], 'Sound & light');
+ $this->assertEquals($options[0]['value'], 1);
+ $this->assertEquals($options[1]['value'], 2);
+ $this->assertEquals($options[2]['value'], 3);
+ $this->assertEquals($options[3]['value'], 4);
+ $this->assertEquals($options[4]['value'], 5);
+ $this->assertEquals($options[5]['value'], 6);
+ $this->assertEquals($options[6]['value'], 7);
+ $this->assertEquals($options[7]['value'], 8);
+ $this->assertEquals($options[8]['value'], 9);
+ $this->assertEquals($options[9]['value'], 10);
+ $this->assertEquals($options[10]['value'], 11);
+ $this->assertEquals($options[11]['value'], 12);
+ $this->assertEquals($options[12]['value'], 13);
+ $this->assertEquals($options[13]['value'], 14);
+ $this->assertEquals($options[14]['value'], 15);
+ $this->assertEquals($options[15]['value'], 16);
+ $this->assertEquals($options[16]['value'], 17);
+ $this->assertEquals($options[17]['value'], 18);
+ $this->assertEquals($options[18]['value'], 19);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ShipMethodTypeTest.php b/app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ShipMethodTypeTest.php
new file mode 100644
index 0000000..b989a8d
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Source/Kwixo/ShipMethodTypeTest.php
@@ -0,0 +1,25 @@
+toOptionArray();
+ $this->assertTrue(is_array($options));
+ // check for the existence of the keys for order or quote id
+ $this->assertEquals($options[0]['label'], '--Please select--');
+ $this->assertEquals($options[1]['label'], 'Pick up at merchant');
+ $this->assertEquals($options[2]['label'], 'Collection point (Kiala...)');
+ $this->assertEquals($options[3]['label'], 'Collect at airport, train station or travel agency');
+ $this->assertEquals($options[4]['label'], 'Transporter (La Poste, UPS...)');
+ $this->assertEquals($options[5]['label'], 'Download');
+ $this->assertEquals($options[0]['value'], '');
+ $this->assertEquals($options[1]['value'], 1);
+ $this->assertEquals($options[2]['value'], 2);
+ $this->assertEquals($options[3]['value'], 3);
+ $this->assertEquals($options[4]['value'], 4);
+ $this->assertEquals($options[5]['value'], 5);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Source/ModeTest.php b/app/code/community/Netresearch/OPS/Test/Model/Source/ModeTest.php
new file mode 100644
index 0000000..df36bae
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Source/ModeTest.php
@@ -0,0 +1,21 @@
+toOptionArray();
+ $this->assertTrue(is_array($options));
+ $this->assertEquals(Netresearch_OPS_Model_Source_Mode::TEST, $options[0]['value']);
+ $this->assertEquals(Netresearch_OPS_Model_Source_Mode::PROD, $options[1]['value']);
+ $this->assertEquals(Netresearch_OPS_Model_Source_Mode::CUSTOM, $options[2]['value']);
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Source/OrderReferenceTest.php b/app/code/community/Netresearch/OPS/Test/Model/Source/OrderReferenceTest.php
new file mode 100644
index 0000000..9b43536
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Source/OrderReferenceTest.php
@@ -0,0 +1,22 @@
+toOptionArray();
+ $this->assertTrue(is_array($options));
+ // check for the existence of the keys for order or quote id
+ $this->assertEquals($options[0]['value'], Netresearch_OPS_Model_Payment_Abstract::REFERENCE_QUOTE_ID);
+ $this->assertEquals($options[1]['value'], Netresearch_OPS_Model_Payment_Abstract::REFERENCE_ORDER_ID);
+ }
+
+}
+
+
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest.php b/app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest.php
new file mode 100644
index 0000000..86d4498
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest.php
@@ -0,0 +1,311 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Test_Model_Status_UpdateTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected function mockSessions()
+ {
+ $sessionMock = $this->getModelMock('admin/session', array());
+ $sessionMock->disableOriginalConstructor();
+ $this->replaceByMock('singleton', 'admin/session', $sessionMock);
+ }
+
+ public function testNoUpdateForNonOpsPayments()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('checkmo');
+ $order->setPayment($payment);
+ $statusUpdateApi = Mage::getModel('ops/status_update');
+ $statusUpdateApi->updateStatusFor($order);
+ $this->assertNull($statusUpdateApi->getOrder());
+ }
+
+ public function testBuildParamsForOpsOrderWithOrderId()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_paypal');
+ $order->setPayment($payment);
+ $orderHelperMock = $this->getHelperMock('ops/order', array('getOpsOrderId'));
+ $orderHelperMock->expects($this->once())
+ ->method('getOpsOrderId')
+ ->with($order, true)
+ ->will($this->returnValue('#1000000'));
+
+ $statusUpdateApiMock = $this->getModelMock('ops/status_update', array('performRequest', 'updatePaymentStatus'));
+ $statusUpdateApiMock->setOrderHelper($orderHelperMock);
+ $statusUpdateApiMock->updateStatusFor($order);
+ $requestParams = $statusUpdateApiMock->getRequestParams();
+ $this->assertArrayHasKey('ORDERID', $requestParams);
+ $this->assertEquals('#1000000', $requestParams['ORDERID']);
+ }
+
+ public function testBuildParamsForOpsOrderWithQuoteId()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_directDebit');
+ $order->setPayment($payment);
+ $orderHelperMock = $this->getHelperMock('ops/order', array('getOpsOrderId'));
+ $orderHelperMock->expects($this->once())
+ ->method('getOpsOrderId')
+ ->with($order, false)
+ ->will($this->returnValue('100'));
+
+ $statusUpdateApiMock = $this->getModelMock('ops/status_update', array('performRequest', 'updatePaymentStatus'));
+ $statusUpdateApiMock->setOrderHelper($orderHelperMock);
+ $statusUpdateApiMock->updateStatusFor($order);
+ $requestParams = $statusUpdateApiMock->getRequestParams();
+ $this->assertArrayHasKey('ORDERID', $requestParams);
+ $this->assertEquals('100', $requestParams['ORDERID']);
+ }
+
+ public function testBuildParamsForOpsOrderWithPayId()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_directDebit');
+ $payment->setAdditionalInformation('paymentId', 4711);
+ $order->setPayment($payment);
+
+ $statusUpdateApiMock = $this->getModelMock('ops/status_update', array('performRequest', 'updatePaymentStatus'));
+ $statusUpdateApiMock->updateStatusFor($order);
+ $requestParams = $statusUpdateApiMock->getRequestParams();
+ $this->assertArrayHasKey('PAYID', $requestParams);
+ $this->assertEquals(4711, $requestParams['PAYID']);
+ }
+
+ public function testPerformRequestWithPayId()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_directDebit');
+ $payment->setAdditionalInformation('paymentId', 4711);
+ $order->setPayment($payment);
+
+ $statusUpdateApiMock = $this->getModelMock('ops/status_update', array('updatePaymentStatus'));
+ $directLinkApiMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkApiMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ array(
+ 'PAYID' => 4711
+ ),
+ Mage::getModel('ops/config')->getDirectLinkMaintenanceApiPath($order->getStoreId()),
+ $order->getStoreId()
+ )
+ ->will($this->returnValue(array('STATUS' => 5)));
+ $statusUpdateApiMock->setDirectLinkApi($directLinkApiMock);
+ $statusUpdateApiMock->updateStatusFor($order);
+ $opsResponse = $statusUpdateApiMock->getOpsResponse();
+ $this->assertArrayHasKey('STATUS', $opsResponse);
+ $this->assertEquals(5, $opsResponse['STATUS']);
+ }
+
+
+ public function testPerformRequestWithPayIdAndPayIdSub()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_directDebit');
+ $payment->setAdditionalInformation('paymentId', 4711);
+ $payment->setAdditionalInformation('status', 91);
+ $payment->setLastTransId('4711/1');
+ $order->setPayment($payment);
+
+ $statusUpdateApiMock = $this->getModelMock('ops/status_update', array('updatePaymentStatus'));
+ $directLinkApiMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkApiMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ array(
+ 'PAYID' => 4711,
+ 'PAYIDSUB' => 1
+ ),
+ Mage::getModel('ops/config')->getDirectLinkMaintenanceApiPath($order->getStoreId()),
+ $order->getStoreId()
+ )
+ ->will($this->returnValue(array('STATUS' => 5)));
+ $statusUpdateApiMock->setDirectLinkApi($directLinkApiMock);
+ $statusUpdateApiMock->updateStatusFor($order);
+ $opsResponse = $statusUpdateApiMock->getOpsResponse();
+ $this->assertArrayHasKey('STATUS', $opsResponse);
+ $this->assertEquals(5, $opsResponse['STATUS']);
+ }
+
+ public function testPerformRequestWithPayIdAndPayIdSubForRefund()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_directDebit');
+ $payment->setAdditionalInformation('paymentId', 4711);
+ $payment->setAdditionalInformation('status', 81);
+ $payment->setLastTransId('4711/1');
+ $order->setPayment($payment);
+
+ $statusUpdateApiMock = $this->getModelMock('ops/status_update', array('updatePaymentStatus'));
+ $directLinkApiMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkApiMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ array(
+ 'PAYID' => 4711,
+ 'PAYIDSUB' => 1,
+ ),
+ Mage::getModel('ops/config')->getDirectLinkMaintenanceApiPath($order->getStoreId()),
+ $order->getStoreId()
+ )
+ ->will($this->returnValue(array('STATUS' => 8, 'AMOUNT' => 1,)));
+
+ $statusUpdateApiMock->setDirectLinkApi($directLinkApiMock);
+ $statusUpdateApiMock->updateStatusFor($order);
+ $opsResponse = $statusUpdateApiMock->getOpsResponse();
+ $this->assertArrayHasKey('STATUS', $opsResponse);
+ $this->assertEquals(8, $opsResponse['STATUS']);
+ $this->assertArrayHasKey('AMOUNT', $opsResponse);
+ $this->assertArrayHasKey('amount', $opsResponse);
+ $this->assertEquals(1, $opsResponse['AMOUNT']);
+ $this->assertEquals($opsResponse['amount'], $opsResponse['AMOUNT']);
+ }
+
+ public function testUpdatePaymentStatusWithoutStatusChange()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_directDebit');
+ $payment->setAdditionalInformation('paymentId', 4711);
+ $payment->setAdditionalInformation('status', Netresearch_OPS_Model_Status::REFUNDED);
+ $order->setPayment($payment);
+
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment'));
+ $paymentHelperMock->expects($this->never())
+ ->method('saveOpsStatusToPayment')
+ ->will($this->returnValue('foo'));
+ ;
+
+ // no email on refund response type
+ $dataHelperMock = $this->getHelperMock('ops/data', array('sendTransactionalEmail'));
+ $dataHelperMock
+ ->expects($this->never())
+ ->method('sendTransactionalEmail')
+ ->with($this->isInstanceOf('Mage_Sales_Model_Order'));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+
+
+ $statusUpdateApi = Mage::getModel('ops/status_update');
+ $directLinkApiMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkApiMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ array(
+ 'PAYID' => 4711,
+ ),
+ Mage::getModel('ops/config')->getDirectLinkMaintenanceApiPath($order->getStoreId()),
+ $order->getStoreId()
+ )
+ ->will($this->returnValue(array('STATUS' => Netresearch_OPS_Model_Status::REFUNDED,)));
+
+ $adminSessionMock = $this->getModelMock('adminhtml/session', array('init', 'save', 'addNotice'));
+ $statusUpdateApi->setMessageContainer($adminSessionMock);
+ $statusUpdateApi->setPaymentHelper($paymentHelperMock);
+ $statusUpdateApi->setDirectLinkApi($directLinkApiMock);
+ $statusUpdateApi->updateStatusFor($order);
+ $opsResponse = $statusUpdateApi->getOpsResponse();
+ $this->assertArrayHasKey('STATUS', $opsResponse);
+ $this->assertEquals(Netresearch_OPS_Model_Status::REFUNDED, $opsResponse['STATUS']);
+ }
+
+ public function testUpdatePaymentStatusWithStatusChange()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = $this->getModelMock('sales/order_payment', array('save'));
+ $payment->setMethod('ops_directDebit');
+ $payment->setAdditionalInformation('paymentId', 4711);
+ $payment->setAdditionalInformation('status', 5);
+ $order->setPayment($payment);
+ $response = array('STATUS' => 91,);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment'));
+ $paymentHelperMock->expects($this->any())
+ ->method('saveOpsStatusToPayment')
+ ->with($payment, $response);
+
+ $dataHelperMock = $this->getHelperMock('ops/data', array('sendTransactionalEmail'));
+ $dataHelperMock
+ ->expects($this->once())
+ ->method('sendTransactionalEmail')
+ ->with($this->isInstanceOf('Mage_Sales_Model_Order'));
+ $this->replaceByMock('helper', 'ops/data', $dataHelperMock);
+
+ $adminSessionMock = $this->getModelMock('adminhtml/session', array('init', 'save', 'addSuccess'));
+
+ $statusUpdateApi = Mage::getModel('ops/status_update');
+ $statusUpdateApi->setMessageContainer($adminSessionMock);
+ $directLinkApiMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkApiMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ array(
+ 'PAYID' => 4711,
+ ),
+ Mage::getModel('ops/config')->getDirectLinkMaintenanceApiPath($order->getStoreId()),
+ $order->getStoreId()
+ )
+ ->will($this->returnValue($response));
+
+ $statusUpdateApi->setPaymentHelper($paymentHelperMock);
+ $statusUpdateApi->setDirectLinkApi($directLinkApiMock);
+
+ $statusUpdateApi->updateStatusFor($order);
+ $opsResponse = $statusUpdateApi->getOpsResponse();
+ $this->assertArrayHasKey('STATUS', $opsResponse);
+ $this->assertEquals(91, $opsResponse['STATUS']);
+
+ }
+
+ public function testUpdatePaymentStatusWithStatusChangeOnInitialRequest()
+ {
+ $order = Mage::getModel('sales/order');
+ $payment = Mage::getModel('sales/order_payment');
+ $payment->setMethod('ops_directDebit');
+ $order->setPayment($payment);
+ $response = array('STATUS' => 91,);
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('saveOpsStatusToPayment', 'applyStateForOrder'));
+ $paymentHelperMock->expects($this->any())
+ ->method('saveOpsStatusToPayment')
+ ->with($payment, $response);
+
+ $paymentHelperMock->expects($this->any())
+ ->method('applyStateForOrder')
+ ->with($order, $response);
+ $adminSessionMock = $this->getModelMock('adminhtml/session', array('init', 'save', 'addSuccess'));
+ $statusUpdateApiMock = Mage::getModel('ops/status_update');
+ $statusUpdateApiMock->setMessageContainer($adminSessionMock);
+ $directLinkApiMock = $this->getModelMock('ops/api_directlink', array('performRequest'));
+ $directLinkApiMock->expects($this->once())
+ ->method('performRequest')
+ ->with(
+ array(
+ 'ORDERID' => Mage::getModel('ops/config')->getConfigData('devprefix') . '',
+ ),
+ Mage::getModel('ops/config')->getDirectLinkMaintenanceApiPath($order->getStoreId()),
+ $order->getStoreId()
+ )
+ ->will($this->returnValue($response));
+
+
+ $statusUpdateApiMock->setPaymentHelper($paymentHelperMock);
+ $statusUpdateApiMock->setDirectLinkApi($directLinkApiMock);
+
+ $statusUpdateApiMock->updateStatusFor($order);
+ $opsResponse = $statusUpdateApiMock->getOpsResponse();
+ $this->assertArrayHasKey('STATUS', $opsResponse);
+ $this->assertEquals(91, $opsResponse['STATUS']);
+
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest/fixtures/orders.yaml
new file mode 100644
index 0000000..e99edfd
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Status/UpdateTest/fixtures/orders.yaml
@@ -0,0 +1,135 @@
+tables:
+ sales/order:
+ - entity_id: 25
+ increment_id: 100000025
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'payment_review'
+ status: 'payment_review'
+ quote_id: 10
+
+ - entity_id: 26
+ increment_id: 100000026
+ shipping_address_id: 43
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'payment_review'
+ status: 'payment_review'
+ quote_id: 26
+
+ - entity_id: 27
+ increment_id: 100000027
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+
+
+ sales/quote:
+ - entity_id: 25
+ parent_id: 25
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 26
+ parent_id: 26
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 27
+ parent_id: 27
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+
+
+
+ sales/quote_payment:
+ - payment_id: 25
+ quote_id: 25
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+
+ - payment_id: 26
+ quote_id: 26
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+
+ - payment_id: 27
+ quote_id: 27
+ updated_at: '1970-01-01'
+ method: 'ops_iDeal'
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:9:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+
+
+
+ sales/order_payment:
+ - entity_id: 25
+ parent_id: 25
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+ method: 'ops_iDeal'
+
+ - entity_id: 26
+ parent_id: 26
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+ method: 'ops_iDeal'
+
+ - entity_id: 27
+ parent_id: 27
+ additional_information: 'a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}'
+ method: 'ops_iDeal'
+
+
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 25
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 26
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/StatusTest.php b/app/code/community/Netresearch/OPS/Test/Model/StatusTest.php
new file mode 100644
index 0000000..87eb9b9
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/StatusTest.php
@@ -0,0 +1,122 @@
+assertTrue(Netresearch_OPS_Model_Status::isFinal($status));
+ $status = Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT;
+ $this->assertFalse(Netresearch_OPS_Model_Status::isFinal($status));
+
+ }
+
+ public function testIsIntermediate()
+ {
+ $status = Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT;
+ $this->assertTrue(Netresearch_OPS_Model_Status::isIntermediate($status));
+ $status = Netresearch_OPS_Model_Status::AUTHORIZED;
+ $this->assertFalse(Netresearch_OPS_Model_Status::isIntermediate($status));
+ }
+
+
+ public function testIsCapture()
+ {
+ $captureStatus = array(
+ Netresearch_OPS_Model_Status::PAYMENT_REQUESTED,
+ Netresearch_OPS_Model_Status::PAYMENT_PROCESSING,
+ Netresearch_OPS_Model_Status::PAYMENT_UNCERTAIN,
+ Netresearch_OPS_Model_Status::PAYMENT_REFUSED,
+ Netresearch_OPS_Model_Status::PAYMENT_DECLINED_BY_ACQUIRER,
+ Netresearch_OPS_Model_Status::PAYMENT_PROCESSED_BY_MERCHANT,
+ Netresearch_OPS_Model_Status::REFUND_REVERSED,
+ Netresearch_OPS_Model_Status::PAYMENT_IN_PROGRESS
+ );
+ foreach ($captureStatus as $status) {
+ $this->assertTrue(Netresearch_OPS_Model_Status::isCapture($status));
+ }
+ $this->assertFalse(Netresearch_OPS_Model_Status::isCapture(Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED));
+ }
+
+ public function testIsRefund()
+ {
+ $refundStatus = array(
+ Netresearch_OPS_Model_Status::REFUNDED,
+ Netresearch_OPS_Model_Status::REFUND_PENDING,
+ Netresearch_OPS_Model_Status::REFUND_UNCERTAIN,
+ Netresearch_OPS_Model_Status::REFUND_REFUSED,
+ Netresearch_OPS_Model_Status::REFUNDED_OK,
+ Netresearch_OPS_Model_Status::REFUND_PROCESSED_BY_MERCHANT,
+ );
+ foreach ($refundStatus as $status) {
+ $this->assertTrue(Netresearch_OPS_Model_Status::isRefund($status));
+ }
+ $this->assertFalse(Netresearch_OPS_Model_Status::isCapture(Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED));
+ }
+
+ public function testIsVoid()
+ {
+ $voidStatus = array(
+ Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED,
+ Netresearch_OPS_Model_Status::DELETION_WAITING,
+ Netresearch_OPS_Model_Status::DELETION_UNCERTAIN,
+ Netresearch_OPS_Model_Status::DELETION_REFUSED,
+ Netresearch_OPS_Model_Status::AUTHORIZED_AND_CANCELLED_OK,
+ );
+ foreach ($voidStatus as $status) {
+ $this->assertTrue(Netresearch_OPS_Model_Status::isVoid($status));
+ }
+ $this->assertFalse(Netresearch_OPS_Model_Status::isVoid(Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED));
+ }
+
+
+ public function testIsAuthorize()
+ {
+ $authStatus = array(
+ Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED,
+ Netresearch_OPS_Model_Status::AUTHORIZED,
+ Netresearch_OPS_Model_Status::AUTHORIZED_WAITING_EXTERNAL_RESULT,
+ Netresearch_OPS_Model_Status::AUTHORIZATION_WAITING,
+ Netresearch_OPS_Model_Status::AUTHORIZED_UNKNOWN,
+ Netresearch_OPS_Model_Status::STAND_BY,
+ Netresearch_OPS_Model_Status::OK_WITH_SHEDULED_PAYMENTS,
+ Netresearch_OPS_Model_Status::NOT_OK_WITH_SHEDULED_PAYMENTS,
+ Netresearch_OPS_Model_Status::AUTHORISATION_TO_BE_REQUESTED_MANUALLY
+ );
+ foreach ($authStatus as $status) {
+ $this->assertTrue(Netresearch_OPS_Model_Status::isAuthorize($status));
+ }
+ $this->assertFalse(Netresearch_OPS_Model_Status::isAuthorize(Netresearch_OPS_Model_Status::REFUND_PENDING));
+ }
+
+ public function testIsWaitingStatus()
+ {
+ $waitingStatus = array(
+ Netresearch_OPS_Model_Status::WAITING_CLIENT_PAYMENT,
+ Netresearch_OPS_Model_Status::WAITING_FOR_IDENTIFICATION,
+ Netresearch_OPS_Model_Status::STORED_WAITING_EXTERNAL_RESULT
+ );
+ foreach ($waitingStatus as $status) {
+ $this->assertTrue(Netresearch_OPS_Model_Status::isSpecialStatus($status));
+ }
+ $this->assertFalse(Netresearch_OPS_Model_Status::isSpecialStatus(Netresearch_OPS_Model_Status::REFUND_PENDING));
+ }
+
+
+ public function testCanResendPaymentInfo()
+ {
+ $canResendInfoStatus = array(
+ Netresearch_OPS_Model_Status::NOT_OK_WITH_SHEDULED_PAYMENTS,
+ Netresearch_OPS_Model_Status::CANCELED_BY_CUSTOMER,
+ Netresearch_OPS_Model_Status::AUTHORISATION_DECLINED,
+ Netresearch_OPS_Model_Status::AUTHORISATION_TO_BE_REQUESTED_MANUALLY,
+ Netresearch_OPS_Model_Status::PAYMENT_UNCERTAIN,
+ Netresearch_OPS_Model_Status::PAYMENT_REFUSED,
+ );
+ foreach ($canResendInfoStatus as $status) {
+ $this->assertTrue(Netresearch_OPS_Model_Status::canResendPaymentInfo($status));
+ }
+ $this->assertFalse(Netresearch_OPS_Model_Status::canResendPaymentInfo(Netresearch_OPS_Model_Status::REFUND_PENDING));
+ }
+}
+
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Subscription/ManagerTest.php b/app/code/community/Netresearch/OPS/Test/Model/Subscription/ManagerTest.php
new file mode 100644
index 0000000..5621ea5
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Subscription/ManagerTest.php
@@ -0,0 +1,176 @@
+
+ */
+?>
+assertTrue($subject->getSubscriptionHelper() instanceof Netresearch_OPS_Helper_Subscription);
+ $subject->setSubscriptionHelper($testString);
+ $this->assertEquals($subject->getSubscriptionHelper(), $testString);
+
+ $this->assertTrue($subject->getPaymentHelper() instanceof Netresearch_OPS_Helper_Payment);
+ $subject->setPaymentHelper($testString);
+ $this->assertEquals($subject->getPaymentHelper(), $testString);
+ }
+
+ /**
+ * @return Mage_Sales_Model_Recurring_Profile
+ */
+ protected function getTestProfile()
+ {
+ $profile = Mage::getModel('sales/recurring_profile');
+ $profile->setScheduleDescription('abc')
+ ->setPeriodFrequency(1)
+ ->setPeriodMaxCycles(1)
+ ->setPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_WEEK)
+ ->setInitAmount(10)
+ ->setBillingAmount(15)
+ ->setTaxAmount(5)
+ ->setShippingAmount(5)
+ ->setStartDatetime('')
+ ->setBillingAddressInfo(array('quote_id' => 1))
+ ->setMethodCode(Netresearch_OPS_Model_Payment_Recurring_Cc::CODE)
+ ->setId(0);
+
+ return $profile;
+ }
+
+ /**
+ * @return string[]
+ */
+ protected function getResponseParams()
+ {
+
+ $responseParams = array(
+ 'PAYID' => '123',
+ 'currency' => 'EUR',
+ 'STATUS' => '5',
+ 'orderID' => 'SUB-123',
+ 'amount' => '0'
+ );
+
+ return $responseParams;
+
+ }
+
+ protected function mockDependencies()
+ {
+
+ $profileMock = $this->getModelMock('sales/recurring_profile', array('addOrderRelation'));
+ $profileMock->expects($this->once())
+ ->method('addOrderRelation')
+ ->will($this->returnValue(''));
+ $this->replaceByMock('model', 'sales/recurring_profile', $profileMock);
+
+ $paymentHelperMock = $this->getHelperMock('ops/payment', array('applyStateForOrder'));
+ $paymentHelperMock->expects($this->once())
+ ->method('applyStateForOrder')
+ ->will($this->returnValue(''));
+ $this->replaceByMock('helper', 'ops/payment', $paymentHelperMock);
+
+ $orderMock = $this->getModelMock('sales/order', array('save'));
+ $orderMock->expects($this->any())
+ ->method('save')
+ ->will($this->returnValue(''));
+ $this->replaceByMock('model', 'sales/order', $orderMock);
+
+ $paymentMock = $this->getModelMock(
+ 'sales/order_payment',
+ array('registerAuthorizationNotification', 'registerCaptureNotification')
+ );
+ $paymentMock->expects($this->any())
+ ->method('registerCaptureNotification')
+ ->will($this->returnValue(''));
+ $paymentMock->expects($this->any())
+ ->method('registerAuthorizationNotification')
+ ->will($this->returnValue(''));
+ $this->replaceByMock('model', 'sales/order_payment', $paymentMock);
+ }
+
+ public function testProcessSubscriptionFeedbackWithInitialCreation()
+ {
+ $subject = Mage::getModel('ops/subscription_manager');
+ $profile = $this->getTestProfile();
+ $responseParams = $this->getResponseParams();
+
+ $responseParams['creation_status'] = Netresearch_OPS_Model_Subscription_Manager::CREATION_SUCCEEDED;
+ $responseParams['subscription_id'] = 'test';
+ $result = $subject->processSubscriptionFeedback($responseParams, $profile);
+
+ $this->assertFalse($result);
+ $this->assertEquals($profile->getReferenceId(), 'test');
+ $this->assertEquals($profile->getState(), Mage_Sales_Model_Recurring_Profile::STATE_ACTIVE);
+ }
+
+ public function testProcessSubscriptionFeedbackWithRegularSubscriptionFeedback()
+ {
+ $this->mockDependencies();
+ $subject = Mage::getModel('ops/subscription_manager');
+ $profile = $this->getTestProfile();
+ $responseParams = $this->getResponseParams();
+
+ $result = $subject->processSubscriptionFeedback($responseParams, $profile);
+
+ $this->assertTrue($result instanceof Mage_Sales_Model_Order);
+ $this->assertEquals($result->getShippingAmount(), $profile->getShippingAmount());
+ $this->assertEquals($result->getTaxAmount(), $profile->getTaxAmount());
+ $this->assertEquals($result->getSubtotal(), $profile->getBillingAmount());
+ }
+
+ public function testProcessSubscriptionFeedbackWithTrialSubscriptionFeedback()
+ {
+ /** @var $subject Netresearch_OPS_Model_Subscription_Manager */
+ $this->mockDependencies();
+ $subject = Mage::getModel('ops/subscription_manager');
+ $profile = $this->getTestProfile();
+ $responseParams = $this->getResponseParams();
+ $responseParams['orderID'] = $responseParams['orderID'] . Netresearch_OPS_Helper_Subscription::TRIAL_SUFFIX;
+ $profile->setTrialPeriodUnit(Mage_Sales_Model_Recurring_Profile::PERIOD_UNIT_MONTH)
+ ->setTrialBillingAmount(5)
+ ->setTrialPeriodFrequency(3)
+ ->setTrialPeriodMaxCycles(4)
+ ->setInitAmount(0)
+ ->setOrderItemInfo(array('tax_percent' => 7));
+
+
+ $result = $subject->processSubscriptionFeedback($responseParams, $profile);
+
+ $this->assertTrue($result instanceof Mage_Sales_Model_Order);
+ $this->assertEquals($result->getShippingAmount(), $profile->getShippingAmount());
+ $this->assertEquals($result->getBaseGrandTotal(), $profile->getTrialBillingAmount() + $profile->getShippingAmount());
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Design/BrandsTest.php b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Design/BrandsTest.php
new file mode 100644
index 0000000..1de0549
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Design/BrandsTest.php
@@ -0,0 +1,53 @@
+
+ */
+class Netresearch_OPS_Test_Model_System_Config_Backend_Intersolve_BrandsTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+
+ public function testSave()
+ {
+ $model = Mage::getModel('ops/system_config_backend_intersolve_brands');
+ $invalidData = array(
+ array('brand' => '123', 'value' => '1234'),
+ array('brand' => '123', 'value' => '1234')
+ );
+ $model->setValue($invalidData);
+ $this->setExpectedException('Mage_Core_Exception', 'Brands must be unique');
+ $model->save();
+ $validData = array(
+ array('brand' => '123', 'value' => '1234'),
+ array('brand' => '1234', 'value' => '1234')
+ );
+ $model->setValue($validData);
+ $this->assertTrue(($model->save() instanceof Netresearch_Ops_Model_System_Config_Backend_Intersolve_Brands));
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/EncodingTest.php b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/EncodingTest.php
new file mode 100644
index 0000000..4170b30
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/EncodingTest.php
@@ -0,0 +1,60 @@
+
+ * @copyright 2016 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+
+/**
+ * Netresearch_OPS_Test_Block_System_Config_EncodingTest
+ *
+ * @category OPS
+ * @package Netresearch_OPS
+ * @author Sebastian Ertner
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+class Netresearch_OPS_Test_Model_System_Config_Backend_EncodingTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+ /**
+ * @test
+ */
+ public function testToOptionArray()
+ {
+ /** @var Netresearch_Ops_Model_System_Config_Backend_PaymentLogo $optionModel */
+ $optionModel = Mage::getModel('ops/system_config_backend_encoding');
+
+ $result = $optionModel->toOptionArray();
+
+ $this->assertInternalType('array', $result);
+ $this->assertArrayHasKey('value', $result[0]);
+ $this->assertArrayHasKey('label', $result[0]);
+
+ $this->assertEquals('utf-8', $result[0]['value']);
+ $this->assertEquals('UTF-8', $result[0]['label']);
+
+ $this->assertEquals('other', $result[1]['value']);
+ $this->assertEquals('Other', $result[1]['label']);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Flex/MethodsTest.php b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Flex/MethodsTest.php
new file mode 100644
index 0000000..59385f4
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/Flex/MethodsTest.php
@@ -0,0 +1,106 @@
+
+ */
+?>
+setValue($this->getEmpty());
+
+ $model->save();
+ }
+
+ /**
+ * @expectedException Mage_Core_Exception
+ * @expectedExceptionMessage PM and Brand combination must be unique
+ */
+ public function testSaveWithDuplicateException()
+ {
+ $model = Mage::getModel('ops/system_config_backend_flex_methods');
+ $model->setValue($this->getDuplicate());
+
+ $model->save();
+
+ }
+
+ public function testSave()
+ {
+ $model = Mage::getModel('ops/system_config_backend_flex_methods');
+ $model->setValue(array($this->getSimpleData()));
+ $model->setScope('default')
+ ->setScopeId(0)
+ ->setPath('payment/ops_flex/methods');
+
+ $model->save();
+ Mage::getConfig()->cleanCache();
+ $methods = unserialize(Mage::getStoreConfig('payment/ops_flex/methods'));
+
+ $this->assertTrue(is_array($methods));
+ $this->assertEquals(1, count($methods));
+ }
+
+ protected function getDuplicate()
+ {
+ return array(
+ $this->getSimpleData(),
+ $this->getSimpleData()
+ );
+ }
+
+ protected function getEmpty()
+ {
+ return array(
+ $this->getSimpleData(),
+ array(
+ 'title' => '',
+ 'brand' => '',
+ 'pm' => ''
+ )
+ );
+ }
+
+ protected function getSimpleData()
+ {
+ return array(
+ 'title' => 'foo',
+ 'brand' => 'bar',
+ 'pm' => 'zzz'
+ );
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/PaymentLogoTest.php b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/PaymentLogoTest.php
new file mode 100644
index 0000000..05fc416
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/System/Config/Backend/PaymentLogoTest.php
@@ -0,0 +1,53 @@
+
+ * @copyright 2016 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+
+/**
+ * Netresearch_OPS_Test_Block_System_Config_PaymentLogoTest
+ *
+ * @category OPS
+ * @package Netresearch_OPS
+ * @author Benjamin Heuer
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ * @link http://www.netresearch.de/
+ */
+class Netresearch_OPS_Test_Model_System_Config_Backend_PaymentLogoTest
+ extends EcomDev_PHPUnit_Test_Case
+{
+ /**
+ * @test
+ */
+ public function toOptionArray()
+ {
+ /** @var Netresearch_Ops_Model_System_Config_Backend_PaymentLogo $optionModel */
+ $optionModel = Mage::getModel('ops/system_config_backend_paymentLogo');
+
+ $result = $optionModel->toOptionArray();
+
+ $this->assertInternalType('array', $result);
+ $this->assertArrayHasKey('value', $result[0]);
+ }
+
+}
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Validator/Kwixo/Shipping/Setting.php b/app/code/community/Netresearch/OPS/Test/Model/Validator/Kwixo/Shipping/Setting.php
new file mode 100644
index 0000000..72addd3
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Validator/Kwixo/Shipping/Setting.php
@@ -0,0 +1,124 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Model_Validator_Kwixo_Shipping_Setting
+ extends EcomDev_PHPUnit_Test_Case_Config
+{
+
+ private function getValidator()
+ {
+ return Mage::getModel('ops/validator_kwixo_shipping_setting');
+ }
+
+ public function testKwixoShippingTypeIsValid()
+ {
+ $validator = $this->getValidator();
+ $this->assertFalse($validator->isValid(array()));
+ $falseData = array('dhl' => array('kwixo_shipping_type' => 'abc'));
+ $this->assertFalse($validator->isValid($falseData));
+ $this->assertTrue(0 < count($validator->getMessages()));
+ $falseData = array('dhl' => array('foo' => 'abc'));
+ $this->assertFalse($validator->isValid($falseData));
+ $falseData = array('dhl' => array('kwixo_shipping_type' => 0));
+ $this->assertFalse($validator->isValid($falseData));
+ $falseData = array('dhl' => array('kwixo_shipping_type' => 6));
+ $this->assertFalse($validator->isValid($falseData));
+ $messages = $validator->getMessages();
+ $this->assertEquals(
+ 'invalid shipping type provided',
+ $messages['dhl']['kwixo_shipping_type_error']
+ );
+ $correctData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_type' => 4, 'kwixo_shipping_speed' => 1,
+ 'kwixo_shipping_details' => ''
+ )
+ );
+ $this->assertTrue($validator->isValid($correctData));
+ }
+
+ public function testKwixoShippingSpeedIsValid()
+ {
+ $validator = $this->getValidator();
+ $this->assertFalse($validator->isValid(array()));
+ $falseData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_speed' => 'abc', 'kwixo_shipping_type' => 4
+ )
+ );
+ $this->assertFalse($validator->isValid($falseData));
+ $this->assertTrue(0 < count($validator->getMessages()));
+ $falseData = array(
+ 'dhl' => array(
+ 'foo' => 'abc', 'kwixo_shipping_type' => 4
+ )
+ );
+ $this->assertFalse($validator->isValid($falseData));
+ $falseData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_speed' => 0, 'kwixo_shipping_type' => 4
+ )
+ );
+ $this->assertFalse($validator->isValid($falseData));
+ $messages = $validator->getMessages();
+ $this->assertEquals(
+ 'invalid shipping speed provided',
+ $messages['dhl']['kwixo_shipping_speed_error']
+ );
+ $correctData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_speed' => 4, 'kwixo_shipping_type' => 4,
+ 'kwixo_shipping_details' => ''
+ )
+ );
+ $this->assertTrue($validator->isValid($correctData));
+ }
+
+ public function testKwixoShippingDetailsIsValid()
+ {
+ $validator = $this->getValidator();
+ $this->assertFalse($validator->isValid(array()));
+ $falseData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_speed' => 4, 'kwixo_shipping_type' => 4
+ )
+ );
+ $this->assertFalse($validator->isValid($falseData));
+ $correctData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_speed' => 4, 'kwixo_shipping_type' => 4,
+ 'kwixo_shipping_details' => ''
+ )
+ );
+ $this->assertTrue($validator->isValid($correctData));
+ $longString = '012345678901234567890123456789012345678901234567891';
+ $falseData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_speed' => 4, 'kwixo_shipping_type' => 4,
+ 'kwixo_shipping_details' => $longString
+ )
+ );
+ $this->assertFalse($validator->isValid($falseData));
+ $messages = $validator->getMessages();
+ $this->assertEquals(
+ 'invalid shipping details provided',
+ $messages['dhl']['kwixo_shipping_details_error']
+ );
+ $longString = '01234567890123456789012345678901234567890123456789';
+ $correctData = array(
+ 'dhl' => array(
+ 'kwixo_shipping_speed' => 4, 'kwixo_shipping_type' => 4,
+ 'kwixo_shipping_details' => $longString
+ )
+ );
+ $this->assertTrue($validator->isValid($correctData));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/FactoryTest.php b/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/FactoryTest.php
new file mode 100644
index 0000000..5378bdd
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/FactoryTest.php
@@ -0,0 +1,34 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Model_Validator_Parameter_FactoryTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $validatorFactory = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->validatorFactory = Mage::getModel('ops/validator_parameter_factory');
+ }
+
+ public function testGetValidatorFor()
+ {
+ $validator = $this->validatorFactory->getValidatorFor(null);
+ $this->assertTrue($validator instanceof Netresearch_OPS_Model_Validator_Parameter_Validator);
+ $this->assertEquals(0, count($validator->getValidators()));
+
+ $validator = $this->validatorFactory->getValidatorFor(Netresearch_OPS_Model_Validator_Parameter_Factory::TYPE_REQUEST_PARAMS_VALIDATION);
+ $this->assertTrue($validator instanceof Netresearch_OPS_Model_Validator_Parameter_Validator);
+ $this->assertEquals(1, count($validator->getValidators()));
+ $this->assertTrue(current($validator->getValidators()) instanceof Netresearch_OPS_Model_Validator_Parameter_Length);
+ $this->assertTrue(0 < count(current($validator->getValidators())->getFieldLengths()));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/LengthTest.php b/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/LengthTest.php
new file mode 100644
index 0000000..ebf2267
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/LengthTest.php
@@ -0,0 +1,47 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Model_Validator_Parameter_LengthTest extends EcomDev_PHPUnit_Test_Case
+{
+
+ protected $validator = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->validator = Mage::getModel('ops/validator_parameter_length');
+ }
+
+ public function testValidationPassed()
+ {
+ $this->assertTrue($this->validator->isValid(null));
+ $this->assertTrue($this->validator->isValid(new Varien_Object()));
+ $this->assertTrue($this->validator->isValid(array()));
+ $map = array('foo' => 5, 'bar' => 4, 'baz' => 3, 'borg' => 5);
+ $this->validator->setFieldLengths($map);
+ $data = array('foo' => '12345', 'bar' => '1234', 'baz' => '123', 'borg' => null);
+ $this->assertTrue($this->validator->isValid($data));
+ }
+
+ public function testValidationFailed()
+ {
+ $map = array('foo' => 5, 'bar' => 4, 'baz' => 3);
+ $this->validator->setFieldLengths($map);
+ $data = array('foo' => '123456', 'bar' => '1234', 'baz' => '1238');
+ $this->assertFalse($this->validator->isValid($data));
+ $this->assertTrue(2 == count($this->validator->getMessages()));
+
+ $this->validator = Mage::getModel('ops/validator_parameter_length');
+ $map = array('foo' => 5, 'bar' => 4, 'baz' => 3);
+ $this->validator->setFieldLengths($map);
+ $data = array('foo' => '123456', 'bar' => '1234', 'baz' => '123');
+ $this->assertFalse($this->validator->isValid($data));
+ $this->assertTrue(1 == count($this->validator->getMessages()));
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/ValidatorTest.php b/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/ValidatorTest.php
new file mode 100644
index 0000000..d868532
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/Model/Validator/Parameter/ValidatorTest.php
@@ -0,0 +1,36 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Test_Model_Validator_Parameter_ValidatorTest extends EcomDev_PHPUnit_Test_Case
+{
+ protected $validator = null;
+
+ public function setUp()
+ {
+ parent::setUp();
+ $this->validator = Mage::getModel('ops/validator_parameter_validator');
+ }
+
+ public function testIsValid()
+ {
+ $this->assertTrue($this->validator->isValid(null));
+ $this->validator->addValidator(new Zend_Validate_Alnum());
+ $this->assertFalse($this->validator->isValid(null));
+ $this->assertTrue(0 < count($this->validator->getMessages()));
+ $this->validator->addValidator(new Zend_Validate_EmailAddress());
+ }
+
+ public function testMultipleValidators()
+ {
+ $this->validator->addValidator(new Zend_Validate_Alnum());
+ $this->validator->addValidator(new Zend_Validate_EmailAddress());
+ $this->assertFalse($this->validator->isValid(null));
+ $this->assertTrue(1 < count($this->validator->getMessages()));
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/var/fixtures/aliases.yaml b/app/code/community/Netresearch/OPS/Test/var/fixtures/aliases.yaml
new file mode 100644
index 0000000..829dae0
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/var/fixtures/aliases.yaml
@@ -0,0 +1,92 @@
+tables:
+ ops/alias:
+ - id: 1
+ customer_id: 1
+ alias: 4711
+ brand: 'VISA'
+ billing_address_hash: '0815'
+ shipping_address_hash: '2342'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0116'
+ payment_method: 'ops_cd'
+ state: 'active'
+ store_id: 0
+ created_at: '2000-01-01 00:00:01'
+
+ - id: 2
+ customer_id: 1
+ alias: 4712
+ brand: 'VISA'
+ billing_address_hash: '0816'
+ shipping_address_hash: '2342'
+ pseudo_account_or_cc_no: 'xxxx1112'
+ expiration_date: '0116'
+ payment_method: 'ops_cc'
+ state: 'active'
+ store_id: 0
+ created_at: '1970-01-01 00:00:01'
+
+ - id: 3
+ customer_id: 1
+ alias: 4713
+ brand: 'VISA'
+ billing_address_hash: '0817'
+ shipping_address_hash: '0817'
+ pseudo_account_or_cc_no: 'xxxx1113'
+ expiration_date: '0116'
+ payment_method: 'ops_cc'
+ state: 'pending'
+ store_id: 0
+ created_at: '1970-01-01 00:00:02'
+
+ - id: 4
+ customer_id: 2
+ alias: 4711
+ brand: 'VISA'
+ billing_address_hash: '1508'
+ shipping_address_hash: '4223'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0117'
+ payment_method: 'ops_cc'
+ state: 'active'
+ store_id: 0
+ created_at: '1970-01-01 00:00:02'
+
+ - id: 5
+ customer_id: 1
+ alias: 4711
+ brand: 'VISA'
+ billing_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ shipping_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0117'
+ payment_method: 'ops_cc'
+ state: 'active'
+ store_id: 0
+ created_at: '1970-01-01 00:00:02'
+
+ - id: 6
+ customer_id: 1
+ alias: 4714
+ brand: 'VISA'
+ billing_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ shipping_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0116'
+ payment_method: 'ops_cd'
+ state: 'pending'
+ store_id: 0
+ created_at: '2000-11-01 00:00:01'
+
+ - id: 7
+ customer_id: 23
+ alias: 4714
+ brand: 'VISA'
+ billing_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ shipping_address_hash: '1b9ecdf409e240717f04b7155712658ab09116bb'
+ pseudo_account_or_cc_no: 'xxxx1111'
+ expiration_date: '0116'
+ payment_method: 'ops_cd'
+ state: 'active'
+ store_id: 0
+ created_at: '2000-11-01 00:00:01'
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Test/var/fixtures/orders.yaml b/app/code/community/Netresearch/OPS/Test/var/fixtures/orders.yaml
new file mode 100644
index 0000000..bbebe1c
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/var/fixtures/orders.yaml
@@ -0,0 +1,703 @@
+tables:
+ sales/order:
+ - entity_id: 11
+ increment_id: 100000011
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 23
+ store_id: 0
+
+ - entity_id: 12
+ increment_id: 100000012
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 24
+ store_id: 0
+
+ - entity_id: 13
+ increment_id: 100000013
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'processing'
+ status: 'processing'
+ quote_id: 25
+ store_id: 0
+
+ - entity_id: 14
+ increment_id: 100000014
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 26
+
+ - entity_id: 15
+ increment_id: 100000015
+ shipping_address_id: 43
+ base_grand_total: 177.55
+ grand_total: 200.00
+ currency: '$'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 27
+
+ - entity_id: 16
+ increment_id: 100000016
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 28
+
+ - entity_id: 17
+ increment_id: 100000017
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 29
+
+ - entity_id: 18
+ increment_id: 100000018
+ shipping_address_id: 43
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 30
+
+ - entity_id: 19
+ increment_id: 100000019
+ shipping_address_id: 50
+ base_grand_total: 19.99
+ grand_total: 19.99
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 43
+
+ - entity_id: 20
+ increment_id: 100000020
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+ quote_id: 42#
+
+ - entity_id: 21
+ increment_id: 100000021
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 22
+ increment_id: 100000022
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 23
+ increment_id: 100000023
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 24
+ increment_id: 100000024
+ store_id: 1
+ shipping_address_id: 46
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 24
+ increment_id: 100000024
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 25
+ increment_id: 100000025
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 26
+ increment_id: 100000026
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 27
+ increment_id: 100000027
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 28
+ increment_id: 100000028
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 29
+ increment_id: 100000029
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 30
+ increment_id: 100000030
+ store_id: 1
+ shipping_address_id: 42
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ state: 'pending_payment'
+ status: 'pending_payment'
+
+ - entity_id: 31
+ increment_id: 100000031
+ shipping_address_id: 42
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'processing'
+ status: 'processing'
+ quote_id: 25
+ store_id: 0
+
+ - entity_id: 32
+ increment_id: 100000032
+ shipping_address_id: 42
+ base_grand_total: 177.55
+ grand_total: 177.55
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+ customer_email: 'willi.usa.customer@trash-mail.com'
+ state: 'processing'
+ status: 'processing'
+ quote_id: 32
+ store_id: 0
+
+ sales/quote:
+ - entity_id: 1
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ - entity_id: 2
+ base_grand_total: 119.00
+ grand_total: 200.00
+ currency: '$'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ - entity_id: 10
+ store_id: 0
+ customer_id: 23
+ created_at: '2013-05-14 14:45:00'
+ store_id: 0
+
+ - entity_id: 11
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 23
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 12
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ - entity_id: 32
+ store_id: 0
+ created_at: '2013-05-14 14:45:00'
+
+ sales/quote_payment:
+ - payment_id: 1
+ quote_id: 10
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 2
+ quote_id: 11
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ quote_id: 11
+
+ - payment_id: 3
+ quote_id: 10
+ updated_at: '1970-01-01'
+ method: 'ops_cc'
+ additional_information: a:7:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:3:"cvc";s:3:"123";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 4
+ quote_id: 12
+ updated_at: '1970-01-01'
+ method: 'ops_paypal'
+ additional_information: a:7:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:3:"cvc";s:3:"123";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:4:"4714";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+
+ - payment_id: 5
+ quote_id: 32
+ updated_at: '1970-01-01'
+ method: 'ops_BCMC'
+ additional_information: a:37:{s:5:"PSPID";s:10:"NRMAGENTO8";s:6:"AMOUNT";d:34500;s:8:"CURRENCY";s:3:"EUR";s:7:"ORDERID";s:10:"#145000120";s:8:"LANGUAGE";s:5:"de_DE";s:2:"PM";s:10:"CreditCard";s:5:"EMAIL";s:31:"sebastian.ertner@netresearch.de";s:9:"ACCEPTURL";s:56:"http://ser-ogone-de.magento.nrdev.de/ops/payment/accept/";s:10:"DECLINEURL";s:57:"http://ser-ogone-de.magento.nrdev.de/ops/payment/decline/";s:12:"EXCEPTIONURL";s:59:"http://ser-ogone-de.magento.nrdev.de/ops/payment/exception/";s:9:"CANCELURL";s:56:"http://ser-ogone-de.magento.nrdev.de/ops/payment/cancel/";s:7:"BACKURL";s:125:"http://ser-ogone-de.magento.nrdev.de/ops/payment/retry/?SHASIGN=AEF578B3ED129000FC779255DC04CA535ABB155F&orderID=%23145000120";s:8:"FP_ACTIV";s:1:"0";s:9:"OPERATION";s:3:"RES";s:4:"ORIG";s:10:"OGmg160526";s:5:"BRAND";s:4:"BCMC";s:2:"CN";s:16:"Sebastian Ertner";s:3:"COM";s:27:"Lafayette Convertible Dress";s:8:"ADDMATCH";i:1;s:29:"ECOM_BILLTO_POSTAL_POSTALCODE";s:5:"04229";s:12:"OWNERADDRESS";s:18:"Nonnenstraße 11 d";s:9:"OWNERTOWN";s:7:"Leipzig";s:8:"OWNERZIP";s:5:"04229";s:10:"OWNERTELNO";s:11:"23123123123";s:8:"OWNERCTY";s:2:"DE";s:4:"CUID";s:3:"140";s:6:"DEVICE";s:8:"computer";s:2:"TP";s:57:"http://ser-ogone-de.magento.nrdev.de/ops/payment/paypage/";s:23:"ECOM_SHIPTO_POSTAL_CITY";s:7:"Leipzig";s:29:"ECOM_SHIPTO_POSTAL_POSTALCODE";s:5:"04229";s:24:"ECOM_SHIPTO_POSTAL_STATE";s:2:"SN";s:30:"ECOM_SHIPTO_POSTAL_COUNTRYCODE";s:2:"DE";s:29:"ECOM_SHIPTO_POSTAL_NAME_FIRST";s:9:"Sebastian";s:28:"ECOM_SHIPTO_POSTAL_NAME_LAST";s:6:"Ertner";s:31:"ECOM_SHIPTO_POSTAL_STREET_LINE1";s:13:"Nonnenstraße";s:32:"ECOM_BILLTO_POSTAL_STREET_NUMBER";s:4:"11 d";s:31:"ECOM_SHIPTO_POSTAL_STREET_LINE2";s:0:"";}
+
+ sales/order_payment:
+ - entity_id: 1
+ parent_id: 11
+ additional_information: a:7:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;s:6:"status";s:1:"0";}
+ method: 'ops_bankTransfer'
+
+ - entity_id: 2
+ parent_id: 12
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:1:"5";}
+
+ - entity_id: 3
+ parent_id: 13
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:1:"0";}
+ method: 'ops_bankTransfer'
+
+ - entity_id: 4
+ parent_id: 14
+ additional_information: a:2:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";}
+
+ - entity_id: 5
+ parent_id: 15
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFD";}
+ method: 'ops_cc'
+
+ - entity_id: 6
+ parent_id: 16
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFS";}
+
+ - entity_id: 7
+ parent_id: 17
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFS";s:9:"canRefund";b:0;}
+
+ - entity_id: 8
+ parent_id: 18
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:23:"lastRefundOperationCode";s:3:"RFD";s:9:"canRefund";b:1;}
+
+ - entity_id: 9
+ parent_id: 19
+ method: 'ops_openInvoiceDe'
+
+ - entity_id: 11
+ parent_id: 20
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 12
+ parent_id: 21
+ additional_information: a:4:{s:2:"PM";s:16:"Direct Debits DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+ method: 'ops_directDebit'
+
+ - entity_id: 13
+ parent_id: 22
+ additional_information: a:4:{s:2:"PM";s:16:"Direct Debits NL";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 14
+ parent_id: 23
+ additional_information: a:4:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:11:"HTML_ANSWER";s:4:"HTML";s:9:"canRefund";b:1;}
+
+ - entity_id: 42
+ parent_id: 20
+
+ - entity_id: 15
+ parent_id: 24
+ additional_information: a:6:{s:8:"CC_BRAND";s:4:"VISA";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_cc'
+
+ - entity_id: 16
+ parent_id: 25
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_cc'
+
+ - entity_id: 17
+ parent_id: 26
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_paypal'
+
+ - entity_id: 18
+ parent_id: 27
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoApresReception'
+
+ - entity_id: 19
+ parent_id: 28
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoComptant'
+
+ - entity_id: 20
+ parent_id: 29
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'ops_kwixoCredit'
+
+ - entity_id: 21
+ parent_id: 30
+ additional_information: a:6:{s:8:"CC_BRAND";s:16:"PostFinance Card";s:5:"CC_CN";s:10:"Max Muster";s:12:"saveOpsAlias";s:1:"0";s:5:"alias";s:12:"041907169941";s:12:"ops_response";a:22:{s:7:"orderID";s:11:"SER13041841";s:5:"PAYID";s:8:"20908736";s:8:"NCSTATUS";s:1:"0";s:7:"NCERROR";s:1:"0";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"5";s:5:"IPCTY";s:2:"AU";s:5:"CCCTY";s:2:"US";s:3:"ECI";s:2:"12";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:6:"amount";s:2:"35";s:8:"currency";s:3:"EUR";s:2:"PM";s:10:"CreditCard";s:5:"BRAND";s:4:"VISA";s:7:"SCORING";s:1:"3";s:12:"SCO_CATEGORY";s:1:"O";s:5:"ALIAS";s:12:"041907169941";s:11:"NCERRORPLUS";s:1:"!";}s:28:"checkoutFinishedSuccessfully";b:1;}
+ method: 'checkmo'
+
+ - entity_id: 22
+ parent_id: 31
+ additional_information: a:3:{s:2:"PM";s:16:"Bank transfer DE";s:5:"BRAND";s:16:"Bank transfer DE";s:6:"status";s:2:"51";}
+ method: 'ops_bankTransfer'
+
+ - entity_id: 23
+ parent_id: 32
+ additional_information: a:29:{s:7:"orderID";s:10:"#145000119";s:8:"currency";s:3:"EUR";s:6:"amount";s:2:"80";s:2:"PM";s:10:"CreditCard";s:10:"ACCEPTANCE";s:7:"test123";s:6:"STATUS";s:1:"9";s:6:"CARDNO";s:18:"670300-XXXXXXXX-03";s:3:"BIN";s:6:"670300";s:2:"ED";s:4:"0926";s:2:"CN";s:16:"Sebastian Ertner";s:7:"TRXDATE";s:8:"09/15/16";s:5:"PAYID";s:10:"3009110929";s:7:"NCERROR";s:1:"0";s:5:"BRAND";s:22:"Bancontact/Mister Cash";s:11:"CREDITDEBIT";s:0:"";s:5:"IPCTY";s:2:"DE";s:5:"CCCTY";s:2:"BE";s:3:"ECI";s:1:"5";s:8:"CVCCheck";s:2:"NO";s:8:"AAVCheck";s:2:"NO";s:2:"VC";s:2:"NO";s:6:"AAVZIP";s:2:"NO";s:10:"AAVADDRESS";s:2:"NO";s:7:"AAVMAIL";s:2:"NO";s:7:"SCORING";s:1:"0";s:12:"SCO_CATEGORY";s:1:"G";s:2:"IP";s:13:"178.24.30.185";s:10:"MOBILEMODE";s:2:"QR";s:7:"SHASIGN";s:40:"76A28E77731F97339BB752509BBE46B8E464A8D6";}
+ method: 'ops_BCMC'
+
+ sales/shipment:
+ - entity_id: 1
+ increment_id: 100000077
+ order_id: 11
+ shipping_address_id: 42
+
+ - entity_id: 2
+ increment_id: 100000078
+ order_id: 12
+ shipping_address_id: 43
+
+ sales/order_address:
+ - entity_id: 42
+ parent_id: 11
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ fax: 12345678
+
+ - entity_id: 43
+ parent_id: 11
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 44
+ parent_id: 12
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 45
+ parent_id: 12
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: 'An der Tabaksmühle 3a'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 46
+ parent_id: 24
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_billing: 1
+
+ - entity_id: 47
+ parent_id: 27
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+ same_as_shipping: 1
+
+ - entity_id: 147
+ parent_id: 27
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04229'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+
+ - entity_id: 48
+ parent_id: 28
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 49
+ parent_id: 19
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 50
+ parent_id: 19
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 51
+ parent_id: 15
+ address_type: 'shipping'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ - entity_id: 52
+ parent_id: 32
+ address_type: 'billing'
+ firstname: 'Hubertus'
+ postcode: '04227'
+ lastname: 'Fürstenberg'
+ street: '44 rue Parmentier'
+ city: 'Leipzig'
+ email: 'hubertus.von.fuerstenberg@trash-mail.com'
+ country_id: 'DE'
+ prefix: 'Prof. Dr.'
+ middlename: 'von'
+ suffix: 'MdL'
+ company: ''
+
+ sales/order_item:
+ - item_id: 11
+ order_id: 11
+ qty_ordered: 2.0000
+ qty_shipped: 2.0000
+ sku: 4711
+ name: 'some great test item'
+ price: 19.99
+ tax_amount: 1.99
+
+ - item_id: 12
+ order_id: 11
+ qty_ordered: 2.0000
+ qty_shipped: 2.0000
+ sku: 4711
+ name: 'some great test item 2'
+ price: 19.99
+ tax_amount: 1.99
+
+ - item_id: 13
+ order_id: 19
+ qty_ordered: 1.0000
+ qty_shipped: 0.0000
+ sku: 4711
+ name: 'some great test item'
+ price: 19.99
+ tax_amount: 1.99
+
diff --git a/app/code/community/Netresearch/OPS/Test/var/fixtures/quotes.yaml b/app/code/community/Netresearch/OPS/Test/var/fixtures/quotes.yaml
new file mode 100644
index 0000000..412ffd3
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Test/var/fixtures/quotes.yaml
@@ -0,0 +1,21 @@
+tables:
+ sales/quote:
+ - entity_id: 1
+ base_grand_total: 119.00
+ grand_total: 119.00
+ currency: 'EUR'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ - entity_id: 2
+ increment_id: 100000002
+ base_grand_total: 119.00
+ grand_total: 200.00
+ currency: '$'
+ customer_gender: 1
+ shipping_method: 'flatrate_flatrate'
+
+ sales/quote_payment:
+ - entity_id: 1
+ quote_id: 1
+ method: 'ops_cc'
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Trait/AliasController.php b/app/code/community/Netresearch/OPS/Trait/AliasController.php
new file mode 100644
index 0000000..49ef187
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Trait/AliasController.php
@@ -0,0 +1,259 @@
+
+ */
+?>
+getRequest()->getParams();
+ $requiredParams = array_fill_keys(array('Alias_OrderId', 'Alias_AliasId'), '');
+ $missingParams = count(array_diff_key($requiredParams, $params));
+ if ($missingParams) {
+
+ return $this->parseFrontendException();
+ } else {
+ $helper = Mage::helper('ops');
+ $helper->log(
+ $helper->__(
+ "Incoming accepted Ingenico ePayments Alias Feedback\n\nRequest Path: %s\nParams: %s\n",
+ $this->getRequest()->getPathInfo(),
+ serialize($params)
+ )
+ );
+ Mage::helper('ops/alias')->saveAlias($params);
+
+
+ if (array_key_exists('Alias_OrderId', $params)) {
+ $quote = Mage::getModel('sales/quote')->load($params['Alias_OrderId']);
+ $this->updateAdditionalInformation($quote, $params);
+ } else {
+ $quote = Mage::getSingleton('checkout/session')->getQuote();
+ }
+
+ // OGNH-7 special handling for admin orders
+ Mage::helper('ops/alias')->setAliasToPayment(
+ $quote->getPayment(),
+ array_change_key_case($params, CASE_LOWER),
+ false
+ );
+
+ return $this->parseFrontendSuccess($params['Alias_AliasId']);
+ }
+ }
+
+ /**
+ * exception-action for Alias-generating iframe-response
+ *
+ */
+ public function exceptionAction()
+ {
+ $params = $this->getRequest()->getParams();
+ $errors = array();
+
+ foreach ($params as $key => $value) {
+ if (stristr($key, 'error') && 0 != $value) {
+ $errors[] = $value;
+ }
+ }
+
+ $helper = Mage::helper('ops');
+ $helper->log(
+ $helper->__(
+ "Incoming exception Ingenico ePayments Alias Feedback\n\nRequest Path: %s\nParams: %s\n",
+ $this->getRequest()->getPathInfo(),
+ serialize($params)
+ )
+ );
+
+ return $this->parseFrontendException();
+ }
+
+ /**
+ * Generates the hash for the hosted tokenization page request
+ *
+ * @throws Exception
+ */
+ public function generateHashAction()
+ {
+ $storeId = $this->getStoreId();
+
+ $result = $this->generateHash($storeId);
+
+ $this->getResponse()->setBody(Mage::helper('core')->jsonEncode($result));
+ }
+
+ /**
+ * Get store id from quote or request
+ *
+ * @return int
+ */
+ protected function getStoreId()
+ {
+ $storeId = null;
+
+ if (Mage::app()->getStore()->isAdmin()) {
+ $quote = Mage::getSingleton('adminhtml/session_quote');
+ $storeId = $quote->getStoreId();
+ } else {
+ $quoteId = $this->getRequest()->getParam('orderid');
+
+ $quote = Mage::getModel('sales/quote')->load($quoteId);
+
+ if ($quote->getId() === null) {
+ $quote = Mage::getModel('sales/quote')->loadByIdWithoutStore($quoteId);
+ }
+
+ if ($quote->getId() !== null) {
+ $storeId = $quote->getStoreId();
+ }
+ if ($this->getRequest()->getParam('storeId') !== null) {
+ $storeId = $this->getRequest()->getParam('storeId');
+ }
+ }
+
+ return $storeId;
+ }
+
+ /**
+ * updates the additional information from payment, thats needed for backend reOrders
+ *
+ * @param Mage_Sales_Model_Quote $quote
+ * @param string[] $params
+ */
+ public function updateAdditionalInformation(Mage_Sales_Model_Quote $quote, $params)
+ {
+ if ($quote->getId() !== null && $quote->getPayment() && $quote->getPayment()->getId() !== null) {
+ $payment = $quote->getPayment();
+ if (array_key_exists('Alias_AliasId', $params)) {
+ $payment->setAdditionalInformation('alias', $params['Alias_AliasId']);
+ }
+ if (array_key_exists('Card_Brand', $params)) {
+ $payment->setAdditionalInformation('CC_BRAND', $params['Card_Brand']);
+ }
+ if (array_key_exists('Card_CardHolderName', $params)) {
+ $payment->setAdditionalInformation('CC_CN', $params['Card_CardHolderName']);
+ }
+ if ($this->userIsRegistering()) {
+ $payment->setAdditionalInformation('userIsRegistering', true);
+ }
+ $quote->setPayment($payment)->setDataChanges(true)->save();
+ $quote->setDataChanges(true)->save();
+ }
+ }
+
+ /**
+ * Checks if checkout method is registering
+ *
+ * @return bool
+ */
+ protected function userIsRegistering()
+ {
+ return Mage::getSingleton('checkout/type_onepage')->getCheckoutMethod()
+ === Mage_Checkout_Model_Type_Onepage::METHOD_REGISTER;
+ }
+
+ /**
+ * Generate hash from request parameters
+ *
+ * @param $storeId
+ *
+ * @return array
+ */
+ protected function generateHash($storeId)
+ {
+ $data = $this->cleanParamKeys();
+
+ $secret = $this->getConfig()->getShaOutCode($storeId);
+ $raw = $this->getPaymentHelper()->getSHAInSet($data, $secret);
+ $result = array('hash' => Mage::helper('ops/payment')->shaCrypt($raw));
+
+ return $result;
+ }
+
+ /**
+ * Cleans param array from magentos admin params, fixes underscored keys
+ *
+ * @return array
+ */
+ protected function cleanParamKeys()
+ {
+ $data = array();
+ foreach ($this->getRequest()->getParams() as $key => $value) {
+ if ($key == 'form_key' || $key == 'isAjax' || $key == 'key') {
+ continue;
+ }
+ $data[str_replace('_', '.', $key)] = $value;
+ }
+
+ return $data;
+ }
+
+ /**
+ * @return Mage_Core_Controller_Response_Http
+ */
+ protected function parseFrontendException()
+ {
+ $result = "";
+
+ return $this->getResponse()->setBody($result);
+ }
+
+ /**
+ * @param string $alias alias to be parsed in frontend javascript event
+ *
+ * @return Mage_Core_Controller_Response_Http
+ */
+ protected function parseFrontendSuccess($alias)
+ {
+ $result = sprintf(
+ "",
+ $alias
+ );
+
+ return $this->getResponse()->setBody($result);
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/Trait/PaymentHelper.php b/app/code/community/Netresearch/OPS/Trait/PaymentHelper.php
new file mode 100644
index 0000000..34135bb
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/Trait/PaymentHelper.php
@@ -0,0 +1,60 @@
+
+ */
+?>
+paymentHelper) {
+ $this->paymentHelper = Mage::helper('ops/payment');
+ }
+
+ return $this->paymentHelper;
+ }
+
+ /**
+ * @param Netresearch_OPS_Helper_Payment $paymentHelper
+ *
+ * @returns $this
+ */
+ public function setPaymentHelper($paymentHelper)
+ {
+ $this->paymentHelper = $paymentHelper;
+
+ return $this;
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/controllers/Adminhtml/AdminController.php b/app/code/community/Netresearch/OPS/controllers/Adminhtml/AdminController.php
new file mode 100644
index 0000000..ef0b4e3
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/Adminhtml/AdminController.php
@@ -0,0 +1,80 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Adminhtml_AdminController extends Mage_Adminhtml_Controller_Action
+{
+ protected function _isAllowed()
+ {
+ return true;
+ }
+
+ public function saveAliasAction()
+ {
+ $alias = $this->_request->getParam('alias');
+ $quote = Mage::getSingleton('admin/session_quote');
+ if (0 < strlen($alias)) {
+ $payment = $quote->getPayment();
+ $payment->setAdditionalInformation('alias', $alias);
+ Mage::helper('ops')->log('saved alias ' . $alias . ' for quote #' . $quote->getId());
+ $payment->setDataChanges(true);
+ $payment->save();
+ }
+ }
+
+ public function downloadLogAction()
+ {
+ $helper = Mage::helper('ops/data');
+ $logPath = $helper->getLogPath();
+ $downloader = Mage::getModel('ops/file_download');
+ $fileToDownload = '';
+ try {
+ $fileToDownload = $downloader->getFile($logPath);
+ } catch (Exception $e) {
+ $this->_getSession()->addError($e->getMessage());
+ }
+ if ($fileToDownload === '') {
+ $message = Mage::helper('ops')->__('Log file could not be retrieved.');
+ $this->_getSession()->addError($message);
+ } else {
+ $this->_prepareDownloadResponse(
+ 'ops.log', array(
+ 'value' => $fileToDownload,
+ 'type' => 'filename'
+ )
+ );
+ }
+ $this->_redirectReferer();
+ }
+
+ /**
+ * Resends the payment information for the given order
+ */
+ public function resendInfoAction()
+ {
+ $orderId = $this->getRequest()->getParam('order_id');
+ $order = Mage::getModel('sales/order')->load($orderId);
+ /** @var Netresearch_OPS_Model_Payment_Features_PaymentEmail $paymentEmail */
+ $paymentEmail = Mage::getModel('ops/payment_features_paymentEmail');
+ $success = false;
+
+
+ if ($paymentEmail->isAvailableForOrder($order)) {
+ $success = $paymentEmail->resendPaymentInfo($order);
+ }
+
+ if ($success) {
+ $this->_getSession()->addSuccess($this->__('Payment information has been resend to customer.'));
+ } else {
+ $this->_getSession()->addError($this->__('Payment information could not be sent.'));
+ }
+
+ $this->_redirectReferer();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/controllers/Adminhtml/AliasController.php b/app/code/community/Netresearch/OPS/controllers/Adminhtml/AliasController.php
new file mode 100644
index 0000000..85c2196
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/Adminhtml/AliasController.php
@@ -0,0 +1,42 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Adminhtml_AliasController extends Mage_Adminhtml_Controller_Action
+{
+ use Netresearch_OPS_Trait_AliasController;
+
+ protected $_publicActions = array('accept', 'exception');
+
+ protected function _isAllowed()
+ {
+ return Mage::getSingleton('admin/session')->isAllowed('customer/manage');
+ }
+
+ public function deleteAction()
+ {
+ $aliasId = $this->_request->getParam('id');
+ $alias = Mage::getModel('ops/alias')->load($aliasId);
+ if ($alias->getId()) {
+ $alias->delete();
+ $this->_getSession()->addSuccess(
+ Mage::helper('ops')->__('Removed alias %s.', $alias->getAlias())
+ );
+ return $this->_redirectReferer();
+ }
+ $this->_getSession()->addError(
+ Mage::helper('ops')->__('Could not remove alias %s.', $alias->getAlias())
+ );
+ return $this->_redirectReferer();
+ }
+
+ protected function _getSession()
+ {
+ return Mage::getSingleton('adminhtml/session');
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixocategoryController.php b/app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixocategoryController.php
new file mode 100644
index 0000000..cb9d7cf
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixocategoryController.php
@@ -0,0 +1,228 @@
+
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_Adminhtml_KwixocategoryController
+ extends Mage_Adminhtml_Controller_Action
+{
+
+ protected $_block = 'ops/adminhtml_kwixocategory_edit';
+
+ /**
+ * @param bool $getRootInstead
+ * @return bool
+ */
+ protected function _initCategory($getRootInstead = false)
+ {
+ $categoryId = (int)$this->getRequest()->getParam('id', false);
+ $storeId = (int)$this->getRequest()->getParam('store', 0);
+ $category = Mage::getModel('catalog/category');
+ $category->setStoreId($storeId);
+
+ if ($categoryId) {
+ $category->load($categoryId);
+ if ($storeId) {
+ $rootId = Mage::app()->getStore($storeId)->getRootCategoryId();
+ if (!in_array($rootId, $category->getPathIds())) {
+ // load root category instead wrong one
+ if ($getRootInstead) {
+ $category->load($rootId);
+ } else {
+ $this->_redirect(
+ '*/*/', array('_current' => true, 'id' => null)
+ );
+
+ return false;
+ }
+ }
+ }
+ }
+
+ Mage::register('category', $category);
+ Mage::register('current_category', $category);
+
+ return $category;
+ }
+
+ public function treeAction()
+ {
+ $categoryId = (int)$this->getRequest()->getParam('id');
+ $storeId = $this->getRequest()->getParam('store', 0);
+ if ($storeId) {
+ if (!$categoryId) {
+ $store = Mage::app()->getStore($storeId);
+ $rootId = $store->getRootCategoryId();
+ $this->getRequest()->setParam('id', $rootId);
+ }
+ }
+
+ $category = $this->_initCategory(true);
+
+ $block = $this->getLayout()->createBlock('ops/adminhtml_kwixocategory_categoryTree');
+ $root = $block->getRoot();
+ $this->getResponse()->setBody(
+ Zend_Json::encode(
+ array(
+ 'data' => $block->getTree(),
+ 'parameters' => array(
+ 'text' => $block->buildNodeName($root),
+ 'draggable' => false,
+ 'allowDrop' => false,
+ 'id' => (int)$root->getId(),
+ 'expanded' => (int)$block->getIsWasExpanded(),
+ 'store_id' => (int)$block->getStore()->getId(),
+ 'category_id' => (int)$category->getId(),
+ 'root_visible' => (int)$root->getIsVisible()
+ ))
+ )
+ );
+ }
+
+
+ public function categoriesJsonAction()
+ {
+ if ($this->getRequest()->getParam('expand_all')) {
+ Mage::getSingleton('admin/session')->setIsTreeWasExpanded(true);
+ } else {
+ Mage::getSingleton('admin/session')->setIsTreeWasExpanded(false);
+ }
+ if (($categoryId = (int)$this->getRequest()->getPost('id'))) {
+ $this->getRequest()->setParam('id', $categoryId);
+
+ if (!$category = $this->_initCategory()) {
+ return;
+ }
+ $this->getResponse()->setBody(
+ $this->getLayout()->createBlock(
+ 'ops/adminhtml_kwixocategory_categoryTree'
+ )->getTreeJson($category)
+ );
+ }
+ }
+
+ public function indexAction()
+ {
+ $this->loadLayout();
+
+ $selectedCategory = Mage::getSingleton('admin/session')->getLastEditedCategory(true);
+ if ($selectedCategory) {
+ $this->getRequest()->setParam('id', $selectedCategory);
+ }
+ $selectedCategory = (int)$this->getRequest()->getParam('id', 0);
+ $this->_initCategory(true);
+
+ if ($selectedCategory > 0) {
+ $this->getLayout()->getBlock('tree')->setData(
+ 'selectedCategory', $selectedCategory
+ );
+ }
+
+ $this->renderLayout();
+ }
+
+ public function editAction()
+ {
+
+ $params = array('_current' => true);
+ $redirect = false;
+
+ $storeId = (int)$this->getRequest()->getParam('store');
+ $parentId = (int)$this->getRequest()->getParam('parent');
+ $prevStoreId = Mage::getSingleton('admin/session')->getLastViewedStore(
+ true
+ );
+
+ if ($prevStoreId != null && !$this->getRequest()->getQuery('isAjax')) {
+ $params['store'] = $prevStoreId;
+ $redirect = true;
+ }
+
+ $prevCategoryId = Mage::getSingleton('admin/session')
+ ->getLastEditedCategory(true);
+ if ($prevCategoryId && !$this->getRequest()->getQuery('isAjax')) {
+ $this->getRequest()->setParam('id', $prevCategoryId);
+ }
+ if ($redirect) {
+ $this->_redirect('*/*/edit', $params);
+
+ return;
+ }
+
+ $categoryId = (int)$this->getRequest()->getParam('id');
+ if ($storeId && !$categoryId && !$parentId) {
+ $store = Mage::app()->getStore($storeId);
+ $prevCategoryId = (int)$store->getRootCategoryId();
+ $this->getRequest()->setParam('id', $prevCategoryId);
+ }
+
+ if (!($category = $this->_initCategory(true))) {
+ return;
+ }
+
+ $data = Mage::getSingleton('adminhtml/session')->getCategoryData(true);
+ if (isset($data['general'])) {
+ $category->addData($data['general']);
+ }
+
+ if ($this->getRequest()->getQuery('isAjax')) {
+ Mage::getSingleton('admin/session')->setLastViewedStore(
+ $this->getRequest()->getParam('store')
+ );
+ Mage::getSingleton('admin/session')->setLastEditedCategory(
+ $category->getId()
+ );
+ $this->_initLayoutMessages('adminhtml/session');
+ $this->getResponse()->setBody(
+ $this->getLayout()->getMessagesBlock()->getGroupedHtml()
+ . $this->getLayout()->createBlock(
+ 'ops/adminhtml_kwixocategory_edit'
+ )->setController('kwixocategory')->toHtml()
+ );
+
+ return;
+ }
+ $this->_redirect('*/*/index', $params);
+ }
+
+ public function saveAction()
+ {
+ $post = $this->getRequest()->getPost();
+ try {
+ Mage::helper('ops/kwixo')->saveKwixoconfigurationMapping($post);
+ } catch (Exception $e) {
+ Mage::getSingleton('adminhtml/session')->addError($e->getMessage());
+ }
+ $this->_redirect(
+ '*/*/index/',
+ array('_current' => true, "id" => $post['category_id'], "store" => $post['storeId'])
+ );
+ }
+
+ public function deleteAction()
+ {
+ $id = $this->getRequest()->getParam('id', 0);
+ $storeId = $this->getRequest()->getParam('store', 0);
+ try {
+ Mage::getModel('ops/kwixo_category_mapping')
+ ->loadByCategoryId($id)
+ ->delete();
+ $message = Mage::helper('ops/data')->__('Data succesfully deleted.');
+ Mage::getSingleton('adminhtml/session')->addSuccess($message);
+ } catch (Exception $e) {
+ Mage::getSingleton('adminhtml/session')->addError($e->getMessage());
+ }
+ $this->_redirect('*/*/index/', array("id" => $id, "store" => $storeId));
+ }
+
+ protected function _isAllowed()
+ {
+ return Mage::getSingleton('admin/session')->isAllowed('catalog/categories');
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixoshippingController.php b/app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixoshippingController.php
new file mode 100644
index 0000000..c17ad74
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/Adminhtml/KwixoshippingController.php
@@ -0,0 +1,93 @@
+
+ * @category Netresearch
+ * @package Netresearch_OPS
+ * @copyright Copyright (c) 2013 Netresearch GmbH & Co. KG
+ * (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php
+ * Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_Adminhtml_KwixoshippingController
+ extends Mage_Adminhtml_Controller_Action
+{
+
+ /**
+ * displays the form
+ */
+ public function indexAction()
+ {
+ $this->loadLayout();
+
+ $storeId = $this->getRequest()->getParam('store', 0);
+ $this->getLayout()->getBlock('kwixoshipping')->setData(
+ 'store', $storeId
+ );
+ $this->getLayout()->getBlock('kwixoshipping')->setData(
+ 'postData',
+ Mage::getModel('adminhtml/session')->getData('errorneousData')
+ );
+ Mage::getModel('adminhtml/session')->unsetData('errorneousData');
+ $this->renderLayout();
+ }
+
+ /**
+ * save submitted form data
+ */
+ public function saveAction()
+ {
+ if ($this->getRequest()->isPost()) {
+ $postData = $this->getCleanPostData();
+ $validator = Mage::getModel('ops/validator_kwixo_shipping_setting');
+ if (true === $validator->isValid($postData)) {
+ $collection = Mage::getModel('ops/kwixo_shipping_setting')->getCollection()
+ ->addFieldToFilter('shipping_code', array('in' => array_keys($postData)));
+ /** @var Netresearch_OPS_Model_Kwixo_Shipping_Setting $kwixoShippingModel */
+ foreach ($collection->getItems() as $kwixoShippingModel) {
+ if (!array_key_exists($kwixoShippingModel->getShippingCode(), $postData)) {
+ continue;
+ }
+ $kwixoData = $postData[$kwixoShippingModel->getShippingCode()];
+ $kwixoShippingModel
+ ->setKwixoShippingType($kwixoData['kwixo_shipping_type'])
+ ->setKwixoShippingSpeed($kwixoData['kwixo_shipping_speed'])
+ ->setKwixoShippingDetails($kwixoData['kwixo_shipping_details']);
+ }
+ $collection->save();
+ } else {
+ $postData = array_merge_recursive($postData, $validator->getMessages());
+ Mage::getModel('adminhtml/session')->setData('errorneousData', $postData);
+ }
+
+ }
+ $this->_redirect('adminhtml/kwixoshipping/index');
+ }
+
+ protected function _isAllowed()
+ {
+ return Mage::getSingleton('admin/session')->isAllowed('sales/shipment');
+ }
+
+ /**
+ * removes any methods not in the actual systems carrier list from the post parameters
+ *
+ * @return array
+ */
+ protected function getCleanPostData()
+ {
+ $postData = $this->getRequest()->getPost();
+ $methodCodes = array_keys(
+ Mage::getSingleton('shipping/config')->getAllCarriers()
+ );
+ $invalidateShippingCodes = function ($key) use ($methodCodes) {
+ return !in_array($key, $methodCodes);
+ };
+ $validKeys = array_filter(array_keys($postData), $invalidateShippingCodes);
+ $cleanPostData = array_diff_key($postData, $validKeys);
+
+ return $cleanPostData;
+ }
+
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/controllers/Adminhtml/OpsstatusController.php b/app/code/community/Netresearch/OPS/controllers/Adminhtml/OpsstatusController.php
new file mode 100644
index 0000000..2140c25
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/Adminhtml/OpsstatusController.php
@@ -0,0 +1,31 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+
+class Netresearch_OPS_Adminhtml_OpsstatusController extends Mage_Adminhtml_Controller_Action
+{
+
+ protected function _isAllowed()
+ {
+ return Mage::getSingleton('admin/session')->isAllowed('sales/order/actions/invoice');
+ }
+
+ /**
+ * performs the status update call to Ingenico ePayments
+ */
+ public function updateAction()
+ {
+ $orderId = $this->getRequest()->getParam('order_id');
+ if (0 < $orderId) {
+ $order = Mage::getModel('sales/order')->load($orderId);
+ Mage::getModel('ops/status_update')->updateStatusFor($order);
+ }
+ $this->_redirect('adminhtml/sales_order/view/', array("order_id" => $orderId));
+ }
+
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/controllers/AliasController.php b/app/code/community/Netresearch/OPS/controllers/AliasController.php
new file mode 100644
index 0000000..06290a1
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/AliasController.php
@@ -0,0 +1,13 @@
+
+ * @author André Herrn
+ * @license OSL 3.0
+ */
+class Netresearch_OPS_ApiController extends Netresearch_OPS_Controller_Abstract
+{
+ /**
+ * Order instance
+ */
+ protected $_order;
+
+ /*
+ * Predispatch to check the validation of the request from OPS
+ */
+ public function preDispatch()
+ {
+ parent::preDispatch();
+ if (!$this->_validateOPSData()) {
+ $this->getResponse()->setHttpResponseCode(422);
+ $this->setFlag('', self::FLAG_NO_DISPATCH, 1);
+
+ return;
+ }
+ }
+
+ /**
+ * Action to control postback data from ops
+ *
+ */
+ public function postBackAction()
+ {
+ $params = $this->getRequest()->getParams();
+
+ try {
+ $status = $this->getPaymentHelper()->applyStateForOrder(
+ $this->_getOrder(),
+ $params
+ );
+ $redirectRoute = Mage::helper('ops/api')
+ ->getRedirectRouteFromStatus($status);
+
+ $this->_redirect(
+ $redirectRoute, array(
+ '_store' => $this->_getOrder()->getStoreId(),
+ '_query' => $params,
+ '_nosid' => true
+ )
+ );
+ } catch (Exception $e) {
+ Mage::helper('ops')->log(
+ "Run into exception '{$e->getMessage()}' in postBackAction"
+ );
+ $this->getResponse()->setHttpResponseCode(500);
+ }
+ }
+
+ /**
+ * Action to control postback data from ops
+ *
+ */
+ public function directLinkPostBackAction()
+ {
+
+ $params = $this->getRequest()->getParams();
+
+ try {
+ if (Mage::helper('ops/subscription')->isSubscriptionFeedback($params)) {
+ $this->getSubscriptionManager()->processSubscriptionFeedback($params);
+ } else {
+ $this->getDirectlinkHelper()->processFeedback(
+ $this->_getOrder(),
+ $params
+ );
+ }
+ } catch (Exception $e) {
+ Mage::helper('ops')->log(
+ "Run into exception '{$e->getMessage()}' in directLinkPostBackAction"
+ );
+ $this->getResponse()->setHttpResponseCode(500);
+ }
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/controllers/CustomerController.php b/app/code/community/Netresearch/OPS/controllers/CustomerController.php
new file mode 100644
index 0000000..fdc05ca
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/CustomerController.php
@@ -0,0 +1,68 @@
+
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+
+/**
+ * Netresearch_OPS_CustomerController
+ *
+ * @author Thomas Birke
+ * @author Michael Lühr
+ * @copyright Copyright (c) 2012 Netresearch GmbH & Co. KG
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+class Netresearch_OPS_CustomerController extends Mage_Core_Controller_Front_Action
+{
+ /**
+ * Check customer authentication
+ */
+ public function preDispatch()
+ {
+ parent::preDispatch();
+ $loginUrl = Mage::helper('customer')->getLoginUrl();
+
+ if (!Mage::getSingleton('customer/session')->authenticate($this, $loginUrl)) {
+ $this->setFlag('', self::FLAG_NO_DISPATCH, true);
+ }
+ }
+
+ /**
+ *
+ */
+ public function aliasesAction()
+ {
+ $this->loadLayout();
+ $this->_initLayoutMessages('customer/session');
+ if ($block = $this->getLayout()->getBlock('ops_customer_aliases')) {
+ $block->setRefererUrl($this->_getRefererUrl());
+ }
+ $headBlock = $this->getLayout()->getBlock('head');
+ if ($headBlock) {
+ $headBlock->setTitle(Mage::helper('ops')->__('My payment information'));
+ }
+ $this->renderLayout();
+ }
+
+ public function deleteAliasAction()
+ {
+ $aliasId = $this->_request->getParam('id');
+ $alias = Mage::getModel('ops/alias')->load($aliasId);
+ $customerId = Mage::helper('customer')->getCustomer()->getId();
+ if ($alias->getId() && $alias->getCustomerId() == $customerId) {
+ $alias->delete();
+ Mage::getSingleton('customer/session')->addSuccess(
+ Mage::helper('ops')->__('Removed payment information %s.', $alias->getPseudoAccountOrCcNo())
+ );
+ return $this->_redirectReferer();
+ }
+ Mage::getSingleton('customer/session')->addError(
+ Mage::helper('ops')->__('Could not remove payment information %s.', $alias->getPseudoAccountOrCcNo())
+ );
+ return $this->_redirectReferer();
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/controllers/DeviceController.php b/app/code/community/Netresearch/OPS/controllers/DeviceController.php
new file mode 100644
index 0000000..4c5b736
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/DeviceController.php
@@ -0,0 +1,83 @@
+
+ */
+?>
+config) {
+ $this->config = Mage::getModel('ops/config');
+ }
+
+ return $this->config;
+ }
+
+ /**
+ * Toggles the customers consent to transmit the generated deviceid to Ingenico ePayments
+ * to the value specified in request parameter consent
+ *
+ */
+ public function toggleConsentAction()
+ {
+ if ($this->getConfig()->getDeviceFingerPrinting()) {
+ $consent = (bool)$this->getRequest()->getParam(self::CONSENT_PARAMETER_KEY);
+ Mage::getSingleton('customer/session')
+ ->setData(Netresearch_OPS_Model_Payment_Abstract::FINGERPRINT_CONSENT_SESSION_KEY, $consent);
+ }
+
+ $this->consentAction();
+ }
+
+ /**
+ * Returns the state of consent of the customer
+ */
+ public function consentAction()
+ {
+ $resultArray = array(self::CONSENT_PARAMETER_KEY => false);
+
+ if ($this->getConfig()->getDeviceFingerPrinting()) {
+ $resultArray[self::CONSENT_PARAMETER_KEY] =
+ (bool)Mage::getSingleton('customer/session')
+ ->getData(Netresearch_OPS_Model_Payment_Abstract::FINGERPRINT_CONSENT_SESSION_KEY);
+ }
+
+ $this->getResponse()->setHeader('Content-type', 'application/json');
+ $this->getResponse()->setBody(Mage::helper('core')->jsonEncode($resultArray));
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/controllers/PaymentController.php b/app/code/community/Netresearch/OPS/controllers/PaymentController.php
new file mode 100644
index 0000000..245f74f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/controllers/PaymentController.php
@@ -0,0 +1,408 @@
+
+ * @author André Herrn
+ * @author Paul Siedler
+ */
+class Netresearch_OPS_PaymentController extends Netresearch_OPS_Controller_Abstract
+{
+ /**
+ * Load place from layout to make POST on ops
+ */
+ public function placeformAction()
+ {
+
+ $lastIncrementId = $this->_getCheckout()->getLastRealOrderId();
+
+ if ($lastIncrementId) {
+ $order = Mage::getModel('sales/order');
+ $order->loadByIncrementId($lastIncrementId);
+ } else {
+ return $this->_redirect('checkout/cart');
+ }
+
+ $quote = $this->_getCheckout()->getQuote();
+ if ($quote) {
+ $quote->setIsActive(false)->save();
+ }
+ $this->_getCheckout()->setOPSQuoteId($this->_getCheckout()->getQuoteId());
+ $this->_getCheckout()->setOPSLastSuccessQuoteId($this->_getCheckout()->getLastSuccessQuoteId());
+ $this->_getCheckout()->clear();
+
+ $this->loadLayout();
+ $this->renderLayout();
+ }
+
+ /**
+ * Render 3DSecure response HTML_ANSWER
+ */
+ public function placeform3dsecureAction()
+ {
+ $this->loadLayout();
+ $this->renderLayout();
+ }
+
+ /**
+ * Display our pay page, need to ops payment with external pay page mode *
+ */
+ public function paypageAction()
+ {
+ $this->loadLayout();
+ $this->renderLayout();
+ }
+
+ /**
+ * when payment gateway accept the payment, it will land to here
+ * need to change order status as processed ops
+ * update transaction id
+ *
+ */
+ public function acceptAction()
+ {
+ $redirect = '';
+ try {
+ $order = $this->_getOrder();
+ if ($this->getQuote()) {
+ $this->getQuote()->setIsActive(false)->save();
+ }
+ $this->_getCheckout()->setLastSuccessQuoteId($order->getQuoteId());
+ $this->_getCheckout()->setLastQuoteId($order->getQuoteId());
+ $this->_getCheckout()->setLastOrderId($order->getId());
+ } catch (Exception $e) {
+ /** @var Netresearch_OPS_Helper_Data $helper */
+ $helper = Mage::helper('ops');
+ $helper->log($helper->__("Exception in acceptAction: " . $e->getMessage()));
+ $this->getPaymentHelper()->refillCart($this->_getOrder());
+ $redirect = 'checkout/cart';
+ }
+ if ($redirect === '') {
+ $redirect = 'checkout/onepage/success';
+ }
+
+ $this->redirectOpsRequest($redirect);
+ }
+
+ /**
+ * the payment result is uncertain
+ * exception status can be 52 or 92
+ * need to change order status as processing ops
+ * update transaction id
+ *
+ */
+ public function exceptionAction()
+ {
+ $order = $this->_getOrder();
+ $this->_getCheckout()->setLastSuccessQuoteId($order->getQuoteId());
+ $this->_getCheckout()->setLastQuoteId($order->getQuoteId());
+ $this->_getCheckout()->setLastOrderId($order->getId());
+
+ $msg = 'Your order has been registered, but your payment is still marked as pending.';
+ $msg .= ' Please have patience until the final status is known.';
+ $this->_getCheckout()->addError(Mage::helper('ops/data')->__($msg));
+
+ $this->redirectOpsRequest('checkout/onepage/success');
+ }
+
+ /**
+ * when payment got decline
+ * need to change order status to cancelled
+ * take the user back to shopping cart
+ *
+ */
+ public function declineAction()
+ {
+ try {
+ $this->_getCheckout()->setQuoteId($this->_getCheckout()->getOPSQuoteId());
+ } catch (Exception $e) {
+ Mage::logException($e);
+ }
+
+ $this->getPaymentHelper()->refillCart($this->_getOrder());
+
+ $message = Mage::helper('ops')->__(
+ 'Your payment information was declined. Please select another payment method.'
+ );
+ Mage::getSingleton('core/session')->addNotice($message);
+ $redirect = 'checkout/onepage';
+ $this->redirectOpsRequest($redirect);
+ }
+
+ /**
+ * when user cancel the payment
+ * change order status to cancelled
+ * need to redirect user to shopping cart
+ *
+ */
+ public function cancelAction()
+ {
+ try {
+ $this->_getCheckout()->setQuoteId($this->_getCheckout()->getOPSQuoteId());
+ } catch (Exception $e) {
+ Mage::logException($e);
+ }
+ if (false == $this->_getOrder()->getId()) {
+ $this->_order = null;
+ $this->_getOrder($this->_getCheckout()->getLastQuoteId());
+ }
+
+ $this->getPaymentHelper()->refillCart($this->_getOrder());
+
+ $redirect = 'checkout/cart';
+ $this->redirectOpsRequest($redirect);
+
+ }
+
+ /**
+ * when user cancel the payment and press on button "Back to Catalog" or "Back to Merchant Shop" in Orops
+ *
+ */
+ public function continueAction()
+ {
+ /** @var Mage_Sales_Model_Order $order */
+ $order = Mage::getModel('sales/order')->load(
+ $this->_getCheckout()->getLastOrderId()
+ );
+ $this->getPaymentHelper()->refillCart($order);
+ $redirect = $this->getRequest()->getParam('redirect');
+ if ($redirect == 'catalog'): //In Case of "Back to Catalog" Button in OPS
+ $redirect = '/';
+ else: //In Case of Cancel Auto-Redirect or "Back to Merchant Shop" Button
+ $redirect = 'checkout/cart';
+ endif;
+ $this->redirectOpsRequest($redirect);
+ }
+
+ /*
+ * Check the validation of the request from OPS
+ */
+ protected function checkRequestValidity()
+ {
+ if (!$this->_validateOPSData()) {
+ Mage::throwException("Hash is not valid");
+ }
+ }
+
+ public function registerDirectDebitPaymentAction()
+ {
+ $params = $this->getRequest()->getParams();
+ $validator = Mage::getModel('ops/validator_payment_directDebit');
+ if (false === $validator->isValid($params)) {
+ $this->getResponse()
+ ->setHttpResponseCode(406)
+ ->setBody($this->__(implode(PHP_EOL, $validator->getMessages())))
+ ->sendHeaders();
+
+ return;
+ }
+ $payment = $this->_getCheckout()->getQuote()->getPayment();
+ $helper = Mage::helper('ops/directDebit');
+ $payment = $helper->setDirectDebitDataToPayment($payment, $params);
+
+ $payment->save();
+
+ $this->getResponse()->sendHeaders();
+ }
+
+ public function saveCcBrandAction()
+ {
+ $brand = $this->getRequest()->getParam('brand');
+ $alias = $this->getRequest()->getParam('alias');
+ $quote = $this->getQuote();
+ if ($quote->getId() === null) {
+ $this->_redirect('checkout/cart');
+ } else {
+ $payment = $quote->getPayment();
+ $payment->setAdditionalInformation('CC_BRAND', $brand);
+ $payment->setAdditionalInformation('alias', $alias);
+ $payment->setDataChanges(true);
+ $payment->save();
+ Mage::helper('ops')->log('saved cc brand ' . $brand . ' for quote #' . $quote->getId());
+ $this->getResponse()->sendHeaders();
+ }
+ }
+
+ /**
+ * Action to retry paying the order on Ingenico
+ *
+ */
+ public function retryAction()
+ {
+
+ $order = $this->_getOrder();
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $order->getPayment();
+ $message = false;
+
+ // only validate the parameters we added to the BACKURL ourselves
+ $params = array(
+ 'SHASIGN' => $this->getRequest()->getParam('SHASIGN'),
+ 'orderID' => $this->getRequest()->getParam('orderID')
+ );
+
+ if ($this->_validateOPSData($params) === false) {
+ $message = Mage::helper('ops')->__('Hash not valid');
+
+ } else {
+
+ if ($this->canRetryPayment($payment)) {
+
+ // Add Quote to Session, for the payment methods
+ /** @var Mage_Sales_Model_Quote $quote */
+ $quote = Mage::getModel('sales/quote')->load($order->getQuoteId());
+ /** @var Mage_Checkout_Model_Session $checkoutSession */
+ $checkoutSession = Mage::getSingleton('checkout/session');
+ $checkoutSession->setQuoteId($quote->getId());
+ // Set Quote to Active, to be able to load quote data
+ $quote->setIsActive(1);
+ $quote->save();
+
+ $this->loadLayout();
+ $this->renderLayout();
+
+ } else {
+ $message = Mage::helper('ops')->__(
+ 'Not possible to reenter the payment details for order %s', $order->getIncrementId()
+ );
+ }
+ }
+ if ($message) {
+ Mage::getSingleton('core/session')->addNotice($message);
+ $this->redirectOpsRequest('/');
+ }
+ }
+
+ public function updatePaymentAndPlaceFormAction()
+ {
+ // Save new payment method in order
+ /** @var Mage_Sales_Model_Order $order */
+ $order = $this->_getOrder();
+ /** @var Mage_Sales_Model_Order_Payment $payment */
+ $payment = $order->getPayment();
+ /** @var Mage_Sales_Model_Quote $quote */
+ $quote = Mage::getModel('sales/quote')->load($order->getQuoteId());
+ $quote->setIsActive(0);
+ $message = false;
+
+ try {
+ $newPayment = $this->getRequest()->getParam('payment');
+ $quote->getPayment()->importData($newPayment);
+ $payment->setMethod($newPayment['method'])->getMethodInstance()->assignData(new Varien_Object($newPayment));
+ $remoteAddr = Mage::helper('core/http')->getRemoteAddr();
+ $quote->setRemoteIp($remoteAddr);
+ $order->setRemoteIp($remoteAddr);
+ $quote->save();
+ $payment->save();
+ $order->save();
+
+ // Set Session Data for further process
+ /** @var Mage_Checkout_Model_Session $checkoutSession */
+ $checkoutSession = Mage::getSingleton('checkout/session');
+ $checkoutSession->replaceQuote($quote);
+ $checkoutSession->setLastOrderId($order->getId());
+ $checkoutSession->setLastRealOrderId($order->getIncrementId());
+ $checkoutSession->setLastQuoteId($quote->getId());
+ $checkoutSession->setLastSuccessQuoteId($quote->getId());
+
+ $redirectUrl = $payment->getMethodInstance()->getOrderPlaceRedirectUrl();
+
+ // Place order or rather in this case, send the inline payment method to Ingenico ePayments
+ if (empty($redirectUrl)) {
+ $checkoutSession->setRedirectUrl($redirectUrl);
+ $order->place();
+ $order->save();
+ }
+ } catch (Exception $e) {
+ $message = $e->getMessage();
+ }
+
+ if ($message) {
+ Mage::getSingleton('core/session')->addNotice($message);
+ $this->_redirect('checkout/cart');
+ } else {
+ if (empty($redirectUrl)) {
+ $this->_redirect('checkout/onepage/success');
+ } else {
+ $this->_redirectUrl($redirectUrl);
+ }
+ }
+ }
+
+ protected function wasIframeRequest()
+ {
+ return $this->getConfig()->getConfigData('template', $this->_getOrder()->getStoreId())
+ === Netresearch_OPS_Model_Payment_Abstract::TEMPLATE_OPS_IFRAME;
+ }
+
+ /**
+ * Generates the Javascript snippet that move the redirect to the parent frame in iframe mode.
+ *
+ * @param $redirect
+ *
+ * @return string javascript snippet
+ */
+ protected function generateJavaScript($redirect)
+ {
+ $javascript
+ = "
+ ";
+
+ return $javascript;
+ }
+
+ /**
+ * Redirects the customer to the given redirect path or inserts the js-snippet needed for iframe template mode into
+ * the response instead
+ *
+ * @param $redirect
+ */
+ protected function redirectOpsRequest($redirect)
+ {
+ if ($this->wasIframeRequest()) {
+ $this->getResponse()->setBody($this->generateJavaScript($redirect));
+ } else {
+ $this->_redirect($redirect);
+ }
+ }
+
+ /**
+ * @param Mage_Sales_Model_Order_Payment $payment
+ *
+ * @return bool
+ */
+ protected function canRetryPayment($payment)
+ {
+ $additionalInformation = $payment->getAdditionalInformation();
+ if (is_array($additionalInformation) && array_key_exists('status', $additionalInformation)) {
+ $status = $additionalInformation['status'];
+ return Netresearch_OPS_Model_Status::canResendPaymentInfo($status);
+ }
+
+ return true;
+ }
+}
diff --git a/app/code/community/Netresearch/OPS/data/ops_setup/data-install-14.02.05.php b/app/code/community/Netresearch/OPS/data/ops_setup/data-install-14.02.05.php
new file mode 100644
index 0000000..3821c2a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/data/ops_setup/data-install-14.02.05.php
@@ -0,0 +1,12 @@
+setConfigData(Netresearch_OPS_Model_Config::OPS_PAYMENT_PATH . 'mode', Netresearch_OPS_Model_Source_Mode::TEST);
diff --git a/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.02.05-14.06.25.php b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.02.05-14.06.25.php
new file mode 100644
index 0000000..3deb805
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.02.05-14.06.25.php
@@ -0,0 +1,12 @@
+getStores();
+foreach ($stores as $store) {
+ $activatedBrands = Mage::getStoreConfig('payment/ops_directEbanking/brands', $store->getId());
+ if (0 < strlen(trim($activatedBrands))) {
+ $activatedBrands = str_replace('Sofort Uberweisung', 'DirectEbanking', $activatedBrands);
+ Mage::getConfig()->saveConfig('payment/ops_directEbanking/brands', $activatedBrands, 'stores', $store->getId());
+ }
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.06.25-14.07.16.php b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.06.25-14.07.16.php
new file mode 100644
index 0000000..05ff059
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-14.06.25-14.07.16.php
@@ -0,0 +1,150 @@
+
+ * @category Netresearch
+ * @copyright Copyright (c) 2014 Netresearch GmbH & Co. KG (http://www.netresearch.de)
+ * @license http://opensource.org/licenses/osl-3.0.php Open Software License (OSL 3.0)
+ */
+/*
+ * @var $installer Mage_Core_Model_Resource_Setup
+ */
+$installer = $this;
+
+$regions = array(
+ array("CN",11,"Beijing"),
+ array("CN",50,"Chongqing"),
+ array("CN",31,"Shanghai"),
+ array("CN",12,"Tianjin"),
+ array("CN",34,"Anhui"),
+ array("CN",35,"Fujian"),
+ array("CN",62,"Gansu"),
+ array("CN",44,"Guangdong"),
+ array("CN",52,"Guizhou"),
+ array("CN",46,"Hainan"),
+ array("CN",13,"Hebei"),
+ array("CN",23,"Heilongjiang"),
+ array("CN",41,"Henan"),
+ array("CN",42,"Hubei"),
+ array("CN",43,"Hunan"),
+ array("CN",32,"Jiangsu"),
+ array("CN",36,"Jiangxi"),
+ array("CN",22,"Jilin"),
+ array("CN",21,"Liaoning"),
+ array("CN",63,"Qinghai"),
+ array("CN",61,"Shaanxi"),
+ array("CN",37,"Shandong"),
+ array("CN",14,"Shanxi"),
+ array("CN",51,"Sichuan"),
+ array("CN",71,"Taiwan"),
+ array("CN",53,"Yunnan"),
+ array("CN",33,"Zhejiang"),
+ array("CN",45,"Guangxi"),
+ array("CN",15,"Nei Mongol"),
+ array("CN",64,"Ningxia"),
+ array("CN",65,"Xinjiang"),
+ array("CN",54,"Xizang"),
+ array("CN",91,"Xianggang"),
+ array("CN",92,"Aomen"),
+ array("JP",1,"Hokkaidô"),
+ array("JP",2,"Aomori"),
+ array("JP",3,"Iwate"),
+ array("JP",4,"Miyagi"),
+ array("JP",5,"Akita"),
+ array("JP",6,"Yamagata"),
+ array("JP",7,"Hukusima"),
+ array("JP",8,"Ibaraki"),
+ array("JP",9,"Totigi"),
+ array("JP",10,"Gunma"),
+ array("JP",11,"Saitama"),
+ array("JP",12,"Tiba"),
+ array("JP",13,"Tôkyô"),
+ array("JP",14,"Kanagawa"),
+ array("JP",15,"Niigata"),
+ array("JP",16,"Toyama"),
+ array("JP",17,"Isikawa"),
+ array("JP",18,"Hukui"),
+ array("JP",19,"Yamanasi"),
+ array("JP",20,"Nagano"),
+ array("JP",21,"Gihu"),
+ array("JP",22,"Sizuoka"),
+ array("JP",23,"Aiti"),
+ array("JP",24,"Mie"),
+ array("JP",25,"Siga"),
+ array("JP",26,"Kyôto"),
+ array("JP",27,"Ôsaka"),
+ array("JP",28,"Hyôgo"),
+ array("JP",29,"Nara"),
+ array("JP",30,"Wakayama"),
+ array("JP",31,"Tottori"),
+ array("JP",32,"Simane"),
+ array("JP",33,"Okayama"),
+ array("JP",34,"Hirosima"),
+ array("JP",35,"Yamaguti"),
+ array("JP",36,"Tokusima"),
+ array("JP",37,"Kagawa"),
+ array("JP",38,"Ehime"),
+ array("JP",39,"Kôti"),
+ array("JP",40,"Hukuoka"),
+ array("JP",41,"Saga"),
+ array("JP",42,"Nagasaki"),
+ array("JP",43,"Kumamoto"),
+ array("JP",44,"Ôita"),
+ array("JP",45,"Miyazaki"),
+ array("JP",46,"Kagosima"),
+ array("JP",47,"Okinawa"),
+ array("MX","DIF","Distrito Federal"),
+ array("MX","AGU","Aguascalientes"),
+ array("MX","BCN","Baja California"),
+ array("MX","BCS","Baja California Sur"),
+ array("MX","CAM","Campeche"),
+ array("MX","COA","Coahuila"),
+ array("MX","COL","Colima"),
+ array("MX","CHP","Chiapas"),
+ array("MX","CHH","Chihuahua"),
+ array("MX","DUR","Durango"),
+ array("MX","GUA","Guanajuato"),
+ array("MX","GRO","Guerrero"),
+ array("MX","HID","Hidalgo"),
+ array("MX","JAL","Jalisco"),
+ array("MX","MEX","México"),
+ array("MX","MIC","Michoacán"),
+ array("MX","MOR","Morelos"),
+ array("MX","NAY","Nayarit"),
+ array("MX","NLE","Nuevo León"),
+ array("MX","OAX","Oaxaca"),
+ array("MX","PUE","Puebla"),
+ array("MX","QUE","Querétaro"),
+ array("MX","ROO","Quintana Roo"),
+ array("MX","SLP","San Luis Potosí"),
+ array("MX","SIN","Sinaloa"),
+ array("MX","SON","Sonora"),
+ array("MX","TAB","Tabasco"),
+ array("MX","TAM","Tamaulipas"),
+ array("MX","TLA","Tlaxcala"),
+ array("MX","VER","Veracruz"),
+ array("MX","YUC","Yucatán"),
+ array("MX","ZAC","Zacatecas")
+);
+
+foreach ($regions as $row) {
+ $bind = array(
+ 'country_id' => $row[0],
+ 'code' => $row[1],
+ 'default_name' => $row[2],
+ );
+ $installer->getConnection()->insert($installer->getTable('directory/country_region'), $bind);
+ $regionId = $installer->getConnection()->lastInsertId($installer->getTable('directory/country_region'));
+
+ $bind = array(
+ 'locale' => 'en_US',
+ 'region_id' => $regionId,
+ 'name' => $row[2]
+ );
+ $installer->getConnection()->insert($installer->getTable('directory/country_region_name'), $bind);
+}
+
+$countries = explode(',', Mage::getStoreConfig(Mage_Directory_Helper_Data::XML_PATH_STATES_REQUIRED));
+$countries[] = 'CN';
+$countries[] = 'JP';
+$countries[] = 'MX';
+Mage::getConfig()->saveConfig(Mage_Directory_Helper_Data::XML_PATH_STATES_REQUIRED, implode(',', $countries));
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.06.08-15.11.02.php b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.06.08-15.11.02.php
new file mode 100644
index 0000000..6e27115
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.06.08-15.11.02.php
@@ -0,0 +1,44 @@
+
+ */
+?>
+getModuleConfig('Mage_Admin')->version;
+if (version_compare($adminVersion, '1.6.1.1', '>')) {
+ /** @var Mage_Admin_Model_Variable $variable */
+ $variable = Mage::getModel('admin/variable')->load($variableName, 'variable_name');
+
+ $variable->setData('variable_name', $variableName)
+ ->setData('is_allowed', 1)
+ ->save();
+}
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.11.09-16.03.09.php b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.11.09-16.03.09.php
new file mode 100644
index 0000000..40dfa65
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/data/ops_setup/data-upgrade-15.11.09-16.03.09.php
@@ -0,0 +1,37 @@
+saveConfig($aliasUrlPath, $newAliasUrl);
+
+$websites = Mage::app()->getWebsites();
+
+/** @var Mage_Core_Model_Website $website */
+foreach($websites as $website){
+ $oldWebsiteAliasUrl = $website->getConfig($aliasUrlPath);
+ if(strlen($oldWebsiteAliasUrl) > 0 && $oldWebsiteAliasUrl != $oldAliasUrl){
+
+ $newWebsiteAliasUrl = str_replace('ncol/prod/alias_gateway_utf8.asp', 'Tokenization/HostedPage', $oldWebsiteAliasUrl);
+ Mage::getConfig()->saveConfig($aliasUrlPath, $newWebsiteAliasUrl, 'websites', $website->getId());
+ }
+ /** @var Mage_Core_Model_Store $store */
+ foreach($website->getStores() as $store){
+ $oldStoreAliasUrl = Mage::getStoreConfig($aliasUrlPath, $store->getId());
+ if(strlen($oldStoreAliasUrl) > 0 && $oldStoreAliasUrl != $oldAliasUrl) {
+ $newStoreAliasUrl = str_replace('ncol/prod/alias_gateway_utf8.asp', 'Tokenization/HostedPage', $oldStoreAliasUrl);
+ Mage::getConfig()->saveConfig($aliasUrlPath, $newStoreAliasUrl, 'stores', $store->getId());
+ }
+ }
+}
+
+Mage::getConfig()->cleanCache();
+
+
diff --git a/app/code/community/Netresearch/OPS/etc/config.xml b/app/code/community/Netresearch/OPS/etc/config.xml
new file mode 100644
index 0000000..16345ef
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/etc/config.xml
@@ -0,0 +1,599 @@
+
+
+
+
+
+ 16.12.14
+
+
+
+
+
+ Netresearch_OPS_Helper
+
+
+
+
+ Netresearch_OPS_Model
+ ops_mysql4
+
+
+ Netresearch_OPS_Model_Mysql4
+
+
+
+
+
+ ops_kwixo_category_mapping
+
+
+ ops_kwixo_shipping_setting
+
+
+
+
+
+
+ Netresearch_OPS_Block
+
+
+
+
+
+
+
+ singleton
+ ops/observer
+ checkoutTypeOnepageSaveOrderBefore
+
+
+
+
+
+
+ singleton
+ ops/observer
+ setOrderStateDirectLink
+
+
+
+
+
+
+
+ singleton
+ ops/observer
+ updateOrderCancelButton
+
+
+ singleton
+ ops/observer
+ updateRecurringProfileButtons
+
+
+
+
+
+
+
+ downloadable/observer
+ setLinkStatus
+
+
+
+
+
+
+
+ singleton
+ ops/observer
+ clearPaymentMethodFromQuote
+
+
+
+
+
+
+ ops/observer
+ addCcPaymentMethod
+
+
+
+
+
+
+
+ ops/observer
+ sendTransactionalEmails
+ singleton
+
+
+
+
+
+
+
+
+ Netresearch_OPS
+ Mage_Sales_Model_Mysql4_Setup
+
+
+
+
+
+
+
+ Ingenico ePayments resend payment information
+ ops/ops_email_resend_payment_info.html
+ html
+
+
+ Ingenico ePayments suspend subscription request
+ ops/suspend_subscription.html
+ html
+
+
+ Ingenico ePayments payPerMail template
+ ops/ops_pay_per_mail_info.html
+ html
+
+
+
+
+
+
+
+
+
+ Netresearch_OPS_Adminhtml
+
+
+
+
+
+
+
+
+
+ ops.xml
+
+
+
+
+
+
+
+ ops/observer
+ appendCheckBoxToRefundForm
+
+
+ ops/observer
+ showWarningForClosedTransactions
+
+
+ singleton
+ ops/observer
+ updateRecurringProfileEditForm
+
+
+
+
+
+
+
+ ops/observer
+ salesOrderPaymentCapture
+
+
+
+
+
+
+ ops/observer
+ addStatusUpdateButtonToOrderView
+
+
+ ops/observer
+ disableCaptureForZeroAmountInvoice
+
+
+ ops/observer
+ addResendPaymentInfoButtonToOrderView
+
+
+
+
+
+
+ ops/observer
+ sendPayPerMailInfo
+
+
+
+
+
+
+
+
+ Netresearch_OPS.csv
+
+
+
+
+
+
+
+
+
+ ops.xml
+
+
+
+
+ /ops/api
+
+
+
+ standard
+
+ Netresearch_OPS
+ ops
+
+
+
+
+
+
+
+ Netresearch_OPS.csv
+
+
+
+
+
+
+
+
+ ops/observer
+ controllerActionCheckoutOnepagePostdispatch
+
+
+
+
+
+
+ ops/observer
+ overrideRecurringProfileState
+
+
+
+
+
+
+
+
+
+ ops/payment_abstract
+ Ingenico ePayments
+
+ sha1
+ authorize
+ 0
+ ops
+ custom
+
+ https://secure.ogone.com/ncol/test
+ https://secure.ogone.com/ncol/prod
+ /orderstandard_utf8.asp
+ /Tokenization/HostedPage
+ /orderstandard_utf8.asp
+ /maintenancedirect.asp
+ /orderdirect.asp
+ /querydirect.asp
+
+ https://secure.ogone.com/ncol/test/orderstandard_utf8.asp
+ https://secure.ogone.com/ncol/test/Tokenization/HostedPage
+ https://secure.ogone.com/ncol/test/orderstandard_utf8.asp
+ https://secure.ogone.com/ncol/test/maintenancedirect.asp
+ https://secure.ogone.com/ncol/test/orderdirect.asp
+ https://secure.ogone.com/ncol/test/querydirect.asp
+ https://ogone.test.v-psp.com/Tokenization/HostedPage
+ 1
+ 1
+ support@ecom.ingenico.com
+
+ http://payment-services.ingenico.com/en/ogone/support/guides/integration%20guides/magento-extension
+ http://ingenico.support.netresearch.de/
+ http://ingenico.support.netresearch.de/
+ orderId
+ orderId
+ 1
+ 0
+
+ 1
+
+ 50
+ 50
+ 35
+ 35
+ 35
+ 2
+ 25
+ 10
+ 25
+ 10
+ 35
+ 35
+ 10
+ 2
+ 40
+ 30
+ 35
+ 10
+ 50
+ 50
+
+
+
+ billing:firstname
+ billing:lastname
+
+ billing:postcode
+ billing:region_id
+ billing:city
+ OWNERTELNO
+ billing:street1
+ billing:firstname
+ billing:lastname
+ billing:postcode
+ shipping:firstname
+ shipping:lastname
+ shipping:street1
+ shipping:street2
+ shipping:street3
+ shipping:country_id
+ shipping:region_id
+ shipping:postcode
+ shipping:city
+ shipping:street
+ shipping:region_id
+
+ sales
+ payment_services_ops_resendPaymentInfo_template
+ payment_services_ops_payPerMail_template
+ 15
+ 0
+ sales
+ payment_services_ops_suspendSubscription_template
+ 0
+ 45
+ 0
+
+
+
+
+ Ingenico ePayments DirectDebit
+ ops/payment_directDebit
+
+
+ Ingenico ePayments PostFinanceEFinance
+ ops/payment_postFinanceEFinance
+
+
+ Ingenico ePayments EDankort
+ ops/payment_eDankort
+
+
+ Ingenico ePayments KbcOnline
+ ops/payment_kbcOnline
+
+
+ Ingenico ePayments iDEAL
+ ops/payment_iDeal
+
+ ABN AMRO
+ Rabobank
+ ING
+ SNS Bank
+ Regio Bank
+ ASN Bank
+ Bunq
+ Triodos Bank
+ Van Lanschot Bankiers
+ Knab Bank
+
+
+
+ Ingenico ePayments Belfius Direct Net
+ ops/payment_belfiusDirectNet
+
+
+ Ingenico ePayments BankTransfer
+ ops/payment_bankTransfer
+
+
+ Rechnung
+ ops/payment_openInvoiceDe
+ 0
+ 1
+ DE
+
+
+ Rechnung (Niederlande)
+ ops/payment_openInvoiceNl
+ 1
+ NL
+
+
+ Rechnung (Österreich)
+ ops/payment_openInvoiceAt
+ 0
+ 1
+ AT
+
+
+ Ingenico ePayments CbcOnline
+ ops/payment_cbcOnline
+
+
+ Ingenico ePayments GiroPay
+ ops/payment_giroPay
+
+
+ Ingenico ePayments Masterpass
+ ops/payment_masterpass
+
+
+ Ingenico ePayments InterSolve
+ ops/payment_interSolve
+
+
+ Ingenico ePayments CashU
+ ops/payment_cashU
+
+
+ Ingenico ePayments Paypal
+ ops/payment_paypal
+
+
+ Ingenico ePayments Eps
+ ops/payment_eps
+
+
+ Ingenico ePayments PingPing
+ ops/payment_pingPing
+
+
+ Ingenico ePayments FortisPayButton
+ ops/payment_fortisPayButton
+
+
+ Ingenico ePayments SofortÜberweisung
+ ops/payment_directEbanking
+
+
+ Ingenico ePayments Cc
+ ops/payment_cc
+ 0
+ 0
+ American Express,Diners Club,Maestro,MaestroUK,MasterCard,VISA,JCB
+ AIRPLUS,American Express,Aurore,CB,Cofinoga,Dankort,Diners Club,JCB,Maestro,MaestroUK,MasterCard,PRIVILEGE,PostFinance card,UATP,UNEUROCOM,VISA
+ 0
+
+
+ Ingenico ePayments DebitCard
+ ops/payment_debitcard
+ 0
+ 0
+ Maestro,MaestroUK,MasterCard,VISA
+ Maestro,MaestroUK,MasterCard,VISA
+ 0
+
+
+ Ingenico ePayments IngHomePay
+ ops/payment_ingHomePay
+
+
+ Ingenico ePayments Paysafecard
+ ops/payment_paysafecard
+
+
+ Ingenico ePayments Kwixo Credit
+ ops/payment_kwixoCredit
+
+
+ Ingenico ePayments Kwixo Apres Reception
+ ops/payment_KwixoApresReception
+
+
+ Ingenico ePayments Kwixo Comptant
+ ops/payment_KwixoComptant
+
+
+ Additional Ingenico ePayments payment methods
+ ops/payment_Flex
+
+
+ Existing Ingenico ePayments Transaction
+ ops/payment_backend_opsId
+
+
+
+ Netresearch_OPS_Model_Payment_OpenInvoiceNl
+ Netresearch_OPS_Model_Payment_OpenInvoiceAt
+
+
+ Netresearch_OPS_Model_Payment_OpenInvoiceNl
+ Netresearch_OPS_Model_Payment_OpenInvoiceAt
+
+
+
+ Ingenico ePayments ChinaUnionPay
+ ops/payment_chinaUnionPay
+
+
+ 0
+ Ingenico ePayments Subscription Manager via Cc
+ ops/payment_recurring_cc
+ 0
+ American Express,Diners Club,MaestroUK,MasterCard,VISA,JCB
+ American Express,Diners Club,MaestroUK,MasterCard,VISA,JCB
+ 0
+
+
+
+ ops/payment_bancontact
+
+
+
+ ops/payment_payPerMail
+ 1
+
+
+
+
+
+
+
+
+ */5 * * * *
+
+
+ ops/observer::cleanUpOldPaymentData
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/app/code/community/Netresearch/OPS/etc/jstranslator.xml b/app/code/community/Netresearch/OPS/etc/jstranslator.xml
new file mode 100644
index 0000000..a4a9472
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/etc/jstranslator.xml
@@ -0,0 +1,27 @@
+
+
+
+ Payment failed. Please select another payment method.
+
+
+ Payment failed. Please review your input or select another payment method.
+
+
+ LOAD_TOKEN
+
+
+ SUCCESS_TOKEN
+
+
+ SUCCESS_TOKEN_FRONTEND
+
+
+ FAILURE_TOKEN
+
+
+ FAILURE_TOKEN_FRONTEND
+
+
+ This is a required field.
+
+
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/etc/system.xml b/app/code/community/Netresearch/OPS/etc/system.xml
new file mode 100644
index 0000000..d8bd02f
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/etc/system.xml
@@ -0,0 +1,3542 @@
+
+
+
+
+
+ Payment Services
+ sales
+ text
+ 450
+ 1
+ 1
+ 1
+
+
+ Ingenico ePayments Information
+ text
+ ops/system_config_support
+ 0
+ 1
+ 1
+ 1
+
+
+ Ingenico ePayments Account
+ text
+ 1
+ 1
+ 1
+ 1
+
+
+ Debug
+ This will log requests and responses in /var/log/ops.log
+ Make sure the global Magento logging is also enabled.
+ select
+ adminhtml/system_config_source_yesno
+ 2000
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 30
+ 1
+ 1
+ 1
+
+
+ PSPID
+ text
+ PSPID is a case sensitive field
+ 40
+ 1
+ 1
+ 1
+
+
+ Hash algorithm
+ select
+ ops/system_config_backend_hashMethods
+ 49
+ 1
+ 1
+ 1
+ Technical information on tab Global security parameters .]]>
+
+
+ SHA-IN Pass phrase
+ Technical Information on tab Data and origin verification .]]>
+ Technical information on tab Data and origin verification .]]>
+ adminhtml/system_config_backend_encrypted
+ obscure
+ 50
+ 1
+ 1
+ 1
+
+
+ SHA-OUT Pass phrase
+ Technical Information on tab Transaction feedback .]]>
+ Technical information on tab Transaction feedback .]]>
+ adminhtml/system_config_backend_encrypted
+ obscure
+ 60
+ 1
+ 1
+ 1
+
+
+ Mode
+
+ 69
+ select
+ ops/source_mode
+ ops/system_config_mode
+ Please note that, after changing this value, you might also need to update additional fields like API-User and password, PSPID or SHA-IN/OUT pass phrase.
]]>
+ 1
+ 1
+ 1
+
+
+ Frontend Gateway URL
+ text
+ Production url example: https://secure.ogone.com/ncol/prod/orderstandard_utf8.asp]]>
+ 70
+ 1
+ 1
+ 1
+ custom
+
+
+ Alias Gateway URL
+ text
+ Production url example: https://secure.ogone.com/Tokenization/HostedPage]]>
+ 71
+ 1
+ 1
+ 1
+ custom
+
+
+ DirectLink Gateway URL
+ text
+ Production url example: https://secure.ogone.com/ncol/prod/maintenancedirect.asp]]>
+ 72
+ 1
+ 1
+ 1
+ custom
+
+
+ DirectLink Gateway Order URL
+ text
+ Production url example: https://secure.ogone.com/ncol/prod/orderdirect.asp]]>
+ 73
+ 1
+ 1
+ 1
+ custom
+
+
+ DirectLink Maintenance API URL
+ text
+ Production url example: https://secure.ogone.com/ncol/prod/querydirect.asp]]>
+ 74
+ 1
+ 1
+ 1
+ custom
+
+
+ API User
+ Users.]]>
+ text
+ 85
+ 1
+ 1
+ 1
+
+
+ API Password
+
+ adminhtml/system_config_backend_encrypted
+ obscure
+ 88
+ 1
+ 1
+ 1
+
+
+ Payment Action
+ Technical information on tab Global transaction parameters .]]>
+ select
+ ops/source_paymentAction
+ 90
+ 1
+ 1
+ 0
+
+
+ Send Invoice to Customer
+ select
+ adminhtml/system_config_source_yesno
+ authorize_capture
+ 95
+ 1
+ 1
+ 0
+
+
+ Payment Template
+ select
+ ops/source_template
+
+ ops/system_config_template
+
+ 100
+ 1
+ 1
+ 1
+
+
+
+ Template Identifier/Url
+ Enter the TemplateRootId you received from Ingenico ePayments or the url to an external template.
+ text
+ 102
+ 1
+ 1
+ 1
+ ops_template
+ required-entry
+
+
+ Title of the Ingenico ePayments Template
+ text
+ 110
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Background Color of Ingenico ePayments Template
+ text
+
+ 130
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Text Color of the Ingenico ePayments Template
+ text
+
+ 140
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Table Background Color of the Ingenico ePayments Template
+ text
+
+ 150
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Table Text Color of the Ingenico ePayments Template
+ text
+
+ 160
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Show catalog button
+ select
+ adminhtml/system_config_source_yesno
+ 165
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Show home button
+ select
+ adminhtml/system_config_source_yesno
+ 165
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Button Background Color of the Ingenico ePayments Template
+ text
+ 170
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Button Text Color of the Ingenico ePayments Template
+ text
+
+ 180
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Font Family of the Ingenico ePayments Template
+ text
+
+ 190
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Logo of the Ingenico ePayments Template
+ text
+ URL/filename of the logo. The URL must be absolute and stored on a secure server.
+ 200
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Layout of Payment Methods
+
+ select
+ ops/source_pmlist
+ 210
+ 1
+ 1
+ 1
+ ops,ops_iframe
+ required-entry
+
+
+ Order reference in case of redirect payments
+ See chapter 'Configuration', section 'Magento - Backend' in the documentation. Please note that the option 'orderId' is not used for the Kwixo payment methods.
+ select
+ ops/source_orderReference
+ 220
+ 1
+ 1
+ 1
+
+
+ Order reference in case of inline payments
+ See chapter 'Configuration', section 'Magento - Backend' in the documentation.
+ select
+ ops/source_orderReference
+ 221
+ 1
+ 1
+ 1
+
+
+ Show Quote ID in the order grid
+ select
+ adminhtml/system_config_source_yesno
+ 230
+ 1
+ 1
+ 1
+
+
+ Submit extra parameters
+
+ Enable this if you wish to use fraud detection
+ select
+ adminhtml/system_config_source_yesno
+ 240
+ 1
+ 1
+ 1
+
+
+ Resend payment information identity
+ select
+ adminhtml/system_config_source_email_identity
+ 250
+ 1
+ 1
+ 1
+ Sender identity. See 'Store Email Adresses'.
+
+
+ Resend payment information template
+ select
+ adminhtml/system_config_source_email_template
+ 260
+ 1
+ 1
+ 1
+ The email template to use. Choose 'Default Template from Locale' to use Ingenico ePayments extensions default template.
+
+
+ Enable device fingerprinting
+ When enabling this, you still need to request the explicit consent of the customer in the checkout to transmit this data.
+ This functionality will transmit specific customer data as hash to Ingenico ePayments to identify the device from which the transaction was sent can be identified with the highest probability.
+ select
+ adminhtml/system_config_source_yesno
+ 280
+ 1
+ 0
+ 0
+
+
+ Timeout for transactions
+ This value specifies the request timeout for that transaction. A value between 30 and 60 seconds is possible.
+ text
+ validate-digits-range digits-range-30-60
+ 290
+ 1
+ 0
+ 0
+
+
+ Credit/Debit card Split
+
+ Ingenico ePayments documentation.]]>
+ select
+ adminhtml/system_config_source_yesno
+ 300
+ 1
+ 1
+ 1
+
+
+ Billing day for monthly subscriptions
+ text
+ validate-digits validate-digits-range digits-range-1-31
+ 300
+ Determines the day of the month when a monthly subscription gets triggered.
+ 1
+ 1
+ 0
+
+
+ Billing day for weekly subscriptions
+ select
+ adminhtml/system_config_source_locale_weekdays
+ 310
+ Determines the day of the week when a weekly subscription gets triggered.
+ 1
+ 1
+ 0
+
+
+ Store contact responsible for subscription handling
+ select
+ adminhtml/system_config_source_email_identity
+ 320
+ 1
+ 1
+ 1
+ This contact will receive the suspend/cancel requests for the subscriptions. See 'Store Email Adresses'.
+
+
+ E-Mail template for suspending/canceling a subscription
+ select
+ adminhtml/system_config_source_email_template
+ 330
+ 1
+ 1
+ 1
+ This e-mail template is used for the automatically generated e-mail that is getting sent to the corresponding contact, if a customer wants to cancel a subscription.
+
+
+
+
+
+
+ ops/system_config_paymentForm
+
+
+ Ingenico ePayments DirectDebit
+ 40
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Countries
+ multiselect
+ required-entry
+ 1
+ 30
+ ops/source_directDebit_countries
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ 40
+ allowspecific
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ 50
+ multiselect
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 60
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 70
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+ Enable for backend
+ select
+ adminhtml/system_config_source_yesno
+ 100
+ 1
+ 1
+ 1
+
+
+ Enabled Alias Manager
+ select
+ adminhtml/system_config_source_yesno
+ 110
+ If this option is enabled, the customer's alias data will be saved in the shop. The data can then be used again later if the buyer has stored them permanently on Ingenico ePayments side.
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments PostFinanceEFinance
+ 50
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments EDankort
+ 60
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments KbcOnline
+ 70
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments iDEAL
+ 80
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Belfius Direct Net
+ 90
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments BankTransfer
+ 100
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Countries
+ multiselect
+ required-entry
+ 1
+ 30
+ ops/source_bankTransfer_countries
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 40
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 50
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 60
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 70
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Open Invoice DE
+ 110
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ gender and date of birth are required fields in the checkout. Otherwise this payment method will not be displayed.]]>
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Allow for discounted carts
+ Allow payment method for discounted carts. Please note that not all aquirers support transmission of discount items.
+ select
+ adminhtml/system_config_source_yesno
+ 10
+ 1
+ 1
+ 1
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment Logo
+ 30
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 40
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+ Request Data Encoding
+ 50
+ select
+ ops/system_config_backend_encoding
+
+
+ 1
+ 1
+ 1
+
+
+ Show invoice terms link
+ 60
+ select
+ adminhtml/system_config_source_yesno
+
+ 1
+ 1
+ 1
+
+
+ Invoice terms title
+ 61
+ text
+ 1
+ 1
+ 1
+
+ 1
+
+ required-entry
+
+
+ Invoice terms URL
+ 62
+ text
+ 1
+ 1
+ 1
+
+ 1
+
+ required-entry
+
+
+
+
+ Ingenico ePayments Open Invoice AT
+ 120
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ gender and date of birth are required fields in the checkout. Otherwise this payment method will not be displayed.]]>
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Allow for discounted carts
+ Allow payment method for discounted carts. Please note that not all aquirers support transmission of discount items.
+ select
+ adminhtml/system_config_source_yesno
+ 10
+ 1
+ 1
+ 1
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment Logo
+ 30
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 40
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+ Request Data Encoding
+ 50
+ select
+ ops/system_config_backend_encoding
+
+
+ 1
+ 1
+ 1
+
+
+ Show invoice terms link
+ 60
+ select
+ adminhtml/system_config_source_yesno
+
+ 1
+ 1
+ 1
+
+
+ Invoice terms title
+ 61
+ text
+ 1
+ 1
+ 1
+
+ 1
+
+ required-entry
+
+
+ Invoice terms URL
+ 62
+ text
+ 1
+ 1
+ 1
+
+ 1
+
+ required-entry
+
+
+
+
+ Ingenico ePayments Open Invoice NL
+ 130
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ gender and date of birth are required fields in the checkout. Otherwise this payment method will not be displayed.]]>
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment Logo
+ 30
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 40
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+ Request Data Encoding
+ 50
+ select
+ ops/system_config_backend_encoding
+
+
+ 1
+ 1
+ 1
+
+
+ Show invoice terms link
+ 60
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+
+
+
+ Invoice terms title
+ 61
+ text
+ 1
+ 1
+ 1
+
+ 1
+
+ required-entry
+
+
+ Invoice terms URL
+ 62
+ text
+ 1
+ 1
+ 1
+
+ 1
+
+ required-entry
+
+
+
+
+ Ingenico ePayments CbcOnline
+ 140
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments GiroPay
+ 150
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Masterpass
+ 160
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments InterSolve
+ 170
+ 1
+ 1
+ 1 fkbc
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+ Brand
+ ops/system_config_form_field_brand
+ ops/system_config_backend_intersolve_brands
+ 70
+ 1
+ 1
+ 1
+ Add one or more brands. In field "BRAND" you will have to enter the value you got from Ingenico ePayments.
+
+
+
+
+ Ingenico ePayments CashU
+ 180
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Paypal
+ 200
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Eps
+ 210
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments PingPing
+ 220
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments FortisPayButton
+ 230
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePaymentsSofortÜberweisung
+ 240
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Brands
+ multiselect
+ required-entry
+ 1
+ 20
+ ops/source_directEbanking_brands
+ 1
+ 1
+ 1
+
+
+ Sort Order
+ text
+ 30
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 40
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 50
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 60
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 70
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Cc
+ 250
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 10
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Enabled Card Types
+ multiselect
+ 30
+ ops/source_cc_types
+ 1
+ 1
+ 1
+
+
+ Enable redirect payment for all card types
+ Yes, customers will be redirected to the external Ingenico ePayments payment page.]]>
+ select
+ adminhtml/system_config_source_yesno
+ 40
+ 1
+ 1
+ 1
+
+
+ Enable inline payment (Direct Link) for these card types
+
+ multiselect
+ ops/source_cc_aliasInterfaceEnabledTypes
+ 41
+ 0
+ 1
+ 1
+ 1
+
+
+ Enable 3D secure
+
+ select
+ adminhtml/system_config_source_yesno
+ 50
+ 1
+ 1
+ 0
+
+
+ Payment Logo
+ 80
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 90
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+ Enable for backend
+
+ select
+ adminhtml/system_config_source_yesno
+ 100
+ 1
+ 1
+ 1
+
+
+ Enabled Alias Manager
+ select
+ adminhtml/system_config_source_yesno
+ 110
+ If this option is enabled, the customer's alias data will be saved in the shop. The data can then be used again later if the buyer has stored them permanently on Ingenico ePayments side.
+ 1
+ 1
+ 1
+
+
+ Aliasusage New
+ text
+ 110
+ Here you can enter the desired text which will be displayed on Ingenico ePayments side.
+ 1
+ 1
+ 1
+
+
+ Aliasusage existing Alias
+ text
+ 111
+ Here you can enter the desired text which is used for existing alias, the text will be displayed on Ingenico ePayments side.
+ 1
+ 1
+ 1
+
+
+ Allow zero amount authorization
+ Only if payment action is authorize.
+ select
+ adminhtml/system_config_source_yesno
+ 130
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Dc
+ 260
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 10
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 11
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Enabled Card Types
+ multiselect
+ 30
+ ops/source_debitCard_types
+ 1
+ 1
+ 1
+
+
+ Enable redirect payment for all card types
+ Yes, customers will be redirected to the external Ingenico ePayments payment page.]]>
+ select
+ adminhtml/system_config_source_yesno
+ 40
+ 1
+ 1
+ 1
+
+
+ Enable inline payment (Direct Link) for these card types
+
+ multiselect
+ ops/source_debitCard_aliasInterfaceEnabledTypes
+ 41
+ 0
+ 1
+ 1
+ 1
+
+
+ Enable 3D secure
+
+ select
+ adminhtml/system_config_source_yesno
+ 50
+ 1
+ 1
+ 0
+
+
+ Payment Logo
+ 80
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 90
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+ Enable for backend
+
+ select
+ adminhtml/system_config_source_yesno
+ 100
+ 1
+ 1
+ 1
+
+
+ Enabled Alias Manager
+ select
+ adminhtml/system_config_source_yesno
+ 110
+ 1
+ 1
+ 1
+
+
+ Aliasusage New
+ text
+ 111
+ Here you can enter the desired text which will be displayed on Ingenico ePayments side.
+ 1
+ 1
+ 1
+
+
+ Aliasusage existing Alias
+ text
+ 112
+ Here you can enter the desired text which is used for existing alias, the text will be displayed on Ingenico ePayments side.
+ 1
+ 1
+ 1
+
+
+ Show Alias Manager information for guests
+ select
+ adminhtml/system_config_source_yesno
+ 120
+ 1
+ 1
+ 1
+ 1
+
+
+ Allow zero amount authorization
+ Only if payment action is authorize.
+ select
+ adminhtml/system_config_source_yesno
+ 130
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments IngHomePay
+ 270
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Paysafecard
+ 280
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments KwixoCredit
+ 290
+ 1
+ 1
+ 1
+
+
+ Kwixxo Config
+ text
+ ops/system_config_kwixoconfiguration
+ 0
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Estimated Delivery Date
+ text
+ 30
+ required-entry validate-number validate-greater-than-zero
+ 1
+ 1
+ 1
+ 1
+
+
+ RNP Fee
+ select
+ adminhtml/system_config_source_yesno
+ 40
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Method Type
+ select
+ ops/source_kwixo_shipMethodType
+ validate-select
+ 50
+ 1
+ 1
+ 1
+
+ 1
+
+
+
+ Default Shipping Speed (in hours)
+ Text
+ validate-number validate-greater-than-zero
+ 60
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Method Details
+ Textarea
+ validate-length maximum-length-50
+ 80
+ 1
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 90
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 100
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 110
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 120
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments KwixoApresReception
+ 300
+ 1
+ 1
+ 1
+
+
+ Kwixxo Config
+ text
+ ops/system_config_kwixoconfiguration
+ 0
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Estimated Delivery Date
+ text
+ 30
+ required-entry validate-greater-than-zero
+ 1
+ 1
+ 1
+ 1
+
+
+ RNP Fee
+ select
+ adminhtml/system_config_source_yesno
+ 40
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Method Type
+ select
+ ops/source_kwixo_shipMethodType
+ 50
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Speed (in hours)
+ Text
+ validate-number validate-greater-than-zero
+ 60
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Method Details
+ Text
+ validate-length maximum-length-50
+ 70
+ 1
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 80
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 90
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 100
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 110
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments KwixoComptant
+ 310
+ 1
+ 1
+ 1
+
+
+ Kwixxo Config
+ text
+ ops/system_config_kwixoconfiguration
+ 0
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Estimated Delivery Date
+ text
+ 30
+ required-entry validate-number validate-greater-than-zero
+ 1
+ 1
+ 1
+ 1
+
+
+ RNP Fee
+ select
+ adminhtml/system_config_source_yesno
+ 40
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Method Type
+ select
+ ops/source_kwixo_shipMethodType
+ validate-select
+ 50
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Speed (in hours)
+ Text
+ validate-number validate-greater-than-zero
+ 60
+ 1
+ 1
+ 1
+ 1
+
+
+ Default Shipping Method Details
+ Textarea
+ validate-length maximum-length-50
+ 80
+ 1
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 90
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 100
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 110
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 120
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Existing Ingenico ePayments Transaction
+ 320
+ 1
+ 0
+ 0
+
+
+ Enable for backend
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 0
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 0
+ 0
+ required-entry
+
+
+ Sort Order for backend
+ text
+ 20
+ 1
+ 0
+ 0
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Flex payment method
+ 330
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+ 1
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+ 1
+
+
+ Show empty default option
+ select
+ adminhtml/system_config_source_yesno
+ 30
+ 1
+ 1
+ 1
+
+ 1
+
+
+ Default option title
+ text
+ 31
+ 1
+ 1
+ 1
+ required-entry
+ Title to display for the default option.
+ 1
+
+
+ Methods
+ ops/system_config_form_field_method
+ ops/system_config_backend_flex_methods
+ 40
+ 1
+ 1
+ 1
+ Add one or more methods. In field 'PM' you will have to enter the PM value you got from Ingenico ePayments, same goes for the field 'BRAND'.
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 50
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 60
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 70
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 80
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments ChinaUnionPay
+ 340
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ This payment method always uses direct sale as payment action.
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments Subscription Manager via Cc
+ 350
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ ops/system_config_form_field_recurringActive
+ To use this functionality you have to have the Subscription manager function enabled in the Ingenico ePayments backend.]]>
+
+ 10
+ 1
+ 1
+ 1
+
+
+ Enabled Card Types
+ multiselect
+ 30
+ ops/source_cc_recurringTypes
+ 1
+ 1
+ 1
+ 1
+
+
+ Enable 3D secure
+
+ select
+ adminhtml/system_config_source_yesno
+ 50
+ 1
+ 1
+ 0
+ 1
+
+
+ Payment Logo
+ 80
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 90
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments BCMC
+ 360
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 30
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 40
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ Payment Logo
+ 50
+ paymentLogo
+ adminhtml/system_config_backend_image
+ ops/paymentLogo
+ ops/paymentLogo
+ 1
+ 1
+ 1
+ Allowed file types: jpeg, gif, png.
+
+
+ Payment Logo Visibility
+ 60
+ select
+ ops/system_config_backend_paymentLogo
+ 1
+ 1
+ 1
+
+
+
+
+ Ingenico ePayments PayPerMail
+ 370
+ 1
+ 1
+ 1
+
+
+ Enabled
+ select
+ adminhtml/system_config_source_yesno
+ 1
+ 1
+ 1
+ 0
+
+
+ Title
+ text
+ 10
+ 1
+ 1
+ 1
+ required-entry
+
+ 1
+
+
+
+ Sort Order
+ text
+ 20
+ 1
+ 1
+ 1
+ 1
+
+ 1
+
+
+
+ Payment from Applicable Countries
+ allowspecific
+ 50
+ adminhtml/system_config_source_payment_allspecificcountries
+ 1
+ 1
+ 0
+
+
+ Payment from Specific Countries
+ multiselect
+ 60
+ adminhtml/system_config_source_country
+ 1
+ 1
+ 0
+ 1
+ 1
+
+
+ PayPerMail Email Template
+ select
+ adminhtml/system_config_source_email_template
+ 260
+ 1
+ 1
+ 1
+ The email template to use. Choose 'Default Template from Locale' to use Ingenico ePayments extensions default template.
+
+
+
+
+
+
+ 0
+ 0
+ 0
+
+
+ 0
+ 0
+ 0
+
+
+ 27
+
+
+
+
+
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-install-1.0.1.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-install-1.0.1.php
new file mode 100644
index 0000000..61f4dae
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-install-1.0.1.php
@@ -0,0 +1,46 @@
+
+ * @author Thomas Birke
+ * @copyright 2012 Netresearch App Factory AG (http://www.netresearch.de)
+ * @license OSL 3.0 (http://opensource.org/licenses/osl-3.0.php)
+ * @link http://www.netresearch.de/magento/
+ */
+
+/* @var $this Mage_Sales_Model_Mysql4_Setup */
+$this->startSetup();
+// Add column to grid table
+$this->getConnection()->addColumn(
+ $this->getTable('sales/order_grid'),
+ 'quote_id',
+ "int(10) unsigned NOT NULL default '0' comment 'id of related quote'"
+);
+// Add key to table for this field,
+// it will improve the speed of searching & sorting by the field
+$this->getConnection()->addKey(
+ $this->getTable('sales/order_grid'),
+ 'quote_id',
+ 'quote_id'
+);
+
+// Now you need to fullfill existing rows with data from address table
+$select = $this->getConnection()->select();
+$select->join(
+ array('flat_order'=>$this->getTable('sales/order')),
+ $this->getConnection()->quoteInto(
+ 'flat_order.entity_id = order_grid.entity_id',
+ 'quote_id'
+ ),
+ array('quote_id' => 'quote_id')
+);
+$this->getConnection()->query(
+ $select->crossUpdateFromSelect(
+ array('order_grid' => $this->getTable('sales/order_grid'))
+ )
+);
+
+$this->endSetup();
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-1.0.1-12.12.03.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-1.0.1-12.12.03.php
new file mode 100644
index 0000000..3a8ee78
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-1.0.1-12.12.03.php
@@ -0,0 +1,24 @@
+startSetup();
+
+$installer->run(
+ "
+ DROP TABLE IF EXISTS {$this->getTable('ops_alias')};
+ CREATE TABLE {$this->getTable('ops_alias')} (
+ `id` int(11) unsigned NOT NULL auto_increment,
+ `customer_id` int(10),
+ `alias` varchar(32),
+ `brand` varchar(50),
+ `billing_address_hash` varchar(255),
+ `shipping_address_hash` varchar(255),
+ `pseudo_account_or_cc_no` varchar(255),
+ `expiration_date` varchar(10),
+ `payment_method` varchar(50),
+ `created_at` timestamp default CURRENT_TIMESTAMP,
+ PRIMARY KEY (`id`)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+"
+);
+
+$installer->endSetup();
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.04.10-13.04.16.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.04.10-13.04.16.php
new file mode 100644
index 0000000..7313e34
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.04.10-13.04.16.php
@@ -0,0 +1,126 @@
+startSetup();
+
+// delete obsolete credit card brands
+$obsoleteCCTypes = array(
+ 'billy',
+ 'solo',
+ 'aurora',
+ 'netreserve',
+
+);
+
+// remove obsolete credit card brands from the configured types array
+$ccTypes = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_cc/types')
+ ->load();
+foreach ($ccTypes as $ccType) {
+ $newCcTypes = array();
+ $values = explode(',', $ccType->getValue());
+ foreach ($values as $value) {
+ if (in_array(strToLower($value), $obsoleteCCTypes)) {
+ continue;
+ }
+ $newCcTypes[] = $value;
+ }
+ $ccType->setValue(implode(',', $newCcTypes));
+ $ccType->save();
+}
+
+// remove obsolete credit card brands from available types array
+$ccTypes = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_cc/availableTypes')
+ ->load();
+foreach ($ccTypes as $ccType) {
+ $newCcTypes = array();
+ $values = explode(',', $ccType->getValue());
+ foreach ($values as $value) {
+ if (in_array(strToLower($value), $obsoleteCCTypes)) {
+ continue;
+ }
+ $newCcTypes[] = $value;
+ }
+ $ccType->setValue(implode(',', $newCcTypes));
+ $ccType->save();
+}
+
+// remove obsolete credit card brands from the configured inline types array
+$ccTypes = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_cc/inline_types')
+ ->load();
+foreach ($ccTypes as $ccType) {
+ $newCcTypes = array();
+ $values = explode(',', $ccType->getValue());
+ foreach ($values as $value) {
+ if (in_array(strToLower($value), $obsoleteCCTypes)) {
+ continue;
+ }
+ $newCcTypes[] = $value;
+ }
+ $ccType->setValue(implode(',', $newCcTypes));
+ $ccType->save();
+}
+
+// delete obsolete payment method config acceptgiro and centea online
+$installer->run(
+ "
+ DELETE FROM {$this->getTable('core_config_data')}
+ WHERE 'path' IN
+ ('payment/ops_acceptgiro/active',
+ 'payment/ops_acceptgiro/title',
+ 'payment/ops_acceptgiro/sort_order'
+ );
+ DELETE FROM {$this->getTable('core_config_data')}
+ WHERE `path` IN
+ ('payment/ops_centeaonline/active',
+ 'payment/ops_centeaonline/title',
+ 'payment/ops_centeaonline/sort_order'
+ );
+"
+);
+
+
+// update dexiaOnline to belfiusOnline
+$belfiusActive = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_belfiusDirectNet/active')
+ ->load();
+if (0 === $belfiusActive->count()) {
+ $installer->run(
+ "
+ UPDATE {$this->getTable('core_config_data')}
+ SET path = 'payment/ops_belfiusDirectNet/active'
+ WHERE path = 'payment/ops_dexiaDirectNet/active';
+ "
+ );
+}
+
+$belfiusTitle = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_belfiusDirectNet/title')
+ ->load();
+if (0 == $belfiusTitle->count()) {
+ $installer->run(
+ "
+ UPDATE {$this->getTable('core_config_data')}
+ SET path = 'payment/ops_belfiusDirectNet/title'
+ WHERE path = 'payment/ops_dexiaDirectNet/title';
+ "
+ );
+}
+
+$belfiusSortOrder = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_belfiusDirectNet/sort_order')
+ ->load();
+if (0 === $belfiusSortOrder->count()) {
+ $installer->run(
+ "
+ UPDATE {$this->getTable('core_config_data')}
+ SET path = 'payment/ops_belfiusDirectNet/sort_order'
+ WHERE path = 'payment/ops_dexiaDirectNet/sort_order';
+ "
+ );
+}
+/*
+ *
+ */
+$installer->endSetup();
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.05.30-13.06.07.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.05.30-13.06.07.php
new file mode 100644
index 0000000..e4046dc
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.05.30-13.06.07.php
@@ -0,0 +1,70 @@
+startSetup();
+$conn = $installer->getConnection();
+$conn->addColumn(
+ $this->getTable('ops/alias'),
+ 'card_holder',
+ 'VARCHAR(255) NULL DEFAULT NULL AFTER `alias`'
+);
+$conn->addColumn(
+ $this->getTable('ops/alias'),
+ 'state',
+ "VARCHAR(100) NULL DEFAULT '". Netresearch_OPS_Model_Alias_State::PENDING ."' AFTER `payment_method`"
+);
+
+$conn->addColumn(
+ $this->getTable('ops/alias'),
+ 'store_id',
+ "smallint(5) NULL DEFAULT NULL AFTER `state`"
+);
+
+$installer->run(
+ "
+ UPDATE {$this->getTable('ops_alias')}
+ SET state = '". Netresearch_OPS_Model_Alias_State::ACTIVE ."'
+ WHERE alias IS NOT NULL;
+
+"
+);
+
+$installer->run(
+ "
+ DELETE FROM {$this->getTable('ops_alias')}
+ WHERE id NOT in (
+ SELECT alias.id FROM (
+ SELECT * FROM {$this->getTable('ops_alias')}
+ ORDER BY `created_at` desc
+ ) as alias
+ GROUP BY alias.customer_id, alias.billing_address_hash, alias.shipping_address_hash
+ )
+"
+);
+
+$aliasActive = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_cc/active_alias')
+ ->load();
+if (0 === $aliasActive->count()) {
+ $installer->run(
+ "
+ UPDATE {$this->getTable('core_config_data')}
+ SET path = 'payment/ops_cc/active_alias'
+ WHERE path = 'payment/ops_alias/active';
+ "
+ );
+}
+$hintForGuestsActive = Mage::getModel('core/config_data')->getCollection()
+ ->addFieldToFilter('path', 'payment/ops_cc/show_alias_manager_info_for_guests')
+ ->load();
+if (0 == $hintForGuestsActive->count()) {
+ $installer->run(
+ "
+ UPDATE {$this->getTable('core_config_data')}
+ SET path = 'payment/ops_cc/show_alias_manager_info_for_guests'
+ WHERE path = 'payment/ops_alias/show_info_for_guests';
+ "
+ );
+}
+
+$installer->endSetup();
+
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.06.07-13.07.04.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.06.07-13.07.04.php
new file mode 100644
index 0000000..2ce5b89
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.06.07-13.07.04.php
@@ -0,0 +1,17 @@
+startSetup();
+
+
+
+$installer->run(
+ "
+ UPDATE {$this->getTable('core_config_data')}
+ SET value = 'Ingenico ePayments Belfius Direct Net'
+ WHERE path = 'payment/ops_belfiusDirectNet/title'
+ AND value = 'Ingenico ePayments BelfiusDirectNet';
+ "
+);
+
+$installer->endSetup();
+
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.07.10-13.07.23.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.07.10-13.07.23.php
new file mode 100644
index 0000000..f648f07
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.07.10-13.07.23.php
@@ -0,0 +1,14 @@
+startSetup();
+$installer->run(
+ "
+ CREATE TABLE IF NOT EXISTS {$this->getTable('ops/kwixo_category_mapping')} (
+ `id` int(11) unsigned NOT NULL auto_increment,
+ `kwixo_category_id` int(10),
+ `category_id` int(10),
+ PRIMARY KEY (`id`)
+ ) ENGINE=InnoDB DEFAULT CHARSET=utf8;
+ "
+);
+$installer->endSetup();
\ No newline at end of file
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.11.04-13.11.05.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.11.04-13.11.05.php
new file mode 100644
index 0000000..4d59817
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-13.11.04-13.11.05.php
@@ -0,0 +1,15 @@
+startSetup();
+
+$installer->run(
+ "
+ UPDATE {$this->getTable('core_config_data')}
+ SET value = '-100'
+ WHERE path = 'payment/ops_cc/sort_order'
+ AND value is NULL
+ "
+);
+
+$installer->endSetup();
+
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-14.01.27-14.02.05.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-14.01.27-14.02.05.php
new file mode 100644
index 0000000..a0ec7be
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-14.01.27-14.02.05.php
@@ -0,0 +1,52 @@
+startSetup();
+
+$tableName = $installer->getTable('ops/kwixo_shipping_setting');
+$table = $installer->getConnection()
+ ->newTable($tableName)
+ ->addColumn(
+
+ 'id', Varien_Db_Ddl_Table::TYPE_INTEGER, null, array(
+ 'unsigned' => true,
+ 'nullable' => false,
+ 'primary' => true,
+ 'identity' => true,
+ ),
+ 'id'
+ )
+ ->addColumn(
+ 'shipping_code', Varien_Db_Ddl_Table::TYPE_VARCHAR, 255, array(
+ 'nullable' => false,
+ ),
+ 'shipping code'
+ )
+ ->addColumn(
+
+ 'kwixo_shipping_type', Varien_Db_Ddl_Table::TYPE_SMALLINT, null, array(
+ 'unsigned' => true,
+ 'nullable' => false,
+ ),
+ 'kwixo shipping type'
+ )
+ ->addColumn(
+ 'kwixo_shipping_speed', Varien_Db_Ddl_Table::TYPE_SMALLINT, null, array(
+ 'unsigned' => true,
+ 'nullable' => false,
+ 'primary' => false,
+ 'identity' => false,
+ ),
+ 'kwixo shipping type'
+ )
+ ->addColumn(
+
+ 'kwixo_shipping_details', Varien_Db_Ddl_Table::TYPE_VARCHAR, 50, array(
+ 'unsigned' => true,
+ 'nullable' => true,
+ ),
+ 'kwixo shipping details'
+ )
+ ->addIndex('unique', 'shipping_code');
+$installer->getConnection()->createTable($table);
+$installer->endSetup();
+
diff --git a/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-16.05.26-27.06.16.php b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-16.05.26-27.06.16.php
new file mode 100644
index 0000000..a67d87a
--- /dev/null
+++ b/app/code/community/Netresearch/OPS/sql/ops_setup/mysql4-upgrade-16.05.26-27.06.16.php
@@ -0,0 +1,8 @@
+getConnection()->modifyColumn(
+ $installer->getTable('ops/alias'), 'alias', "varchar(255) NULL DEFAULT NULL"
+);
diff --git a/app/design/adminhtml/default/default/layout/ops.xml b/app/design/adminhtml/default/default/layout/ops.xml
new file mode 100644
index 0000000..86eab1b
--- /dev/null
+++ b/app/design/adminhtml/default/default/layout/ops.xml
@@ -0,0 +1,89 @@
+
+
+
+
+
+
+ quote_id
+
+
+ quote_id
+ text
+ 80px
+
+ real_order_id
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ skin_css ops.css
+
+
+
+
+
+
+
+
+
+
+
+
+ customer_edit_tab_ops_alias customer_edit_tab_ops_alias
+
+
+
+
+ extjs/ext-tree.js
+ extjs/ext-tree-checkbox.js
+ js extjs/ext-tree.js
+ js extjs/ext-tree-checkbox.js
+ js_css extjs/resources/css/ext-all.css
+ js_css extjs/resources/css/ytheme-magento.css
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/app/design/adminhtml/default/default/template/ops/categoriestree.phtml b/app/design/adminhtml/default/default/template/ops/categoriestree.phtml
new file mode 100644
index 0000000..d9dbf8f
--- /dev/null
+++ b/app/design/adminhtml/default/default/template/ops/categoriestree.phtml
@@ -0,0 +1,632 @@
+
+
+
+getStoreSwitcherHtml() ?>
+
+getRoot()): ?>
+
+
+
+
+
+
\ No newline at end of file
diff --git a/app/design/adminhtml/default/default/template/ops/form/cc.phtml b/app/design/adminhtml/default/default/template/ops/form/cc.phtml
new file mode 100644
index 0000000..31cee98
--- /dev/null
+++ b/app/design/adminhtml/default/default/template/ops/form/cc.phtml
@@ -0,0 +1,177 @@
+
+ */
+
+/** @var $this Netresearch_OPS_Block_Form_Cc */
+?>
+
+
+getMethodCode() ?>
+
+getQuote()->getStoreId(); ?>
+
+
+
diff --git a/app/design/adminhtml/default/default/template/ops/form/directDebit.phtml b/app/design/adminhtml/default/default/template/ops/form/directDebit.phtml
new file mode 100644
index 0000000..133cc5b
--- /dev/null
+++ b/app/design/adminhtml/default/default/template/ops/form/directDebit.phtml
@@ -0,0 +1,189 @@
+
+ */
+?>
+
+
+getMethodCode();
+$storeId = $this->getQuote()->getStoreId();
+?>
+
\ No newline at end of file
diff --git a/app/design/adminhtml/default/default/template/ops/form/kwixo/category.phtml b/app/design/adminhtml/default/default/template/ops/form/kwixo/category.phtml
new file mode 100644
index 0000000..2193dab
--- /dev/null
+++ b/app/design/adminhtml/default/default/template/ops/form/kwixo/category.phtml
@@ -0,0 +1,21 @@
+
+ getFormInitScripts() ?>
+
+
+
+
+ hasFooterButtons()): ?>
+
+
+
+ getFormScripts() ?>
+
\ No newline at end of file
diff --git a/app/design/adminhtml/default/default/template/ops/form/kwixo/shipping.phtml b/app/design/adminhtml/default/default/template/ops/form/kwixo/shipping.phtml
new file mode 100644
index 0000000..cf5614d
--- /dev/null
+++ b/app/design/adminhtml/default/default/template/ops/form/kwixo/shipping.phtml
@@ -0,0 +1,102 @@
+
+
+getShippingMethods();
+$kwixoShippingTypes = $this->getKwixoShippingTypes();
+if (0 < count($shippingMethods)):
+?>
+