TimeTrex Community Edition v16.2.0

This commit is contained in:
2022-12-13 07:10:06 +01:00
commit 472f000c1b
6810 changed files with 2636142 additions and 0 deletions
.htaccess3rd_party_credits.txtINSTALL.txtLICENSEREADME.txtUPGRADE.txt
api
classes
.htaccess
ChequeForms
GovernmentForms
GovernmentForms.class.phpGovernmentForms_Base.class.php
country
ca
grid.class.php
us
examples
adodb
adodb-active-record.inc.phpadodb-active-recordx.inc.phpadodb-csvlib.inc.phpadodb-datadict.inc.phpadodb-error.inc.phpadodb-errorhandler.inc.phpadodb-errorpear.inc.phpadodb-exceptions.inc.phpadodb-iterator.inc.phpadodb-lib.inc.phpadodb-loadbalancer.inc.phpadodb-memcache.lib.inc.phpadodb-pager.inc.phpadodb-pear.inc.phpadodb-perf.inc.phpadodb-php4.inc.phpadodb-time.inc.phpadodb-xmlschema.inc.phpadodb-xmlschema03.inc.phpadodb.inc.php
contrib
datadict
drivers
lang
license.txt
pear
perf
pivottable.inc.phprsfilter.inc.phpserver.phptips_portable_sql.htmtoexport.inc.phptohtml.inc.phptute.htmxmlschema.dtdxmlschema03.dtd
xsl
bitmask
bounce_handler
misc
modules
accrual
api
accrual
client
company
core
department
hierarchy
holiday
import
kpi
message
notification
pay_stub
pay_stub_amendment
payperiod
policy
punch
qualification
report
request
roe
schedule
system_job_queue
ui_kit
unauthenticated
users
company
core
Authentication.class.phpAuthenticationTrustedDeviceFactory.class.phpAuthenticationTrustedDeviceListFactory.class.phpAuthorizationFactory.class.phpAuthorizationListFactory.class.phpBackgroundProcess.class.phpBreadCrumb.class.phpCalculatePayStub.class.phpCalculatePolicy.class.phpCurrencyFactory.class.phpCurrencyListFactory.class.phpCurrencyRateFactory.class.phpCurrencyRateListFactory.class.phpCustomFieldFactory.class.phpCustomFieldListFactory.class.phpDebug.class.phpDependencyTree.class.phpEnvironment.class.phpException.class.phpExceptionFactory.class.phpExceptionListFactory.class.phpFactory.class.phpFactoryListIterator.class.phpFastTree.class.phpFormVariables.class.phpGeneralLedgerExport.class.phpGroup.class.phpIdempotentRequestFactory.class.phpIdempotentRequestListFactory.class.phpLockFile.class.phpLogDetailFactory.class.phpLogDetailListFactory.class.phpLogFactory.class.phpLogListFactory.class.phpLogRotate.class.phpMisc.class.phpOption.class.phpOtherFieldFactory.class.phpOtherFieldListFactory.class.phpPager.class.phpPermission.class.phpPermissionControlFactory.class.phpPermissionControlListFactory.class.phpPermissionFactory.class.phpPermissionListFactory.class.phpPermissionUserFactory.class.phpPermissionUserListFactory.class.phpProfiler.class.phpProgressBar.class.phpPurgeDatabase.class.phpRateLimit.class.phpRedirect.class.phpSerializer.class.phpSharedMemory.class.phpSort.class.phpStationBranchFactory.class.phpStationBranchListFactory.class.phpStationDepartmentFactory.class.phpStationDepartmentListFactory.class.phpStationExcludeUserFactory.class.phpStationExcludeUserListFactory.class.phpStationFactory.class.phpStationIncludeUserFactory.class.phpStationIncludeUserListFactory.class.phpStationListFactory.class.phpStationUserFactory.class.phpStationUserGroupFactory.class.phpStationUserGroupListFactory.class.phpStationUserListFactory.class.phpSystemJobQueue.class.phpSystemJobQueueFactory.class.phpSystemJobQueueListFactory.class.phpSystemSettingFactory.class.phpSystemSettingListFactory.class.phpTTDate.class.phpTTLDAP.class.phpTTLicense.class.phpTTLog.class.phpTTMail.class.phpTTPDF.class.phpTTPassword.class.phpTTTree.class.phpTTUUID.class.phpTTi18n.class.phpURLBuilder.class.phpUnitConvert.class.phpUserDateFactory.class.phpUserDateListFactory.class.phpUserDateTotalFactory.class.phpUserDateTotalListFactory.class.phpValidator.class.phpWage.class.php
cron
department
geoip
help
hierarchy
holiday
import
install
Install.class.phpInstallSchema.class.phpInstallSchema_1000A.class.phpInstallSchema_1001A.class.phpInstallSchema_1002A.class.phpInstallSchema_1003A.class.phpInstallSchema_1004A.class.phpInstallSchema_1005A.class.phpInstallSchema_1006A.class.phpInstallSchema_1007A.class.phpInstallSchema_1008A.class.phpInstallSchema_1009A.class.phpInstallSchema_1010A.class.phpInstallSchema_1011A.class.phpInstallSchema_1012A.class.phpInstallSchema_1013A.class.phpInstallSchema_1014A.class.phpInstallSchema_1015A.class.phpInstallSchema_1016A.class.phpInstallSchema_1017A.class.phpInstallSchema_1018A.class.phpInstallSchema_1019A.class.phpInstallSchema_1020A.class.phpInstallSchema_1021A.class.phpInstallSchema_1022A.class.phpInstallSchema_1023A.class.phpInstallSchema_1024A.class.phpInstallSchema_1025A.class.phpInstallSchema_1026A.class.phpInstallSchema_1027A.class.phpInstallSchema_1028A.class.phpInstallSchema_1029A.class.phpInstallSchema_1030A.class.phpInstallSchema_1031A.class.phpInstallSchema_1032A.class.phpInstallSchema_1033A.class.phpInstallSchema_1034A.class.phpInstallSchema_1035A.class.phpInstallSchema_1036A.class.phpInstallSchema_1037A.class.phpInstallSchema_1038A.class.phpInstallSchema_1039A.class.phpInstallSchema_1040A.class.phpInstallSchema_1041A.class.phpInstallSchema_1042A.class.phpInstallSchema_1043A.class.phpInstallSchema_1044A.class.phpInstallSchema_1045A.class.phpInstallSchema_1046A.class.phpInstallSchema_1047A.class.phpInstallSchema_1049A.class.phpInstallSchema_1050A.class.phpInstallSchema_1051A.class.phpInstallSchema_1052A.class.phpInstallSchema_1053A.class.phpInstallSchema_1054A.class.phpInstallSchema_1055A.class.phpInstallSchema_1056A.class.phpInstallSchema_1058A.class.phpInstallSchema_1059A.class.phpInstallSchema_1060A.class.phpInstallSchema_1061A.class.phpInstallSchema_1062A.class.phpInstallSchema_1063A.class.phpInstallSchema_1064A.class.phpInstallSchema_1065A.class.phpInstallSchema_1066A.class.phpInstallSchema_1067A.class.phpInstallSchema_1068A.class.phpInstallSchema_1069A.class.phpInstallSchema_1070A.class.phpInstallSchema_1071A.class.phpInstallSchema_1090A.class.phpInstallSchema_1093A.class.phpInstallSchema_1100A.class.phpInstallSchema_1101A.class.phpInstallSchema_1102A.class.phpInstallSchema_1103A.class.phpInstallSchema_1104A.class.phpInstallSchema_1105A.class.phpInstallSchema_1106A.class.phpInstallSchema_1107A.class.phpInstallSchema_1108A.class.phpInstallSchema_1109A.class.phpInstallSchema_1110A.class.phpInstallSchema_1111A.class.phpInstallSchema_1112A.class.phpInstallSchema_1113A.class.phpInstallSchema_1114A.class.phpInstallSchema_1117A.class.phpInstallSchema_1118A.class.phpInstallSchema_1119A.class.phpInstallSchema_1121A.class.phpInstallSchema_1122A.class.phpInstallSchema_1123A.class.phpInstallSchema_1124A.class.phpInstallSchema_1125A.class.phpInstallSchema_1126A.class.phpInstallSchema_1127A.class.phpInstallSchema_1128A.class.phpInstallSchema_1129A.class.phpInstallSchema_1131A.class.phpInstallSchema_1132A.class.phpInstallSchema_1133A.class.phpInstallSchema_1134A.class.phpInstallSchema_1135A.class.phpInstallSchema_1136A.class.phpInstallSchema_1137A.class.phpInstallSchema_1138A.class.phpInstallSchema_1139A.class.phpInstallSchema_Base.class.php
sql
kpi
message
notification
other
pay_stub
pay_stub_amendment
payperiod
plugins
policy
AbsencePolicyFactory.class.phpAbsencePolicyListFactory.class.phpAccrualPolicyAccountFactory.class.phpAccrualPolicyAccountListFactory.class.phpAccrualPolicyFactory.class.phpAccrualPolicyListFactory.class.phpAccrualPolicyMilestoneFactory.class.phpAccrualPolicyMilestoneListFactory.class.phpBreakPolicyFactory.class.phpBreakPolicyListFactory.class.phpContributingPayCodePolicyFactory.class.phpContributingPayCodePolicyListFactory.class.phpContributingShiftPolicyFactory.class.phpContributingShiftPolicyListFactory.class.phpExceptionPolicyControlFactory.class.phpExceptionPolicyControlListFactory.class.phpExceptionPolicyFactory.class.phpExceptionPolicyListFactory.class.phpHolidayPolicyFactory.class.phpHolidayPolicyListFactory.class.phpHolidayPolicyRecurringHolidayFactory.class.phpHolidayPolicyRecurringHolidayListFactory.class.phpMealPolicyFactory.class.phpMealPolicyListFactory.class.phpOverTimePolicyFactory.class.phpOverTimePolicyListFactory.class.phpPayCodeFactory.class.phpPayCodeListFactory.class.phpPayFormulaPolicyFactory.class.phpPayFormulaPolicyListFactory.class.phpPolicyGroupAccrualPolicyFactory.class.phpPolicyGroupAccrualPolicyListFactory.class.phpPolicyGroupFactory.class.phpPolicyGroupListFactory.class.phpPolicyGroupOverTimePolicyFactory.class.phpPolicyGroupOverTimePolicyListFactory.class.phpPolicyGroupPremiumPolicyFactory.class.phpPolicyGroupPremiumPolicyListFactory.class.phpPolicyGroupRoundIntervalPolicyFactory.class.phpPolicyGroupRoundIntervalPolicyListFactory.class.phpPolicyGroupUserFactory.class.phpPolicyGroupUserListFactory.class.phpPremiumPolicyBranchFactory.class.phpPremiumPolicyBranchListFactory.class.phpPremiumPolicyDepartmentFactory.class.phpPremiumPolicyDepartmentListFactory.class.phpPremiumPolicyFactory.class.phpPremiumPolicyListFactory.class.phpRegularTimePolicyFactory.class.phpRegularTimePolicyListFactory.class.phpRoundIntervalPolicyFactory.class.phpRoundIntervalPolicyListFactory.class.phpSchedulePolicyFactory.class.phpSchedulePolicyListFactory.class.php
punch
qualification
report
request
schedule
soap
ui_kit
users
other
payroll_deduction
pear
upload
composer.jsoncomposer.lockfavicon.icofiles.deletefiles.sha1
includes
index.phpinstall_cron.sh
interface
Login.phpblank.html
flex
html5
.jshintrcConfirmEmail.phpDownForMaintenance.phpIndexController.js
client
components
dist
BaseViewController.bundle.jsBaseWindowController.bundle.jsDocumentSubViewController.bundle.jsJobApplicantEducationSubViewController.bundle.jsJobApplicantEmploymentSubViewController.bundle.jsJobApplicantLanguageSubViewController.bundle.jsJobApplicantLicenseSubViewController.bundle.jsJobApplicantLocationSubViewController.bundle.jsJobApplicantMembershipSubViewController.bundle.jsJobApplicantReferenceSubViewController.bundle.jsJobApplicantSkillSubViewController.bundle.jsJobApplicantSubBaseViewController.bundle.jsJobApplicationSubViewController.bundle.js_css.main_ui.template.html_css.portal.template.html_css.quick_punch.template.html_js.main_ui.template.html_js.portal.template.html_js.quick_punch.template.htmlattendance-accrual-AccrualViewController.bundle.jsattendance-accrual_balance-AccrualBalanceViewController.bundle.jsattendance-exceptions-ExceptionViewController.bundle.jsattendance-in_out-InOutViewController.bundle.jsattendance-job-JobGroupViewController.bundle.jsattendance-job-JobViewController.bundle.jsattendance-job_item-JobItemGroupViewController.bundle.jsattendance-job_item-JobItemViewController.bundle.jsattendance-job_item_amendment-JobItemAmendmentViewController.bundle.jsattendance-map-MapViewController.bundle.jsattendance-map-MapViewController.cssattendance-punch_tag-PunchTagGroupViewController.bundle.jsattendance-punch_tag-PunchTagViewController.bundle.jsattendance-punches-PunchesViewController.bundle.jsattendance-recurring_schedule_control-RecurringScheduleControlViewController.bundle.jsattendance-recurring_schedule_template_control-RecurringScheduleTemplateControlViewController.bundle.jsattendance-schedule-ScheduleShiftViewController.bundle.jsattendance-schedule-ScheduleViewController.bundle.jsattendance-schedule-ScheduleViewController.cssattendance-timesheet-TimeSheetViewController.bundle.jsattendance-timesheet-TimeSheetViewController.cssattendance-timesheet-UserDateTotalParentViewController.bundle.jsattendance-timesheet-UserDateTotalViewController.bundle.jsawesomebox-AComboBox.bundle.jsawesomebox-ADropDown.bundle.jsawesomebox-ALayoutCache.bundle.jsawesomebox-ASearchInput.bundle.jscheckbox-TCheckbox.bundle.jscolor-picker-TColorPicker.bundle.jscolumn_editor-ColumnEditor.bundle.jscombobox-TComboBox.bundle.jscommon-AuthorizationHistoryCommon.bundle.jscommon-BaseTreeViewController.bundle.jscommon-EmbeddedMessageCommon.bundle.jscommon-RequestViewCommonController.bundle.jscompany-branch-BranchViewController.bundle.jscompany-companies-CompaniesViewController.bundle.jscompany-company-CompanyViewController.bundle.jscompany-currency-CurrencyRateViewController.bundle.jscompany-currency-CurrencyViewController.bundle.jscompany-custom_field-CustomFieldViewController.bundle.jscompany-department-DepartmentViewController.bundle.jscompany-ethnic_group-EthnicGroupViewController.bundle.jscompany-geo_fence-GEOFenceViewController.bundle.jscompany-geo_fence-GEOFenceViewController.csscompany-hierarchy_control-HierarchyControlViewController.bundle.jscompany-legal_entity-LegalEntityViewController.bundle.jscompany-other_field-OtherFieldViewController.bundle.jscompany-payroll_remittance_agency-PayrollRemittanceAgencyEventViewController.bundle.jscompany-payroll_remittance_agency-PayrollRemittanceAgencyViewController.bundle.jscompany-permission_control-PermissionControlViewController.bundle.jscompany-remittance_source_account-RemittanceSourceAccountViewController.bundle.jscompany-station-StationViewController.bundle.jscompany-wage-WageViewController.bundle.jscompany-wage_group-WageGroupViewController.bundle.jscore-log-LogViewController.bundle.jsdatepicker-TDatePicker.bundle.jsdatepicker-TRangePicker.bundle.jsdeveloper_tools-AwesomeboxTestViewController.bundle.jsdeveloper_tools-GridTestViewController.bundle.jsdeveloper_tools-WidgetTestViewController.bundle.jsdeveloper_tools-debugPanelController.bundle.jsdocument-DocumentGroupViewController.bundle.jsdocument-DocumentRevisionViewController.bundle.jsdocument-DocumentViewController.bundle.jsdynamic-editview-primevue-button.bundle.jsdynamic-editview-primevue-calendar.bundle.jsdynamic-editview-primevue-dropdown.bundle.jsdynamic-editview-primevue-radiobutton.bundle.jsdynamic-testview.bundle.jsdynamic-testview.cssemployees-employee-EmployeeViewController.bundle.jsemployees-remittance_destination_account-RemittanceDestinationAccountViewController.bundle.jsemployees-roe-ROEViewController.bundle.jsemployees-user_contact-UserContactViewController.bundle.jsemployees-user_default-UserDefaultViewController.bundle.jsemployees-user_group-UserGroupViewController.bundle.jsemployees-user_preference-UserPreferenceViewController.bundle.jsemployees-user_title-UserTitleViewController.bundle.jserror_tip-ErrorTipBox.bundle.jsfeedback-TFeedback.bundle.jsfilebrowser-CameraBrowser.bundle.jsfilebrowser-TImage.bundle.jsfilebrowser-TImageAdvBrowser.bundle.jsfilebrowser-TImageBrowser.bundle.jsfilebrowser-TImageCutArea.bundle.jsfirebase-app.jsfirebase-messaging.jsfirebase-service-worker.bundle.jsformula_builder-FormulaBuilder.bundle.jshelp-AboutViewController.bundle.jshome-dashboard-HomeViewController.bundle.jshome-dashlet-DashletController.bundle.jshr-kpi-KPIGroupViewController.bundle.jshr-kpi-KPIViewController.bundle.jshr-kpi-UserReviewControlViewController.bundle.jshr-qualification-QualificationGroupViewController.bundle.jshr-qualification-QualificationViewController.bundle.jshr-qualification-UserEducationViewController.bundle.jshr-qualification-UserLanguageViewController.bundle.jshr-qualification-UserLicenseViewController.bundle.jshr-qualification-UserMembershipViewController.bundle.jshr-qualification-UserSkillViewController.bundle.jshr-recruitment-JobApplicantEducationViewController.bundle.jshr-recruitment-JobApplicantEmploymentViewController.bundle.jshr-recruitment-JobApplicantLanguageViewController.bundle.jshr-recruitment-JobApplicantLicenseViewController.bundle.jshr-recruitment-JobApplicantLocationViewController.bundle.jshr-recruitment-JobApplicantMembershipViewController.bundle.jshr-recruitment-JobApplicantReferenceViewController.bundle.jshr-recruitment-JobApplicantSkillViewController.bundle.jshr-recruitment-JobApplicantViewController.bundle.jshr-recruitment-JobApplicationViewController.bundle.jshr-recruitment-JobApplicationViewController.csshr-recruitment-JobVacancyViewController.bundle.jshr-recruitment-RecruitmentPortalConfigViewController.bundle.jsinside_editor-InsideEditor.bundle.jsinterface_html5_components_context_menu_TTContextButton_vue.bundle.jsinterface_html5_framework_leaflet_leaflet-timetrex_js.bundle.jsinvoice-area_policy-AreaPolicyViewController.bundle.jsinvoice-client-ClientViewController.bundle.jsinvoice-client_contact-ClientContactViewController.bundle.jsinvoice-client_group-ClientGroupViewController.bundle.jsinvoice-client_payment-ClientPaymentViewController.bundle.jsinvoice-district-InvoiceDistrictViewController.bundle.jsinvoice-invoice-InvoiceViewController.bundle.jsinvoice-invoice_transaction-InvoiceTransactionViewController.bundle.jsinvoice-payment_gateway-PaymentGatewayViewController.bundle.jsinvoice-product_group-ProductGroupViewController.bundle.jsinvoice-products-ProductViewController.bundle.jsinvoice-settings-InvoiceConfigViewController.bundle.jsinvoice-shipping_policy-ShippingPolicyViewController.bundle.jsinvoice-tax_policy-TaxPolicyViewController.bundle.jsjqgrid-TGridHeader.bundle.jsleaflet-timetrex.csslist-TList.bundle.jslive-chat.bundle.jslogin-LoginViewController.bundle.jslogin-LoginViewController.cssmain_ui-styles.bundle.jsmain_ui-styles.cssmain_ui-vendor-styles.bundle.jsmain_ui-vendor-styles.cssmain_ui.bundle.jsmain_ui.cssmessage_box-NoHierarchyBox.bundle.jsmessage_box-NoResultBox.bundle.jsmessage_box-SaveAndContinueBox.bundle.jsmy_account-expense-ExpenseAuthorizationViewController.bundle.jsmy_account-expense-LoginUserExpenseViewController.bundle.jsmy_account-message_control-MessageControlViewController.bundle.jsmy_account-notification-NotificationViewController.bundle.jsmy_account-password-ChangePasswordViewController.bundle.jsmy_account-request-RequestViewController.bundle.jsmy_account-request_authorization-RequestAuthorizationViewController.bundle.jsmy_account-timesheet_authorization-TimeSheetAuthorizationViewController.bundle.jsmy_account-user_contact-LoginUserContactViewController.bundle.jsmy_account-user_preference-LoginUserPreferenceViewController.bundle.jspaging-Paging2.bundle.jspayperiod-PayPeriodScheduleViewController.bundle.jspayroll-company_tax_deduction-CompanyTaxDeductionViewController.bundle.jspayroll-government_document-GovernmentDocumentViewController.bundle.jspayroll-pay_periods-PayPeriodsViewController.bundle.jspayroll-pay_stub-PayStubViewController.bundle.jspayroll-pay_stub_amendment-PayStubAmendmentViewController.bundle.jspayroll-pay_stub_entry_account-PayStubEntryAccountViewController.bundle.jspayroll-pay_stub_transaction-PayStubTransactionViewController.bundle.jspayroll-process_transactions_wizard-ProcessTransactionsWizard.bundle.jspayroll-process_transactions_wizard-ProcessTransactionsWizardController.bundle.jspayroll-process_transactions_wizard-ProcessTransactionsWizardStepHome.bundle.jspayroll-recurring_pay_stub_amendment-RecurringPayStubAmendmentViewController.bundle.jspayroll-remittance_wizard-PayrollRemittanceAgencyEventWizard.bundle.jspayroll-remittance_wizard-PayrollRemittanceAgencyEventWizardController.bundle.jspayroll-remittance_wizard-PayrollRemittanceAgencyEventWizardStepHome.bundle.jspayroll-remittance_wizard-PayrollRemittanceAgencyEventWizardStepPublish.bundle.jspayroll-remittance_wizard-PayrollRemittanceAgencyEventWizardStepReview.bundle.jspayroll-remittance_wizard-PayrollRemittanceAgencyEventWizardStepSubmit.bundle.jspayroll-user_expense-UserExpenseViewController.bundle.jspdf.worker.js
pdfjs-cmaps
78-EUC-H.bcmap78-EUC-V.bcmap78-H.bcmap78-RKSJ-H.bcmap78-RKSJ-V.bcmap78-V.bcmap78ms-RKSJ-H.bcmap78ms-RKSJ-V.bcmap83pv-RKSJ-H.bcmap90ms-RKSJ-H.bcmap90ms-RKSJ-V.bcmap90msp-RKSJ-H.bcmap90msp-RKSJ-V.bcmap90pv-RKSJ-H.bcmap90pv-RKSJ-V.bcmapAdd-H.bcmapAdd-RKSJ-H.bcmapAdd-RKSJ-V.bcmapAdd-V.bcmapAdobe-CNS1-0.bcmapAdobe-CNS1-1.bcmapAdobe-CNS1-2.bcmapAdobe-CNS1-3.bcmapAdobe-CNS1-4.bcmapAdobe-CNS1-5.bcmapAdobe-CNS1-6.bcmapAdobe-CNS1-UCS2.bcmapAdobe-GB1-0.bcmapAdobe-GB1-1.bcmapAdobe-GB1-2.bcmapAdobe-GB1-3.bcmapAdobe-GB1-4.bcmapAdobe-GB1-5.bcmapAdobe-GB1-UCS2.bcmapAdobe-Japan1-0.bcmapAdobe-Japan1-1.bcmapAdobe-Japan1-2.bcmapAdobe-Japan1-3.bcmapAdobe-Japan1-4.bcmapAdobe-Japan1-5.bcmapAdobe-Japan1-6.bcmapAdobe-Japan1-UCS2.bcmapAdobe-Korea1-0.bcmapAdobe-Korea1-1.bcmapAdobe-Korea1-2.bcmapAdobe-Korea1-UCS2.bcmapB5-H.bcmapB5-V.bcmapB5pc-H.bcmapB5pc-V.bcmapCNS-EUC-H.bcmapCNS-EUC-V.bcmapCNS1-H.bcmapCNS1-V.bcmapCNS2-H.bcmapCNS2-V.bcmapETHK-B5-H.bcmapETHK-B5-V.bcmapETen-B5-H.bcmapETen-B5-V.bcmapETenms-B5-H.bcmapETenms-B5-V.bcmapEUC-H.bcmapEUC-V.bcmapExt-H.bcmapExt-RKSJ-H.bcmapExt-RKSJ-V.bcmapExt-V.bcmapGB-EUC-H.bcmapGB-EUC-V.bcmapGB-H.bcmapGB-V.bcmapGBK-EUC-H.bcmapGBK-EUC-V.bcmapGBK2K-H.bcmapGBK2K-V.bcmapGBKp-EUC-H.bcmapGBKp-EUC-V.bcmapGBT-EUC-H.bcmapGBT-EUC-V.bcmapGBT-H.bcmapGBT-V.bcmapGBTpc-EUC-H.bcmapGBTpc-EUC-V.bcmapGBpc-EUC-H.bcmapGBpc-EUC-V.bcmapH.bcmapHKdla-B5-H.bcmapHKdla-B5-V.bcmapHKdlb-B5-H.bcmapHKdlb-B5-V.bcmapHKgccs-B5-H.bcmapHKgccs-B5-V.bcmapHKm314-B5-H.bcmapHKm314-B5-V.bcmapHKm471-B5-H.bcmapHKm471-B5-V.bcmapHKscs-B5-H.bcmapHKscs-B5-V.bcmapHankaku.bcmapHiragana.bcmapKSC-EUC-H.bcmapKSC-EUC-V.bcmapKSC-H.bcmapKSC-Johab-H.bcmapKSC-Johab-V.bcmapKSC-V.bcmapKSCms-UHC-H.bcmapKSCms-UHC-HW-H.bcmapKSCms-UHC-HW-V.bcmapKSCms-UHC-V.bcmapKSCpc-EUC-H.bcmapKSCpc-EUC-V.bcmapKatakana.bcmapLICENSENWP-H.bcmapNWP-V.bcmapRKSJ-H.bcmapRKSJ-V.bcmapRoman.bcmapUniCNS-UCS2-H.bcmapUniCNS-UCS2-V.bcmapUniCNS-UTF16-H.bcmapUniCNS-UTF16-V.bcmapUniCNS-UTF32-H.bcmapUniCNS-UTF32-V.bcmapUniCNS-UTF8-H.bcmapUniCNS-UTF8-V.bcmapUniGB-UCS2-H.bcmapUniGB-UCS2-V.bcmapUniGB-UTF16-H.bcmapUniGB-UTF16-V.bcmapUniGB-UTF32-H.bcmapUniGB-UTF32-V.bcmapUniGB-UTF8-H.bcmapUniGB-UTF8-V.bcmapUniJIS-UCS2-H.bcmapUniJIS-UCS2-HW-H.bcmapUniJIS-UCS2-HW-V.bcmapUniJIS-UCS2-V.bcmapUniJIS-UTF16-H.bcmapUniJIS-UTF16-V.bcmapUniJIS-UTF32-H.bcmapUniJIS-UTF32-V.bcmapUniJIS-UTF8-H.bcmapUniJIS-UTF8-V.bcmapUniJIS2004-UTF16-H.bcmapUniJIS2004-UTF16-V.bcmapUniJIS2004-UTF32-H.bcmapUniJIS2004-UTF32-V.bcmapUniJIS2004-UTF8-H.bcmapUniJIS2004-UTF8-V.bcmapUniJISPro-UCS2-HW-V.bcmapUniJISPro-UCS2-V.bcmapUniJISPro-UTF8-V.bcmapUniJISX0213-UTF32-H.bcmapUniJISX0213-UTF32-V.bcmapUniJISX02132004-UTF32-H.bcmapUniJISX02132004-UTF32-V.bcmapUniKS-UCS2-H.bcmapUniKS-UCS2-V.bcmapUniKS-UTF16-H.bcmapUniKS-UTF16-V.bcmapUniKS-UTF32-H.bcmapUniKS-UTF32-V.bcmapUniKS-UTF8-H.bcmapUniKS-UTF8-V.bcmapV.bcmapWP-Symbol.bcmap
policy-absence_policy-AbsencePolicyViewController.bundle.jspolicy-accrual_policy-AccrualPolicyAccountViewController.bundle.jspolicy-accrual_policy-AccrualPolicyUserModifierViewController.bundle.jspolicy-accrual_policy-AccrualPolicyViewController.bundle.jspolicy-break_policy-BreakPolicyViewController.bundle.jspolicy-contributing_pay_code_policy-ContributingPayCodePolicyViewController.bundle.jspolicy-contributing_shift_policy-ContributingShiftPolicyViewController.bundle.jspolicy-exception_policy-ExceptionPolicyControlViewController.bundle.jspolicy-expense_policy-ExpensePolicyViewController.bundle.jspolicy-holiday-HolidayViewController.bundle.jspolicy-holiday_policy-HolidayPolicyViewController.bundle.jspolicy-meal_policy-MealPolicyViewController.bundle.jspolicy-overtime_policy-OvertimePolicyViewController.bundle.jspolicy-pay_code-PayCodeViewController.bundle.jspolicy-pay_formula_policy-PayFormulaPolicyViewController.bundle.jspolicy-policy_group-PolicyGroupViewController.bundle.jspolicy-premium_policy-PremiumPolicyViewController.bundle.jspolicy-recurring_holiday-RecurringHolidayViewController.bundle.jspolicy-regular_time_policy-RegularTimePolicyViewController.bundle.jspolicy-round_interval_policy-RoundIntervalPolicyViewController.bundle.jspolicy-schedule_policy-SchedulePolicyViewController.bundle.jsportal-PortalBaseViewController.bundle.jsportal-header-HeaderUploadResumeWidget.bundle.jsportal-hr-my_jobapplication-MyJobApplicationViewController.bundle.jsportal-hr-my_profile-JobApplicantEducationSubViewController.bundle.jsportal-hr-my_profile-JobApplicantLanguageSubViewController.bundle.jsportal-hr-my_profile-JobApplicantLicenseSubViewController.bundle.jsportal-hr-my_profile-JobApplicantMembershipSubViewController.bundle.jsportal-hr-my_profile-JobApplicantSubBaseViewController.bundle.jsportal-hr-my_profile-MyProfileViewController.bundle.jsportal-hr-recruitment-PortalJobVacancyDetailController.bundle.jsportal-hr-recruitment-PortalJobVacancyDetailViewController.bundle.jsportal-hr-recruitment-PortalJobVacancyRowController.bundle.jsportal-hr-recruitment-PortalJobVacancyViewController.bundle.jsportal-sign_in-PortalForgotPasswordController.bundle.jsportal-sign_in-PortalResetForgotPasswordController.bundle.jsportal-styles.bundle.jsportal-styles.cssportal.bundle.jsportal.csspost-login-app-dependancies.bundle.jspost-login-main_ui-vendor-dependancies.bundle.jsquick_punch-QuickPunchBaseViewController.bundle.jsquick_punch-header-HeaderViewController.bundle.jsquick_punch-login-QuickPunchLoginViewController.bundle.jsquick_punch-punch-QuickPunchViewController.bundle.jsquick_punch-styles.bundle.jsquick_punch-styles.cssquick_punch.bundle.jsquick_punch.cssreports-ReportBaseViewController.bundle.jsreports-accrual_balance_summary-AccrualBalanceSummaryReportViewController.bundle.jsreports-affordable_care-AffordableCareReportViewController.bundle.jsreports-audittrail-AuditTrailReportViewController.bundle.jsreports-custom_column-CustomColumnViewController.bundle.jsreports-employee_information-UserSummaryReportViewController.bundle.jsreports-exception_summary-ExceptionSummaryReportViewController.bundle.jsreports-expense_summary-ExpenseSummaryReportViewController.bundle.jsreports-form1099-Form1099NecReportViewController.bundle.jsreports-form940-Form940ReportViewController.bundle.jsreports-form941-Form941ReportViewController.bundle.jsreports-formw2-FormW2ReportViewController.bundle.jsreports-general_ledger_summary-GeneralLedgerSummaryReportViewController.bundle.jsreports-invoice_transaction_summary-InvoiceTransactionSummaryReportViewController.bundle.jsreports-job_analysis-JobAnalysisReportViewController.bundle.jsreports-job_info-JobInformationReportViewController.bundle.jsreports-job_item_info-JobItemInformationReportViewController.bundle.jsreports-job_summary-JobSummaryReportViewController.bundle.jsreports-pay_stub_summary-PayStubSummaryReportViewController.bundle.jsreports-pay_stub_transaction_summary-PayStubTransactionSummaryReportViewController.bundle.jsreports-payroll_export-PayrollExportReportViewController.bundle.jsreports-punch_summary-PunchSummaryReportViewController.bundle.jsreports-qualification_summary-UserQualificationReportViewController.bundle.jsreports-recruitment_detail-UserRecruitmentDetailReportViewController.bundle.jsreports-recruitment_summary-UserRecruitmentSummaryReportViewController.bundle.jsreports-remittance_summary-RemittanceSummaryReportViewController.bundle.jsreports-report_schedule-ReportScheduleViewController.bundle.jsreports-review_summary-KPIReportViewController.bundle.jsreports-saved_report-SavedReportViewController.bundle.jsreports-schedule_summary-ScheduleSummaryReportViewController.bundle.jsreports-t4_summary-T4SummaryReportViewController.bundle.jsreports-t4a_summary-T4ASummaryReportViewController.bundle.jsreports-tax_summary-TaxSummaryReportViewController.bundle.jsreports-timesheet_detail-TimesheetDetailReportViewController.bundle.jsreports-timesheet_summary-TimesheetSummaryReportViewController.bundle.jsreports-us_state_unemployment-USStateUnemploymentReportViewController.bundle.jsreports-whos_in_summary-ActiveShiftReportViewController.bundle.jsruntime.bundle.jssearch_panel-SearchPanel.bundle.jsseparated_box-SeparatedBox.bundle.jsswitch_button-SwitchButton.bundle.jstag_input-TTagInput.bundle.jstext-TText.bundle.jstext_input-TPasswordInput.bundle.jstext_input-TTextInput.bundle.jstextarea-TTextArea.bundle.jstimepicker-TTimePicker.bundle.jstoggle_button-TToggleButton.bundle.jsttgrid-TTGrid.bundle.jsui_kit_sample-UIKitChildSampleViewController.bundle.jsui_kit_sample-UIKitSampleViewController.bundle.js
vendor_ui
vendors-node_modules_bootstrap-select_dist_js_bootstrap-select_js.bundle.jsvendors-node_modules_css-loader_dist_cjs_js_node_modules_tinymce_skins_content_default_conten-a516be.bundle.jsvendors-node_modules_css-loader_dist_cjs_js_node_modules_tinymce_skins_content_default_conten-a516be.cssvendors-node_modules_decimal_js_decimal_mjs.bundle.jsvendors-node_modules_jquery-bridget_jquery-bridget_js-node_modules_masonry-layout_masonry_js.bundle.jsvendors-node_modules_jquery-ui_ui_widgets_autocomplete_js-node_modules_jquery-ui_ui_widgets_r-024c3b.bundle.jsvendors-node_modules_jquery-ui_ui_widgets_datepicker_js.bundle.jsvendors-node_modules_leaflet_dist_images_marker-icon-2x_png-node_modules_leaflet_dist_images_-78d511.bundle.jsvendors-node_modules_leaflet_dist_images_marker-icon-2x_png-node_modules_leaflet_dist_images_-78d511.cssvendors-node_modules_linkifyjs_string_js.bundle.jsvendors-node_modules_pdfjs-dist_web_pdf_viewer_js.bundle.jsvendors-node_modules_primevue_button_button_esm_js-node_modules_primevue_menu_menu_esm_js-nod-e86f5b.bundle.jswizard-BaseWizardController.bundle.jswizard-Wizard.bundle.jswizard-WizardStep.bundle.jswizard-dashlet-DashletWizardController.bundle.jswizard-find_available-FindAvailableViewController.bundle.jswizard-find_available-FindAvailableWizardController.bundle.jswizard-forgot_password-ForgotPasswordWizardController.bundle.jswizard-formula_builder_wizard-FormulaBuilderWizardController.bundle.jswizard-generate_pay_stub-GeneratePayStubWizardController.bundle.jswizard-import_csv-ImportCSVWizardController.bundle.jswizard-install-InstallWizardController.bundle.jswizard-job_invoice-JobInvoiceWizardController.bundle.jswizard-login_user-LoginUserViewController.bundle.jswizard-login_user-LoginUserWizardController.bundle.jswizard-pay_code-PayCodeWizardController.bundle.jswizard-pay_stub_account-PayStubAccountWizardController.bundle.jswizard-permission_wizard-PermissionWizardController.bundle.jswizard-process_payroll-ProcessPayrollWizardController.bundle.jswizard-quick_start-QuickStartWizardController.bundle.jswizard-re_calculate_accrual-ReCalculateAccrualWizardController.bundle.jswizard-re_calculate_timesheet-ReCalculateTimeSheetWizardController.bundle.jswizard-report_view-ReportViewWizardController.bundle.jswizard-reset_forgot_password-ResetForgotPasswordWizardController.bundle.jswizard-reset_password-ResetPasswordWizardController.bundle.jswizard-share_report-ShareReportWizardController.bundle.jswizard-user_generic_data_status-UserGenericStatusWindowController.bundle.jswizard-user_photo-UserPhotoWizardController.bundle.js
framework
apollo-vue
.browserslistrc.eslintrc.js.prettierrcCHANGELOG.mdREADME.mdbabel.config.jspackage.jsonpostcss.config.js
public
assets
demo
data
flags
images
layout
css
fonts
images
pages
sass
_fonts.scss
layout
overrides
theme
theme
favicon.icoindex.htmlupload.php
src
tests
vue.config.js
bootstrap-select
bootstrap-toolkit.min.js
bootstrap
decimal.min.js
google
analytics
html5shiv.min.jsinteract.min.jsjquery.bridget.jsjquery.i18n.jsjquery.imgareaselect.jsjquery.json.jsjquery.min.jsjquery.sortable.jsjquery.stickytableheaders.min.jsjquery.tablednd.js
jqueryui
json2.jsmasonry.min.jsmeasurement.jsmoment.jsnanobar.min.jspolyfill.js
qunit
r.jsrequire.jsrequire_async_plugin.jsrespond.min.js
rightclickmenu
tinymce
jquery.tinymce.min.js
langs
license.txt
plugins
skins
themes
tinymce.min.js
vue
widgets
global
index.phpmain.jsmain_ui-styles.jsmain_ui-vendor-styles.js
model
phpinfo.phppost-login-main_ui-dependancies.jspost-login-main_ui-vendor-dependancies.js
services
theme
default
css
application.css
global
widgets
awesomebox
column_editor
datepicker
error_tip
feedback
filebrowser
inside_editor
jqgrid
loading_bar
message_box
ribbon
RibbonView.cssgray.svg
icons
KPI-35x35.pngKPI_groups-35x35.pngabout-35x35.pngabsence_policies-35x35.pngaccrual-35x35.pngaccrual_accounts-35x35.pngaccrual_balance-35x35.pngaccrual_policies-35x35.pngadministration_guide_manual-35x35.pngalert-16x16.pngalert-35x35.pngalert_policies-35x35.pngapproved_expense-35x35.pngapproved_expense_new-35x35.pngapproved_overlay-35x35.pngarea_policies-35x35.pngaudit_trail-35x35.pngauthorization-35x35.pngauthorization2-35x35.pngauthorization3-35x35.pngauthorize-35x35.pngauthorize_request-35x35.pngauthorize_request_new-35x35.pngauthorize_timesheet-35x35.pngauthorize_timesheet_new-35x35.pngback-35x35.pngbank_accounts-35x35.pngbranches-35x35.pngbreak_policies-35x35.pngcalculate-35x35.pngcalculate_paystubs-35x35.pngcancel-35x35.pngclient_groups-35x35.pngclients-35x35.pngclients_contacts-35x35.pngclock_in_out-35x35.pngclose-35x35.pngclose_misc-35x35.pngclose_pay_period-35x35.pngclose_pay_period2-35x35.pngcompanies-35x35.pngcompany_information-35x35.pngcontact_information-35x35.pngcontributing_policies-35x35.pngcontributing_shift_policy-35x35.pngcopy-35x35.pngcopy_as_new-35x35.pngcurrencies-35x35.pngcustom_fields-35x35.pngdecline-35x35.pngdelete-35x35.pngdelete_and_next-35x35.pngdelete_and_previous-35x35.pngdepartments-35x35.pngdirect_deposit-35x35.pngdistrict-35x35.pngdocument_groups-35x35.pngdocuments-35x35.pngdone-35x35.pngdownload1-35x35.pngdownload2-35x35.pngedit-35x35.pngeducation-35x35.pngeligibility_policies-35x35.pngemailhelp-35x35.pngemployee_reports-35x35.pngemployees-35x35.pngethinicgroups-35x35.pngexceptions-35x35.pngexceptions_policies-35x35.pngexpense_policies-35x35.pngexpenses-35x35.pngexport-35x35.pngexport_to_efile-35x35.pngexport_to_excel-35x35.pngexport_to_xml-35x35.pngfaq-35x35.pngfillshift-35x35.pngformula_builder-16x16.pngformula_builder-35x35.pnggo-35x35.pnggovernment_payroll_documents-35x35.pnggroups-35x35.pnghappy.pnghappy_light.pnghelp-35x35.pnghierarchy-35x35.pngholiday_policies-35x35.pnghr_reports-35x35.pngimport-35x35.pnginbox-35x35.pnginvoice_reports-35x35.pnginvoice_wizard-35x35.pnginvoices-35x35.pngjob_applicant-35x35.pngjob_groups-35x35.pngjob_titles-35x35.pngjob_tracking_reports-35x35.pngjob_vacancies-35x35.pngjob_vacancy-35x35.pngjobapplications-35x35.pngjobs-35x35.pnglanguages-35x35.pnglanguages.pnglegal_entity-35x35.pnglicense-35x35.pnglicenses-35x35.pnglock-35x35.pnglogin-35x35.pnglogout-35x35.pngmap-35x35.pngmass_edit-35x35.pngmass_punches-35x35.pngmass_schedule-35x35.pngmaximize-35x35.pngmeal_policies-35x35.pngmemberships-35x35.pngmemberships.pngmessages-35x35.pngmessages_new-35x35.pngminimize-35x35.pngmove-35x35.pngneutral.pngneutral_light.pngnew_add-35x35.pngnew_hire_defaults-35x35.pngnew_overlay-35x35.pngnext-35x35.pngno_photo-16x16.pngno_photo-256x256.pngno_photo-35x35.pngonline_university-35x35.pngoverride-35x35.pngovertime_policies-35x35.pngpacking_slip-35x35.pngpass-35x35.pngpasswords-35x35.pngpay_code-35x35.pngpay_formula_policy-35x35.pngpay_period_schedules-35x35.pngpay_periods-35x35.pngpay_stub_account_linking-35x35.pngpay_stub_amendments-35x35.pngpay_stubs-35x35.pngpay_stubs_accounts-35x35.pngpayment_gateway_settings-35x35.pngpayment_methods-35x35.pngpayroll_remittance_agency-35x35.pngpayroll_reports-35x35.pngpermission_groups-35x35.pngpiece_work_policies-35x35.pngpolicy_groups-35x35.pngpreferences-35x35.pngpreferences_myaccount-35x35.pngpremium_policies-35x35.pngprint-35x35.pngprint_checks-35x35.pngprocess_payroll-35x35.pngproduct_groups-35x35.pngproducts-35x35.pngpunches-35x35.pngqualification_groups-35x35.pngqualification_groups.pngqualifications-35x35.pngqualifications.pngquicksetupwizard-35x35.pngquotes-35x35.pngrecord_of_employment-35x35.pngrecurring_holidays-35x35.pngrecurring_pay_stub_amendments-35x35.pngrecurring_schedule-35x35.pngrecurring_template-35x35.pngregular_time_policies-35x35.pngrequests-35x35.pngrestart-35x35.pngreviews-35x35.pngrounding_policies-35x35.pngsad.pngsad_light.pngsave-35x35.pngsave_and_back_exit-35x35.pngsave_and_continue-35x35.pngsave_and_copy-35x35.pngsave_and_new-35x35.pngsave_and_next-35x35.pngsave_and_previous-35x35.pngsave_setup-35x35.pngsaved_reports-35x35.pngschedule-35x35.pngschedule_policies-35x35.pngscheduled_shifts-35x35.pngsend-35x35.pngsent-35x35.pngsettings-35x35.pngshare-35x35.pngshipping_policies-35x35.pngshow_all_employees-18x18.pngshow_daily_totals-18x18.pngshow_weekly_totals-18x18.pngskill-35x35.pngskills-35x35.pngstations-35x35.pngstop-35x35.pngstrict_date_range-18x18.pngswap_shift-35x35.pngtags-35x35.pngtask_groups-35x35.pngtasks-35x35.pngtax_policies-35x35.pngtax_reports-35x35.pngtaxes_deductions-35x35.pngtimesheet-35x35.pngtimesheet_reports-35x35.pngtransactions-35x35.pngtrash.pngtrash_small.pngunder_time_policies-35x35.pngunlock-35x35.pngupload_file-16x16.pngupload_file-35x35.pngupload_image-16x16.pngupload_image-35x35.pngview-35x35.pngview_detail-35x35.pngwage_groups-35x35.pngwages-35x35.pngwarning-35x35.pngwhats_new-35x35.pngwizard2-35x35.pngwizard3-35x35.pngwizard4-35x35.pngwork_history_qualifiers-35x35.png
images
search_panel
switch_button
tag_input
talert
timepicker
toggle_button
top_menu
view_min_tab
gray.svg
icon_library
image_area_select
jquery-ui
quickPunch.css
right_click_menu
text_layer_builder.cssui.jqgrid.css
views
images
views
BaseViewController.jsBaseWindowController.jsTTBackboneView.js
attendance
common
company
core
developer_tools
employees
help
home
hr
login
my_account
payperiod
payroll
policy
reports
ui_kit_sample
wizard
BaseWizardController.js
dashlet
forgot_password
generate_pay_stub
import_csv
install
pay_code
pay_stub_account
permission_wizard
process_payroll
quick_start
re_calculate_accrual
re_calculate_timesheet
report_view
reset_forgot_password
reset_password
user_generic_data_status
user_photo
images
index.php
install
locale
ping.htmlping.phpsend_file.php
sounds
system_check.phpupload_file.php
maint
package-lock.jsonpackage.jsontimetrex.ini.php-example_linuxtimetrex.ini.php-example_windows
tools
unit_tests
.htaccessBootStrap.phpBootStrapSelenium.php
TTCodeStandard
beautifier.php
beautifier_filters
coding_standard_check.shcomposer.jsonconfig.xmlconfig_selenium.xmlrun.shrun_selenium.sh
testcases
i18n
kpi
other
payroll_deduction
CAPayrollDeductionCRATest2017.csvCAPayrollDeductionCRATest2018.csvCAPayrollDeductionCRATest2019.csvCAPayrollDeductionCRATest2020.csvCAPayrollDeductionCRATest2021.csvCAPayrollDeductionCRATest2022.csvCAPayrollDeductionTest2006.phpCAPayrollDeductionTest2007.phpCAPayrollDeductionTest2008.phpCAPayrollDeductionTest2009.csvCAPayrollDeductionTest2009.phpCAPayrollDeductionTest2010.csvCAPayrollDeductionTest2010.phpCAPayrollDeductionTest2011.csvCAPayrollDeductionTest2011.phpCAPayrollDeductionTest2012.csvCAPayrollDeductionTest2012.phpCAPayrollDeductionTest2013.csvCAPayrollDeductionTest2013.phpCAPayrollDeductionTest2014.csvCAPayrollDeductionTest2014.phpCAPayrollDeductionTest2015.csvCAPayrollDeductionTest2015.phpCAPayrollDeductionTest2016.csvCAPayrollDeductionTest2016.phpCAPayrollDeductionTest2017.csvCAPayrollDeductionTest2017.phpCAPayrollDeductionTest2018.csvCAPayrollDeductionTest2018.phpCAPayrollDeductionTest2019.csvCAPayrollDeductionTest2019.phpCAPayrollDeductionTest2020.csvCAPayrollDeductionTest2020.phpCAPayrollDeductionTest2021.csvCAPayrollDeductionTest2021.phpCAPayrollDeductionTest2022.csvCAPayrollDeductionTest2022.phpCRPayrollDeductionTest.phpUSPayrollDeductionTest2006.phpUSPayrollDeductionTest2007.phpUSPayrollDeductionTest2008.phpUSPayrollDeductionTest2009.csvUSPayrollDeductionTest2009.phpUSPayrollDeductionTest2010.csvUSPayrollDeductionTest2010.phpUSPayrollDeductionTest2011.csvUSPayrollDeductionTest2011.phpUSPayrollDeductionTest2012.csvUSPayrollDeductionTest2012.phpUSPayrollDeductionTest2013.csvUSPayrollDeductionTest2013.phpUSPayrollDeductionTest2014.csvUSPayrollDeductionTest2014.phpUSPayrollDeductionTest2015.csvUSPayrollDeductionTest2015.phpUSPayrollDeductionTest2016.csvUSPayrollDeductionTest2016.phpUSPayrollDeductionTest2017.csvUSPayrollDeductionTest2017.phpUSPayrollDeductionTest2018.csvUSPayrollDeductionTest2018.phpUSPayrollDeductionTest2019.csvUSPayrollDeductionTest2019.phpUSPayrollDeductionTest2020.csvUSPayrollDeductionTest2020.phpUSPayrollDeductionTest2021.csvUSPayrollDeductionTest2021.phpUSPayrollDeductionTest2022.csvUSPayrollDeductionTest2022.php
paystub
policy
report
Form940ReportTest.phpForm941ReportTest.phpFormW2ReportTest.phpFormW2ReportTest_testEFileFederalA.txtFormW2ReportTest_testEFileFederalB.txtFormW2ReportTest_testEFileFederalC.txtFormW2ReportTest_testEFileFederalMultiEmployeeA.txtFormW2ReportTest_testEFileFederalMultiEmployeeB.txtFormW2ReportTest_testEFileStateAL.txtFormW2ReportTest_testEFileStateAR.txtFormW2ReportTest_testEFileStateAZ.txtFormW2ReportTest_testEFileStateCO.txtFormW2ReportTest_testEFileStateCT.txtFormW2ReportTest_testEFileStateDC.txtFormW2ReportTest_testEFileStateDE.txtFormW2ReportTest_testEFileStateGA.txtFormW2ReportTest_testEFileStateIA.txtFormW2ReportTest_testEFileStateID.txtFormW2ReportTest_testEFileStateIL.txtFormW2ReportTest_testEFileStateIN.txtFormW2ReportTest_testEFileStateKS.txtFormW2ReportTest_testEFileStateKY.txtFormW2ReportTest_testEFileStateKYLocal1.txtFormW2ReportTest_testEFileStateMA.txtFormW2ReportTest_testEFileStateME.txtFormW2ReportTest_testEFileStateMI.txtFormW2ReportTest_testEFileStateMN.txtFormW2ReportTest_testEFileStateMO.txtFormW2ReportTest_testEFileStateMS.txtFormW2ReportTest_testEFileStateMT.txtFormW2ReportTest_testEFileStateMultiEmployeeIA.txtFormW2ReportTest_testEFileStateMultiEmployeeID.txtFormW2ReportTest_testEFileStateNC.txtFormW2ReportTest_testEFileStateND.txtFormW2ReportTest_testEFileStateNE.txtFormW2ReportTest_testEFileStateNY.txtFormW2ReportTest_testEFileStateOH.txtFormW2ReportTest_testEFileStateOK.txtFormW2ReportTest_testEFileStateOR.txtFormW2ReportTest_testEFileStatePA.txtFormW2ReportTest_testEFileStateSC.txtFormW2ReportTest_testEFileStateUT.txtFormW2ReportTest_testEFileStateVA.txtFormW2ReportTest_testEFileStateVT.txtFormW2ReportTest_testEFileStateWI.txtFormW2ReportTest_testFederalEFileWithFederalAndStateTaxesA.txtFormW2ReportTest_testNYEFileWithFederalAndStateTaxesA.txtTaxSummaryReportTest.phpUSStateUnemploymentReportTest.phpUSStateUnemploymentReportTest_testEFileAL.txtUSStateUnemploymentReportTest_testEFileAZ.txtUSStateUnemploymentReportTest_testEFileCA.txtUSStateUnemploymentReportTest_testEFileCO.txtUSStateUnemploymentReportTest_testEFileCT.txtUSStateUnemploymentReportTest_testEFileFL.txtUSStateUnemploymentReportTest_testEFileFederalA.txtUSStateUnemploymentReportTest_testEFileFederalMultiEmployeeA.txtUSStateUnemploymentReportTest_testEFileGA.txtUSStateUnemploymentReportTest_testEFileIA.txtUSStateUnemploymentReportTest_testEFileIL.txtUSStateUnemploymentReportTest_testEFileIN.txtUSStateUnemploymentReportTest_testEFileKS.txtUSStateUnemploymentReportTest_testEFileKY.txtUSStateUnemploymentReportTest_testEFileMI.txtUSStateUnemploymentReportTest_testEFileMS.txtUSStateUnemploymentReportTest_testEFileMT.txtUSStateUnemploymentReportTest_testEFileNC.txtUSStateUnemploymentReportTest_testEFileNY.txtUSStateUnemploymentReportTest_testEFileOK.txtUSStateUnemploymentReportTest_testEFileTN.txtUSStateUnemploymentReportTest_testEFileTX.txtUSStateUnemploymentReportTest_testEFileVA.txtUSStateUnemploymentReportTest_testEFileWA.txtUSStateUnemploymentReportTest_testEFileWI.txt
selenium
upgrade
vendor
.htaccessautoload.php
bin
brianium
cbschuld
composer
doctrine
ezyang
htmlpurifier
CHANGELOG.mdCREDITSLICENSEREADME.mdVERSIONcomposer.json
library
HTMLPurifier.auto.phpHTMLPurifier.autoload-legacy.phpHTMLPurifier.autoload.phpHTMLPurifier.composer.phpHTMLPurifier.func.phpHTMLPurifier.includes.phpHTMLPurifier.kses.phpHTMLPurifier.path.phpHTMLPurifier.phpHTMLPurifier.safe-includes.php
HTMLPurifier
Arborize.phpAttrCollections.phpAttrDef.php
AttrDef
AttrTransform.php
AttrTransform
AttrTypes.phpAttrValidator.phpBootstrap.phpCSSDefinition.phpChildDef.php
ChildDef
Config.phpConfigSchema.php
ConfigSchema
Builder
Exception.phpInterchange.php
Interchange
InterchangeBuilder.phpValidator.phpValidatorAtom.phpschema.ser
schema
Attr.AllowedClasses.txtAttr.AllowedFrameTargets.txtAttr.AllowedRel.txtAttr.AllowedRev.txtAttr.ClassUseCDATA.txtAttr.DefaultImageAlt.txtAttr.DefaultInvalidImage.txtAttr.DefaultInvalidImageAlt.txtAttr.DefaultTextDir.txtAttr.EnableID.txtAttr.ForbiddenClasses.txtAttr.ID.HTML5.txtAttr.IDBlacklist.txtAttr.IDBlacklistRegexp.txtAttr.IDPrefix.txtAttr.IDPrefixLocal.txtAutoFormat.AutoParagraph.txtAutoFormat.Custom.txtAutoFormat.DisplayLinkURI.txtAutoFormat.Linkify.txtAutoFormat.PurifierLinkify.DocURL.txtAutoFormat.PurifierLinkify.txtAutoFormat.RemoveEmpty.Predicate.txtAutoFormat.RemoveEmpty.RemoveNbsp.Exceptions.txtAutoFormat.RemoveEmpty.RemoveNbsp.txtAutoFormat.RemoveEmpty.txtAutoFormat.RemoveSpansWithoutAttributes.txtCSS.AllowDuplicates.txtCSS.AllowImportant.txtCSS.AllowTricky.txtCSS.AllowedFonts.txtCSS.AllowedProperties.txtCSS.DefinitionRev.txtCSS.ForbiddenProperties.txtCSS.MaxImgLength.txtCSS.Proprietary.txtCSS.Trusted.txtCache.DefinitionImpl.txtCache.SerializerPath.txtCache.SerializerPermissions.txtCore.AggressivelyFixLt.txtCore.AggressivelyRemoveScript.txtCore.AllowHostnameUnderscore.txtCore.AllowParseManyTags.txtCore.CollectErrors.txtCore.ColorKeywords.txtCore.ConvertDocumentToFragment.txtCore.DirectLexLineNumberSyncInterval.txtCore.DisableExcludes.txtCore.EnableIDNA.txtCore.Encoding.txtCore.EscapeInvalidChildren.txtCore.EscapeInvalidTags.txtCore.EscapeNonASCIICharacters.txtCore.HiddenElements.txtCore.Language.txtCore.LegacyEntityDecoder.txtCore.LexerImpl.txtCore.MaintainLineNumbers.txtCore.NormalizeNewlines.txtCore.RemoveInvalidImg.txtCore.RemoveProcessingInstructions.txtCore.RemoveScriptContents.txtFilter.Custom.txtFilter.ExtractStyleBlocks.Escaping.txtFilter.ExtractStyleBlocks.Scope.txtFilter.ExtractStyleBlocks.TidyImpl.txtFilter.ExtractStyleBlocks.txtFilter.YouTube.txtHTML.Allowed.txtHTML.AllowedAttributes.txtHTML.AllowedComments.txtHTML.AllowedCommentsRegexp.txtHTML.AllowedElements.txtHTML.AllowedModules.txtHTML.Attr.Name.UseCDATA.txtHTML.BlockWrapper.txtHTML.CoreModules.txtHTML.CustomDoctype.txtHTML.DefinitionID.txtHTML.DefinitionRev.txtHTML.Doctype.txtHTML.FlashAllowFullScreen.txtHTML.ForbiddenAttributes.txtHTML.ForbiddenElements.txtHTML.Forms.txtHTML.MaxImgLength.txtHTML.Nofollow.txtHTML.Parent.txtHTML.Proprietary.txtHTML.SafeEmbed.txtHTML.SafeIframe.txtHTML.SafeObject.txtHTML.SafeScripting.txtHTML.Strict.txtHTML.TargetBlank.txtHTML.TargetNoopener.txtHTML.TargetNoreferrer.txtHTML.TidyAdd.txtHTML.TidyLevel.txtHTML.TidyRemove.txtHTML.Trusted.txtHTML.XHTML.txtOutput.CommentScriptContents.txtOutput.FixInnerHTML.txtOutput.FlashCompat.txtOutput.Newline.txtOutput.SortAttr.txtOutput.TidyFormat.txtTest.ForceNoIconv.txtURI.AllowedSchemes.txtURI.Base.txtURI.DefaultScheme.txtURI.DefinitionID.txtURI.DefinitionRev.txtURI.Disable.txtURI.DisableExternal.txtURI.DisableExternalResources.txtURI.DisableResources.txtURI.Host.txtURI.HostBlacklist.txtURI.MakeAbsolute.txtURI.Munge.txtURI.MungeResources.txtURI.MungeSecretKey.txtURI.OverrideAllowedSchemes.txtURI.SafeIframeRegexp.txtinfo.ini
ContentSets.phpContext.phpDefinition.phpDefinitionCache.php
DefinitionCache
DefinitionCacheFactory.phpDoctype.phpDoctypeRegistry.phpElementDef.phpEncoder.phpEntityLookup.php
EntityLookup
EntityParser.phpErrorCollector.phpErrorStruct.phpException.phpFilter.php
Filter
Generator.phpHTMLDefinition.phpHTMLModule.php
HTMLModule
HTMLModuleManager.phpIDAccumulator.phpInjector.php
Injector
Language.php
Language
messages
LanguageFactory.phpLength.phpLexer.php
Lexer
Node.php
Node
PercentEncoder.phpPrinter.php
Printer
PropertyList.phpPropertyListIterator.phpQueue.phpStrategy.php
Strategy
StringHash.phpStringHashParser.phpTagTransform.php
TagTransform
Token.php
Token
TokenFactory.phpURI.phpURIDefinition.phpURIFilter.php
URIFilter
URIParser.phpURIScheme.php
URIScheme
URISchemeRegistry.phpUnitConverter.phpVarParser.php
VarParser
VarParserException.phpZipper.php
geoip2
jean85
kigkonsult
icalcreator
.github
LICENCEREADME.mdautoload.phpcomposer.json
docs
phpunit.xmlreleaseNotes
src
Available.phpCalendarComponent.phpDScomponent.phpDaylight.php
Formatter
IcalBase.phpIcalInterface.php
Parser
Participant.phpPc.phpStandard.php
Traits
Util
V2component.phpV3component.phpVAcomponent.phpValarm.phpVavailability.phpVcalendar.phpVcomponent.phpVevent.phpVfreebusy.phpVjournal.phpVlocation.phpVresource.phpVtimezone.phpVtodo.php
Xml
test
maennchen
markbaker
maxmind-db
maxmind
myclabs
nikic
php-parser
LICENSEREADME.md
bin
composer.json
grammar
lib
PhpParser
Builder.php
Builder
BuilderFactory.phpBuilderHelpers.phpComment.php
Comment
ConstExprEvaluationException.phpConstExprEvaluator.phpError.phpErrorHandler.php
ErrorHandler
Internal
JsonDecoder.phpLexer.php
Lexer
NameContext.phpNode.php
Node
Arg.phpAttribute.phpAttributeGroup.phpComplexType.phpConst_.phpExpr.php
Expr
FunctionLike.phpIdentifier.phpIntersectionType.phpMatchArm.phpName.php
Name
NullableType.phpParam.phpScalar.php
Scalar
Stmt.php
Stmt
UnionType.phpVarLikeIdentifier.phpVariadicPlaceholder.php
NodeAbstract.phpNodeDumper.phpNodeFinder.phpNodeTraverser.phpNodeTraverserInterface.phpNodeVisitor.php
NodeVisitor
NodeVisitorAbstract.phpParser.php
Parser
ParserAbstract.phpParserFactory.php
PrettyPrinter
PrettyPrinterAbstract.php
pear
archive_tar
cache_lite
console_getopt
mail
mail_mime
mime_type
pear
.travis.ymlCODING_STANDARDSINSTALLLICENSEMakefile.frag
OS
PEAR.php
PEAR
README.CONTRIBUTINGREADME.rstSystem.phpbuild-release.shcatalogcomposer.jsongo-pear-list.phpgo-pear-phar.phpinstall-pear.phpinstall-pear.txtmake-command-xml.phpmake-gopear-phar.phpmake-installpear-nozlib-phar.phpmake-pear-bundle.phppackage-ErrorStack.xmlpackage-manpages.xmlpackage.dtdpackage2.xml
scripts
template.spectest-modified.php
structures_graph
xml_util
phar-io
manifest
version
phpoffice
phpspreadsheet
.php-cs-fixer.dist.php.phpcs.xml.distCHANGELOG.mdCONTRIBUTING.mdLICENSEREADME.mdcomposer.jsonphpstan-baseline.neonphpstan-conditional.phpphpstan.neon.dist
src
PhpSpreadsheet
Calculation
ArrayEnabled.phpBinaryComparison.phpCalculation.phpCategory.phpDatabase.php
Database
DateTime.php
DateTimeExcel
Engine
Engineering.php
Engineering
Exception.phpExceptionHandler.phpFinancial.php
Financial
FormulaParser.phpFormulaToken.phpFunctions.php
Information
Internal
Logical.php
Logical
LookupRef.php
LookupRef
MathTrig.php
MathTrig
Statistical.php
Statistical
TextData.php
TextData
Token
Web.php
Web
locale
Cell
CellReferenceHelper.php
Chart
Collection
Comment.phpDefinedName.php
Document
Exception.phpHashTable.php
Helper
IComparable.phpIOFactory.phpNamedFormula.phpNamedRange.php
Reader
ReferenceHelper.php
RichText
Settings.php
Shared
Spreadsheet.php
Style
Worksheet
Writer
phpunit
php-code-coverage
ChangeLog.mdLICENSEREADME.mdcomposer.json
src
CodeCoverage.php
Driver
Exception
Filter.php
Node
ProcessedCodeCoverageData.phpRawCodeCoverageData.php
Report
StaticAnalysis
Util
Version.php
php-file-iterator
php-invoker
php-text-template
php-timer
phpunit-selenium
.ci
.travis.ymlChangeLog.markdownLICENSE
PHPUnit
README.md
Tests
Vagrantfilebuild.xml
build
composer.jsonphpunit-selenium-bootstrap.phpphpunit.xml.dist
selenium-1-tests
phpunit
.phpstorm.meta.phpChangeLog-8.5.mdChangeLog-9.5.mdLICENSEREADME.mdSECURITY.mdcomposer.jsonphpunitphpunit.xsd
schema
src
Exception.php
Framework
Assert.php
Assert
Constraint
DataProviderTestSuite.php
Error
ErrorTestCase.php
Exception
ExceptionWrapper.phpExecutionOrderDependency.phpIncompleteTest.phpIncompleteTestCase.phpInvalidParameterGroupException.php
MockObject
Api
Builder
ConfigurableMethod.php
Exception
Generator.php
Generator
Invocation.phpInvocationHandler.phpMatcher.phpMethodNameConstraint.phpMockBuilder.phpMockClass.phpMockMethod.phpMockMethodSet.phpMockObject.phpMockTrait.phpMockType.php
Rule
Stub.php
Stub
Verifiable.php
Reorderable.phpSelfDescribing.phpSkippedTest.phpSkippedTestCase.phpTest.phpTestBuilder.phpTestCase.phpTestFailure.phpTestListener.phpTestListenerDefaultImplementation.phpTestResult.phpTestSuite.phpTestSuiteIterator.phpWarningTestCase.php
Runner
TextUI
CliArguments
Command.phpDefaultResultPrinter.php
Exception
Help.phpResultPrinter.phpTestRunner.phpTestSuiteMapper.php
XmlConfiguration
CodeCoverage
Configuration.phpException.php
Filesystem
Generator.php
Group
Loader.php
Logging
Migration
PHP
PHPUnit
TestSuite
Util
psr
sebastian
cli-parser
code-unit-reverse-lookup
code-unit
comparator
complexity
diff
environment
exporter
global-state
lines-of-code
object-enumerator
object-reflector
recursion-context
resource-operations
type
version
setasign
fpdf
fpdi
symfony
console
Application.php
Attribute
CHANGELOG.md
CI
Color.php
Command
CommandLoader
Completion
ConsoleEvents.phpCursor.php
DependencyInjection
Descriptor
Event
EventListener
Exception
Formatter
Helper
Input
LICENSE
Logger
Output
Question
README.md
Resources
SignalRegistry
SingleCommandApplication.php
Style
Terminal.php
Tester
composer.json
deprecation-contracts
polyfill-ctype
polyfill-intl-grapheme
polyfill-intl-normalizer
polyfill-mbstring
polyfill-php73
polyfill-php80
process
service-contracts
string
tecnickcom
theseer
zytzagoo
webpack.config.js

@ -0,0 +1,675 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
/**
* Main package file
*
* Process.php is a unified OOP abstraction layer for credit card and echeck
* processing gateways (similar to what DB does for database calls).
*
* PHP versions 4 and 5
*
* LICENSE: This source file is subject to version 3.0 of the PHP license
* that is available through the world-wide-web at the following URI:
* http://www.php.net/license/3_0.txt. If you did not receive a copy of
* the PHP License and are unable to obtain it through the web, please
* send a note to license@php.net so we can mail you a copy immediately.
*
* @category Payment
* @package Payment_Process
* @author Ian Eure <ieure@php.net>
* @author Joe Stump <joe@joestump.net>
* @copyright 1997-2005 The PHP Group
* @license http://www.php.net/license/3_0.txt PHP License 3.0
* @version CVS: $Id: Process.php,v 1.49 2005/12/16 18:45:57 ieure Exp $
* @link http://pear.php.net/package/Payment_Process
*/
require_once('PEAR.php');
require_once('Validate.php');
require_once('Validate/Finance/CreditCard.php');
require_once('Payment/Process/Type.php');
/**
* Error codes
*/
define('PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED', -100);
define('PAYMENT_PROCESS_ERROR_NOFIELD', -101);
define('PAYMENT_PROCESS_ERROR_NOPROCESSOR', -102);
define('PAYMENT_PROCESS_ERROR_INCOMPLETE', -1);
define('PAYMENT_PROCESS_ERROR_INVALID', -2);
define('PAYMENT_PROCESS_ERROR_AVS', -3);
define('PAYMENT_PROCESS_ERROR_CVV', -4);
/**
* Transaction actions
*/
/**
* A normal transaction
*/
define('PAYMENT_PROCESS_ACTION_NORMAL', 200);
/**
* Authorize only. No funds are transferred.
*/
define('PAYMENT_PROCESS_ACTION_AUTHONLY', 201);
/**
* Credit funds back from a previously-charged transaction.
*/
define('PAYMENT_PROCESS_ACTION_CREDIT', 202);
/**
* Post-authorize an AUTHONLY transaction.
*/
define('PAYMENT_PROCESS_ACTION_POSTAUTH', 203);
/**
* Clear a previous transaction
*/
define('PAYMENT_PROCESS_ACTION_VOID', 204);
/**
* Transaction sources
*/
define('PAYMENT_PROCESS_SOURCE_POS', 300);
define('PAYMENT_PROCESS_SOURCE_ONLINE', 301);
/**
* Result codes
*/
define('PAYMENT_PROCESS_RESULT_APPROVED', 400);
define('PAYMENT_PROCESS_RESULT_DECLINED', 401);
define('PAYMENT_PROCESS_RESULT_OTHER', 402);
define('PAYMENT_PROCESS_RESULT_FRAUD', 403);
define('PAYMENT_PROCESS_RESULT_DUPLICATE',404);
define('PAYMENT_PROCESS_RESULT_REVIEW', 405);
define('PAYMENT_PROCESS_AVS_MATCH', 500);
define('PAYMENT_PROCESS_AVS_MISMATCH', 501);
define('PAYMENT_PROCESS_AVS_ERROR', 502);
define('PAYMENT_PROCESS_AVS_NOAPPLY', 503);
define('PAYMENT_PROCESS_CVV_MATCH', 600);
define('PAYMENT_PROCESS_CVV_MISMATCH', 601);
define('PAYMENT_PROCESS_CVV_ERROR', 602);
define('PAYMENT_PROCESS_CVV_NOAPPLY', 603);
/**
* Payment_Process
*
* @author Ian Eure <ieure@php.net>
* @package Payment_Process
* @category Payment
* @version @version@
*/
class Payment_Process {
/**
* Return an instance of a specific processor.
*
* @param string $type Name of the processor
* @param array $options Options for the processor
* @return mixed Instance of the processor object, or a PEAR_Error object.
*/
// static function,avoid PHP strict error
static function &factory($type, $options = false)
{
$class = "Payment_Process_".$type;
if (include_once "Payment/Process/{$type}.php") {
if (class_exists($class)) {
$object = new $class($options);
return $object;
}
}
$ret = PEAR::raiseError('"'.$type.'" processor does not exist',
PAYMENT_PROCESS_ERROR_NOPROCESSOR);
return $ret;
}
/**
* Determine if a field is required.
*
* @param string $field Field to check
* @return boolean true if required, false if optional.
*/
function isRequired($field)
{
return (isset($this->_required[$field]));
}
/**
* Determines if a field exists.
*
* @author Ian Eure <ieure@php.net>
* @param string $field Field to check
* @return boolean true if field exists, false otherwise
*/
function fieldExists($field)
{
return @in_array($field, $this->getFields());
}
/**
* Get a list of fields.
*
* This function returns an array containing all the possible fields which
* may be set.
*
* @author Ian Eure <ieure@php.net>
* @access public
* @return array Array of valid fields.
*/
function getFields()
{
$vars = array_keys(get_class_vars(get_class($this)));
foreach ($vars as $idx => $field) {
if ($field[0] == '_') {
unset($vars[$idx]);
}
}
return $vars;
}
/**
* Set class options.
*
* @author Ian Eure <ieure@php.net>
* @param Array $options Options to set
* @param Array $defaultOptions Default options
* @return void
*/
function setOptions($options = false, $defaultOptions = false)
{
$defaultOptions = $defaultOptions ? $defaultOptions : $this->_defaultOptions;
$this->_options = @array_merge($defaultOptions, $options);
}
/**
* Get an option value.
*
* @author Ian Eure <ieure@php.net>
* @param string $option Option to get
* @return mixed Option value
*/
function getOption($option)
{
return @$this->_options[$option];
}
/**
* Set an option value
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @param string $option Option name to set
* @param mixed $value Value to set
*/
function setOption($option,$value)
{
return ($this->_options[$option] = $value);
}
/**
* See if a value is a defined constant.
*
* This function checks to see if $value is defined in one of
* PAYMENT_PROCESS_{$class}_*. It's used to verify that e.g.
* $object->action is one of PAYMENT_PROCESS_ACTION_NORMAL,
* PAYMENT_PROCESS_ACTION_AUTHONLY etc.
*
* @access private
* @param mixed $value Value to check
* @param mixed $class Constant class to check
* @return boolean true if it is defined, false otherwise.
*/
function _isDefinedConst($value, $class)
{
$constClass = 'PAYMENT_PROCESS_'.strtoupper($class).'_';
$length = strlen($constClass);
$consts = get_defined_constants();
$found = false;
foreach ($consts as $constant => $constVal) {
if (strncmp($constClass, $constant, $length) === 0
&& $constVal == $value) {
$found = true;
break;
}
}
return $found;
}
/**
* Statically check a Payment_Result class for success
*
* @param mixed $obj
* @return bool
* @access public
* @static
* @author Joe Stump <joe@joestump.net>
*/
function isSuccess($obj)
{
if (is_a($obj, 'Payment_Process_Result')) {
if ($obj->getCode() == PAYMENT_PROCESS_RESULT_APPROVED) {
return true;
}
}
return false;
}
/**
* Statically check a Payment_Result class for error
*
* @param mixed $obj
* @return bool
* @access public
* @author Joe Stump <joe@joestump.net>
*/
function isError($obj)
{
if (PEAR::isError($obj)) {
return true;
}
if (is_a($obj, 'Payment_Process_Result')) {
if ($obj->getCode() != PAYMENT_PROCESS_RESULT_APPROVED) {
return true;
}
}
return false;
}
}
/**
* Payment_Process_Result
*
* The core result class that should be returned from each driver's process()
* function. This should be extended as Payment_Process_Result_DriverName and
* then have the appropriate fields mapped out accordingly.
*
* Take special care to appropriately create a parse() function in your result
* class. You can then call _mapFields() with a resultArray (ie. exploded
* result) to map your results from parse() into the member variables.
*
* Please note that this class keeps your original codes intact so they can
* be accessed directly and then uses the function wrappers to return uniform
* Payment_Process codes.
*
* @author Joe Stump <joe@joestump.net>
* @package Payment_Process
* @category Payment
* @version @version@
*/
class Payment_Process_Result {
/**
* Processor instance which this result was instantiated from.
*
* This should contain a reference to the requesting Processor.
*
* @author Ian Eure <ieure@php.net>
* @access private
* @var Object
*/
var $_request;
/**
* The raw response (ie. from cURL)
*
* @author Joe Stump <joe@joestump.net>
* @access protected
* @var string $_rawResponse
*/
var $_rawResponse = null;
/**
* The approval/decline code
*
* The value returned by your gateway as approved/declined should be mapped
* into this variable. Valid results should then be mapped into the
* appropriate PAYMENT_PROCESS_RESULT_* code using the $_statusCodeMap
* array. Values returned into $code should be mapped as keys in the map
* with PAYMENT_PROCESS_RESULT_* as the values.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var mixed $code
* @see PAYMENT_PROCESS_RESULT_APPROVED, PAYMENT_PROCESS_RESULT_DECLINED
* @see PAYMENT_PROCESS_RESULT_OTHER, $_statusCodeMap
*/
var $code;
/**
* Message/Response Code
*
* Along with the response (yes/no) you usually get a response/message
* code that translates into why it was approved/declined. This is where
* you map that code into. Your $_statusCodeMessages would then be keyed by
* valid messageCode values.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var mixed $messageCode
* @see $_statusCodeMessages
*/
var $messageCode;
/**
* Message from gateway
*
* Map the textual message from the gateway into this variable. It is not
* currently returned or used (in favor of the $_statusCodeMessages map, but
* can be accessed directly for debugging purposes.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $message
* @see $_statusCodeMessages
*/
var $message = 'No message from gateway';
/**
* Authorization/Approval code
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $approvalCode
*/
var $approvalCode;
/**
* Address verification code
*
* The AVS code returned from your gateway. This should then be mapped to
* the appropriate PAYMENT_PROCESS_AVS_* code using $_avsCodeMap. This value
* should also be mapped to the appropriate textual message via the
* $_avsCodeMessages array.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $avsCode
* @see PAYMENT_PROCESS_AVS_MISMATCH, PAYMENT_PROCESS_AVS_ERROR
* @see PAYMENT_PROCESS_AVS_MATCH, PAYMENT_PROCESS_AVS_NOAPPLY, $_avsCodeMap
* @see $_avsCodeMessages
*/
var $avsCode;
/**
* Transaction ID
*
* This is the unique transaction ID, which is used by gateways to modify
* transactions (credit, update, etc.). Map the appropriate value into this
* variable.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $transactionId
*/
var $transactionId;
/**
* Invoice Number
*
* Unique internal invoiceNumber (ie. your company's order/invoice number
* that you assign each order as it is processed). It is always a good idea
* to pass this to the gateway (which is usually then echo'd back).
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $invoiceNumber
*/
var $invoiceNumber;
/**
* Customer ID
*
* Unique internal customer ID (ie. your company's customer ID used to
* track individual customers).
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $customerId
*/
var $customerId;
/**
* CVV Code
*
* The CVV code is the 3-4 digit number on the back of most credit cards.
* This value should be mapped via the $_cvvCodeMap variable to the
* appropriate PAYMENT_PROCESS_CVV_* values.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $cvvCode
*/
var $cvvCode = PAYMENT_PROCESS_CVV_NOAPPLY;
/**
* CVV Message
*
* Your cvvCode value should be mapped to appropriate messages via the
* $_cvvCodeMessage array. This value is merely here to hold the value
* returned from the gateway (if any).
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @var string $cvvMessage
*/
var $cvvMessage = 'No CVV message from gateway';
function __construct($rawResponse, $request)
{
$this->_rawResponse = $rawResponse;
$this->_request = $request;
}
/**
* factory
*
* @author Joe Stump <joe@joestump.net>
* @author Ian Eure <ieure@php.net>
* @param string $type
* @param string $rawResponse
* @param mixed $request
* @return mixed Payment_Process_Result on succes, PEAR_Error on failure
*/
static function &factory($type, $rawResponse, $request)
{
$class = 'Payment_Process_Result_'.$type;
if (class_exists($class)) {
$ret = new $class($rawResponse, $request);
return $ret;
}
$ret = PEAR::raiseError('Invalid response type: '.$type.'('.$class.')');
return $ret;
}
/**
* validate
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @return mixed
*/
function validate()
{
if ($this->_request->getOption('avsCheck') === true) {
if ($this->getAVSCode() != PAYMENT_PROCESS_AVS_MATCH) {
return PEAR::raiseError('AVS check failed',
PAYMENT_PROCESS_ERROR_AVS);
}
}
$paymentType = $this->_request->_payment->_type;
if ($this->_request->getOption('cvvCheck') === true &&
$paymentType == 'CreditCard') {
if ($this->getCvvCode() != PAYMENT_PROCESS_CVV_MATCH) {
return PEAR::raiseError('CVV check failed',
PAYMENT_PROCESS_ERROR_CVV);
}
}
if ($this->getCode() != PAYMENT_PROCESS_RESULT_APPROVED) {
return PEAR::raiseError($this->getMessage(),
PAYMENT_PROCESS_RESULT_DECLINED);
}
return true;
}
/**
* parse
*
* @abstract
* @author Joe Stump <joe@joestump.net>
* @access public
*/
function parse()
{
return PEAR::raiseError('parse() not implemented',
PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED);
}
/**
* parseCallback
*
* @abstract
* @author Joe Stump <joe@joestump.net>
* @access public
* @see Payment_Process_Common::processCallback()
*/
function parseCallback()
{
return PEAR::raiseError('parse() not implemented',
PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED);
}
/**
* isLegitimate
*
* Some gateways allow you to validate the response to make sure it's
* actually them that are sending the response. Override this in the
* driver result class and implement this if your gateway provides such
* a mechanism. Any information required should be passed via $options.
*
* @abstract
* @author Joe Stump <joe@joestump.net>
* @access public
*/
function isLegitimate()
{
return PEAR::raiseError('parse() not implemented',
PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED);
}
/**
* getCode
*
* @author Joe Stump <joe@joestump.net>
* @access public
*/
function getCode()
{
if (isset($this->_statusCodeMap[$this->code])) {
return $this->_statusCodeMap[$this->code];
} else {
return PAYMENT_PROCESS_RESULT_DECLINED;
}
}
/**
* getMessage
*
* Return the message from the code map, or return the raw message if
* there is one. Otherwise, return a worthless message.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @return string
*/
function getMessage()
{
if (isset($this->_statusCodeMessages[$this->messageCode])) {
return $this->_statusCodeMessages[$this->messageCode];
} elseif(strlen($this->message)) {
return $this->message;
} else {
return 'No message reported';
}
}
function getAVSCode()
{
return $this->_avsCodeMap[$this->avsCode];
}
function getAVSMessage()
{
return $this->_avsCodeMessages[$this->avsCode];
}
function getCvvCode()
{
return $this->_cvvCodeMap[$this->cvvCode];
}
function getCvvMessage()
{
return $this->_cvvCodeMessages[$this->cvvCode];
}
/**
* _mapFields
*
* @author Joe Stump <joe@joestump.net>
* @access private
* @param mixed $responseArray
*/
function _mapFields($responseArray) {
foreach($this->_fieldMap as $key => $val) {
$this->$val = $responseArray[$key];
}
}
/**
* Accept an object
*
* @param object $object Object to accept
* @return boolean true if accepted, false otherwise
*/
function accept(&$object)
{
if (is_a($object, 'Log')) {
$this->_log = $object;
return true;
}
return false;
}
/**
* Log a message
*
* @param string $message Message to log
* @param string $priority Message priority
* @return mixed Return value of Log::log(), or false if no Log instance
* has been accepted.
*/
function log($message, $priority = null)
{
if (isset($this->_log) && is_object($this->_log)) {
return $this->_log->log($message, $priority);
}
return false;
}
}
?>

@ -0,0 +1,740 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
/**
* Authorize.Net processor
*
* PHP versions 4 and 5
*
* LICENSE: This source file is subject to version 3.0 of the PHP license
* that is available through the world-wide-web at the following URI:
* http://www.php.net/license/3_0.txt. If you did not receive a copy of
* the PHP License and are unable to obtain it through the web, please
* send a note to license@php.net so we can mail you a copy immediately.
*
* @category Payment
* @package Payment_Process
* @author Joe Stump <joe@joestump.net> |
* @author Philippe Jausions <Philippe.Jausions@11abacus.com>
* @copyright 1997-2005 The PHP Group
* @license http://www.php.net/license/3_0.txt PHP License 3.0
* @version CVS: $Id: AuthorizeNet.php,v 1.33 2005/11/01 18:55:29 jausions Exp $
* @link http://pear.php.net/package/Payment_Process
*/
require_once 'Payment/Process.php';
require_once 'Payment/Process/Common.php';
require_once 'Net/Curl.php';
/**
* Defines global variables
*/
$GLOBALS['_Payment_Process_AuthorizeNet'] = array(
PAYMENT_PROCESS_ACTION_NORMAL => 'AUTH_CAPTURE',
PAYMENT_PROCESS_ACTION_AUTHONLY => 'AUTH_ONLY',
PAYMENT_PROCESS_ACTION_POSTAUTH => 'PRIOR_AUTH_CAPTURE',
PAYMENT_PROCESS_ACTION_VOID => 'VOID'
);
/**
* Payment_Process_AuthorizeNet
*
* This is a processor for Authorize.net's merchant payment gateway.
* (http://www.authorize.net/)
*
* *** WARNING ***
* This is BETA code, and has not been fully tested. It is not recommended
* that you use it in a production environment without further testing.
*
* @package Payment_Process
* @author Joe Stump <joe@joestump.net>
* @author Philippe Jausions <Philippe.Jausions@11abacus.com>
* @version @version@
* @link http://www.authorize.net/
*/
class Payment_Process_AuthorizeNet extends Payment_Process_Common
{
/**
* Front-end -> back-end field map.
*
* This array contains the mapping from front-end fields (defined in
* the Payment_Process class) to the field names Authorize.Net requires.
*
* @see _prepare()
* @access private
*/
var $_fieldMap = array(
// Required
'login' => 'x_login',
'password' => 'x_password',
'action' => 'x_type',
// Optional
'login' => 'x_login',
'invoiceNumber' => 'x_invoice_num',
'customerId' => 'x_cust_id',
'amount' => 'x_amount',
'description' => 'x_description',
'name' => '',
'postalCode' => 'x_zip',
'zip' => 'x_zip',
'company' => 'x_company',
'address' => 'x_address',
'city' => 'x_city',
'state' => 'x_state',
'country' => 'x_country',
'phone' => 'x_phone',
'email' => 'x_email',
'ip' => 'x_customer_ip',
);
/**
* $_typeFieldMap
*
* @author Joe Stump <joe@joestump.net>
* @access protected
*/
var $_typeFieldMap = array(
'CreditCard' => array(
'firstName' => 'x_first_name',
'lastName' => 'x_last_name',
'cardNumber' => 'x_card_num',
'cvv' => 'x_card_code',
'expDate' => 'x_exp_date'
),
'eCheck' => array(
'routingCode' => 'x_bank_aba_code',
'accountNumber' => 'x_bank_acct_num',
'type' => 'x_bank_acct_type',
'bankName' => 'x_bank_name'
)
);
/**
* Default options for this processor.
*
* @see Payment_Process::setOptions()
* @access private
*/
var $_defaultOptions = array(
'authorizeUri' => 'https://secure.authorize.net/gateway/transact.dll',
'x_delim_data' => 'TRUE',
'x_delim_char' => ',',
'x_encap_char' => '|',
'x_relay' => 'FALSE',
'x_email_customer' => 'FALSE',
'x_currency_code' => 'USD',
'x_version' => '3.1'
);
/**
* List of possible encapsulation characters
*
* @var string
* @access private
*/
var $_encapChars = '|~#$^*_=+-`{}![]:";<>?/&';
/**
* Has the transaction been processed?
*
* @type boolean
* @access private
*/
var $_processed = false;
/**
* The response body sent back from the gateway.
*
* @access private
*/
var $_responseBody = '';
/**
* Constructor.
*
* @param array $options Class options to set.
* @see Payment_Process::setOptions()
* @return void
*/
function __construct($options = false)
{
parent::__construct($options);
$this->_driver = 'AuthorizeNet';
$this->_makeRequired('login', 'password', 'action');
}
/**
* Processes the transaction.
*
* Success here doesn't mean the transaction was approved. It means
* the transaction was sent and processed without technical difficulties.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
* @access public
*/
function &process()
{
// Sanity check
$result = $this->validate();
if (PEAR::isError($result)) {
return $result;
}
// Prepare the data
$result = $this->_prepare();
if (PEAR::isError($result)) {
return $result;
}
$fields = $this->_prepareQueryString();
if (PEAR::isError($fields)) {
return $fields;
}
// Don't die partway through
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
$curl = new Net_Curl($this->_options['authorizeUri']);
if (PEAR::isError($curl)) {
PEAR::popErrorHandling();
return $curl;
}
$curl->type = 'post';
$curl->fields = $fields;
$curl->userAgent = 'PEAR Payment_Process_AuthorizeNet 0.1';
$result = $curl->execute();
if (PEAR::isError($result)) {
PEAR::popErrorHandling();
return $result;
} else {
$curl->close();
}
$this->_responseBody = trim($result);
$this->_processed = true;
// Restore error handling
PEAR::popErrorHandling();
$response = &Payment_Process_Result::factory($this->_driver,
$this->_responseBody,
$this);
if (!PEAR::isError($response)) {
$response->parse();
$r = $response->isLegitimate();
if (PEAR::isError($r)) {
return $r;
} elseif ($r === false) {
return PEAR::raiseError('Illegitimate response from gateway');
}
}
$response->action = $this->action;
return $response;
}
/**
* Processes a callback from payment gateway
*
* Success here doesn't mean the transaction was approved. It means
* the callback was received and processed without technical difficulties.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
*/
function &processCallback()
{
$this->_responseBody = $_POST;
$this->_processed = true;
$response = &Payment_Process_Result::factory($this->_driver,
$this->_responseBody);
if (!PEAR::isError($response)) {
$response->_request = $this;
$response->parseCallback();
$r = $response->isLegitimate();
if (PEAR::isError($r)) {
return $r;
} elseif ($r === false) {
return PEAR::raiseError('Illegitimate callback from gateway.');
}
}
return $response;
}
/**
* Get (completed) transaction status.
*
* @return string Two-digit status returned from gateway.
*/
function getStatus()
{
return false;
}
/**
* Prepare the POST query string.
*
* You will need PHP_Compat::str_split() if you run this processor
* under PHP 4.
*
* @access private
* @return string The query string
*/
function _prepareQueryString()
{
$data = array_merge($this->_options, $this->_data);
// Set payment method to eCheck if our payment type is eCheck.
// Default is Credit Card.
$data['x_method'] = 'CC';
if ($this->_payment->getType() == 'eCheck') {
$data['x_method'] = 'ECHECK';
switch ($this->_payment->type) {
case PAYMENT_PROCESS_CK_CHECKING:
$data['x_bank_acct_type'] = 'CHECKING';
break;
case PAYMENT_PROCESS_CK_SAVINGS:
$data['x_bank_acct_type'] = 'SAVINGS';
break;
}
}
// Keep a trace of characters we will get back
// so we can set an appropriate encapsulation character
$chars = '';
$return = array();
foreach ($data as $key => $val) {
if (substr($key, 0, 2) == 'x_'
&& $key != 'x_encap_char'
&& strlen($val)) {
$return[] = $key . '=' . rawurlencode($val);
$chars .= $val;
}
}
// Find an appropriate encapsulation character
$encap = str_replace(array_unique(str_split($chars)), '', $data['x_encap_char'][0] . $this->_encapChars);
if (strlen($encap) == 0) {
$encap = $data['x_encap_char'][0];
} else {
$encap = $encap[0];
}
$this->_options['x_encap_char'] = $encap;
$return[] = 'x_encap_char=' . rawurlencode($encap);
return implode('&', $return);
}
/**
* _handleName
*
* If it's an eCheck we need to combine firstName and lastName into a
* single account name.
*
* @author Joe Stump <joe@joestump.net>
* @access private
*/
function _handleName()
{
if ($this->_payment->getType() == 'eCheck') {
$this->_data['x_bank_acct_name'] = $this->_payment->firstName.' '.$this->_payment->lastName;
}
}
}
class Payment_Process_Result_AuthorizeNet extends Payment_Process_Result {
var $_statusCodeMap = array('1' => PAYMENT_PROCESS_RESULT_APPROVED,
'2' => PAYMENT_PROCESS_RESULT_DECLINED,
'3' => PAYMENT_PROCESS_RESULT_OTHER,
'4' => PAYMENT_PROCESS_RESULT_REVIEW
);
/**
* AuthorizeNet status codes
*
* This array holds many of the common response codes. There are over 200
* response codes - so check the AuthorizeNet manual if you get a status
* code that does not match (see "Response Reason Codes & Response
* Reason Text" in the AIM manual).
*
* @see getStatusText()
* @access private
*/
var $_statusCodeMessages = array(
'1' => 'This transaction has been approved.',
'2' => 'This transaction has been declined.',
'3' => 'This transaction has been declined.',
'4' => 'This transaction has been declined.',
'5' => 'A valid amount is required.',
'6' => 'The credit card number is invalid.',
'7' => 'The credit card expiration date is invalid.',
'8' => 'The credit card has expired.',
'9' => 'The ABA code is invalid.',
'10' => 'The account number is invalid.',
'11' => 'A duplicate transaction has been submitted.',
'12' => 'An authorization code is required but not present.',
'13' => 'The merchant Login ID is invalid or the account is inactive.',
'14' => 'The Referrer or Relay Response URL is invalid.',
'15' => 'The transaction ID is invalid.',
'16' => 'The transaction was not found.',
'17' => 'The merchant does not accept this type of credit card.',
'18' => 'ACH transactions are not accepted by this merchant.',
'19' => 'An error occurred during processing. Please try again in 5 minutes.',
'20' => 'An error occurred during processing. Please try again in 5 minutes.',
'21' => 'An error occurred during processing. Please try again in 5 minutes.',
'22' => 'An error occurred during processing. Please try again in 5 minutes.',
'23' => 'An error occurred during processing. Please try again in 5 minutes.',
'24' => 'The Nova Bank Number or Terminal ID is incorrect. Call Merchant Service Provider.',
'25' => 'An error occurred during processing. Please try again in 5 minutes.',
'26' => 'An error occurred during processing. Please try again in 5 minutes.',
'27' => 'The transaction resulted in an AVS mismatch. The address provided does not match billing address of cardholder.',
'28' => 'The merchant does not accept this type of credit card.',
'29' => 'The PaymentTech identification numbers are incorrect. Call Merchant Service Provider.',
'30' => 'The configuration with the processor is invalid. Call Merchant Service Provider.',
'31' => 'The FDC Merchant ID or Terminal ID is incorrect. Call Merchant Service Provider.',
'32' => 'The merchant password is invalid or not present.',
'33' => 'Missing required field',
'34' => 'The VITAL identification numbers are incorrect. Call Merchant Service Provider.',
'35' => 'An error occurred during processing. Call Merchant Service Provider.',
'36' => 'The authorization was approved, but settlement failed.',
'37' => 'The credit card number is invalid.',
'38' => 'The Global Payment System identification numbers are incorrect. Call Merchant Service Provider.',
'39' => 'The supplied currency code is either invalid, not supported, not allowed for this merchant or doesn\'t have an exchange rate.',
'40' => 'This transaction must be encrypted.',
'41' => 'FraudScreen.net fraud score is higher than threshold set by merchant',
'42' => 'There is missing or invalid information in a required field.',
'43' => 'The merchant was incorrectly set up at the processor. Call your Merchant Service Provider.',
'44' => 'This transaction has been declined. Card Code filter error!',
'45' => 'This transaction has been declined. Card Code / AVS filter error!',
'46' => 'Your session has expired or does not exist. You must log in to continue working.',
'47' => 'The amount requested for settlement may not be greater than the original amount authorized.',
'48' => 'This processor does not accept partial reversals.',
'49' => 'A transaction amount greater than $99,999 will not be accepted.',
'50' => 'This transaction is awaiting settlement and cannot be refunded.',
'51' => 'The sum of all credits against this transaction is greater than the original transaction amount.',
'52' => 'The transaction was authorized, but the client could not be notified; the transaction will not be settled.',
'53' => 'The transaction type was invalid for ACH transactions.',
'54' => 'The referenced transaction does not meet the criteria for issuing a credit.',
'55' => 'The sum of credits against the referenced transaction would exceed the original debit amount.',
'56' => 'This merchant accepts ACH transactions only; no credit card transactions are accepted.',
'57' => 'An error occurred in processing. Please try again in 5 minutes.',
'58' => 'An error occurred in processing. Please try again in 5 minutes.',
'59' => 'An error occurred in processing. Please try again in 5 minutes.',
'60' => 'An error occurred in processing. Please try again in 5 minutes.',
'61' => 'An error occurred in processing. Please try again in 5 minutes.',
'62' => 'An error occurred in processing. Please try again in 5 minutes.',
'63' => 'An error occurred in processing. Please try again in 5 minutes.',
'64' => 'The referenced transaction was not approved.',
'65' => 'This transaction has been declined.',
'66' => 'The transaction did not meet gateway security guidelines.',
'67' => 'The given transaction type is not supported for this merchant.',
'68' => 'The version parameter is invalid.',
'69' => 'The transaction type is invalid. The value submitted in x_type was invalid.',
'70' => 'The transaction method is invalid.',
'71' => 'The bank account type is invalid.',
'72' => 'The authorization code is invalid.',
'73' => 'The driver\'s license date of birth is invalid.',
'74' => 'The duty amount is invalid.',
'75' => 'The freight amount is invalid.',
'76' => 'The tax amount is invalid.',
'77' => 'The SSN or tax ID is invalid.',
'78' => 'The Card Code (CVV2/CVC2/CID) is invalid.',
'79' => 'The driver\'s license number is invalid.',
'80' => 'The driver\'s license state is invalid.',
'81' => 'The merchant requested an integration method not compatible with the AIM API.',
'82' => 'The system no longer supports version 2.5; requests cannot be posted to scripts.',
'83' => 'The requested script is either invalid or no longer supported.',
'84' => 'This reason code is reserved or not applicable to this API.',
'85' => 'This reason code is reserved or not applicable to this API.',
'86' => 'This reason code is reserved or not applicable to this API.',
'87' => 'This reason code is reserved or not applicable to this API.',
'88' => 'This reason code is reserved or not applicable to this API.',
'89' => 'This reason code is reserved or not applicable to this API.',
'90' => 'This reason code is reserved or not applicable to this API.',
'91' => 'Version 2.5 is no longer supported.',
'92' => 'The gateway no longer supports the requested method of integration.',
'93' => 'A valid country is required.',
'94' => 'The shipping state or country is invalid.',
'95' => 'A valid state is required.',
'96' => 'This country is not authorized for buyers.',
'97' => 'This transaction cannot be accepted.',
'98' => 'This transaction cannot be accepted.',
'99' => 'This transaction cannot be accepted.',
'100' => 'The eCheck type is invalid.',
'101' => 'The given name on the account and/or the account type does not match the actual account.',
'102' => 'This request cannot be accepted.',
'103' => 'This transaction cannot be accepted.',
'104' => 'This transaction is currently under review.',
'105' => 'This transaction is currently under review.',
'106' => 'This transaction is currently under review.',
'107' => 'This transaction is currently under review.',
'108' => 'This transaction is currently under review.',
'109' => 'This transaction is currently under review.',
'110' => 'This transaction is currently under review.',
'111' => 'A valid billing country is required.',
'112' => 'A valid billing state/provice is required.',
'116' => 'The authentication indicator is invalid.',
'117' => 'The cardholder authentication value is invalid.',
'118' => 'The combination of authentication indicator and cardholder authentication value is invalid.',
'119' => 'Transactions having cardholder authentication values cannot be marked as recurring.',
'120' => 'An error occurred during processing. Please try again.',
'121' => 'An error occurred during processing. Please try again.',
'122' => 'An error occurred during processing. Please try again.',
'127' => 'The transaction resulted in an AVS mismatch. The address provided does not match billing address of cardholder.',
'141' => 'This transaction has been declined.',
'145' => 'This transaction has been declined.',
'152' => 'The transaction was authorized, but the client could not be notified; the transaction will not be settled.',
'165' => 'This transaction has been declined.',
'170' => 'An error occurred during processing. Please contact the merchant.',
'171' => 'An error occurred during processing. Please contact the merchant.',
'172' => 'An error occurred during processing. Please contact the merchant.',
'173' => 'An error occurred during processing. Please contact the merchant.',
'174' => 'The transaction type is invalid. Please contact the merchant.',
'175' => 'The processor does not allow voiding of credits.',
'180' => 'An error occurred during processing. Please try again.',
'181' => 'An error occurred during processing. Please try again.',
'200' => 'This transaction has been declined.',
'201' => 'This transaction has been declined.',
'202' => 'This transaction has been declined.',
'203' => 'This transaction has been declined.',
'204' => 'This transaction has been declined.',
'205' => 'This transaction has been declined.',
'206' => 'This transaction has been declined.',
'207' => 'This transaction has been declined.',
'208' => 'This transaction has been declined.',
'209' => 'This transaction has been declined.',
'210' => 'This transaction has been declined.',
'211' => 'This transaction has been declined.',
'212' => 'This transaction has been declined.',
'213' => 'This transaction has been declined.',
'214' => 'This transaction has been declined.',
'215' => 'This transaction has been declined.',
'216' => 'This transaction has been declined.',
'217' => 'This transaction has been declined.',
'218' => 'This transaction has been declined.',
'219' => 'This transaction has been declined.',
'220' => 'This transaction has been declined.',
'221' => 'This transaction has been declined.',
'222' => 'This transaction has been declined.',
'223' => 'This transaction has been declined.',
'224' => 'This transaction has been declined.',
'243' => 'Recurring billing is not allowed for this eCheck.Net type',
'244' => 'This eCheck.Net type is not allowed for this Bank Account Type.',
'245' => 'This eCheck.Net type is not allowed when using the payment gateway hosted payment form.',
'246' => 'This eCheck.Net type is not allowed.',
'247' => 'This eCheck.Net type is not allowed.',
'250' => 'This transaction has been declined.',
'251' => 'This transaction has been declined.',
'252' => 'Your order has been received. Thank you for your business!',
'253' => 'Your order has been received. Thank you for your business!',
'254' => 'This transaction has been declined.',
'261' => 'An error occurred during processing. Please try again'
);
var $_avsCodeMap = array(
'A' => PAYMENT_PROCESS_AVS_MISMATCH,
'B' => PAYMENT_PROCESS_AVS_ERROR,
'E' => PAYMENT_PROCESS_AVS_ERROR,
'G' => PAYMENT_PROCESS_AVS_NOAPPLY,
'N' => PAYMENT_PROCESS_AVS_MISMATCH,
'P' => PAYMENT_PROCESS_AVS_NOAPPLY,
'R' => PAYMENT_PROCESS_AVS_ERROR,
'S' => PAYMENT_PROCESS_AVS_ERROR,
'U' => PAYMENT_PROCESS_AVS_ERROR,
'W' => PAYMENT_PROCESS_AVS_MISMATCH,
'X' => PAYMENT_PROCESS_AVS_MATCH,
'Y' => PAYMENT_PROCESS_AVS_MATCH,
'Z' => PAYMENT_PROCESS_AVS_MISMATCH
);
var $_avsCodeMessages = array(
'A' => 'Address matches, postal code does not',
'B' => 'Address information not provided',
'E' => 'Address Verification System Error',
'G' => 'Non-U.S. Card Issuing Bank',
'N' => 'No match on street address nor postal code',
'P' => 'Address Verification System not applicable',
'R' => 'Retry - System unavailable or timeout',
'S' => 'Service not supported by issuer',
'U' => 'Address information unavailable',
'W' => '9-digit postal code matches, street address does not',
'X' => 'Address and 9-digit postal code match',
'Y' => 'Address and 5-digit postal code match',
'Z' => '5-digit postal code matches, street address does not'
);
var $_cvvCodeMap = array('M' => PAYMENT_PROCESS_CVV_MATCH,
'N' => PAYMENT_PROCESS_CVV_MISMATCH,
'P' => PAYMENT_PROCESS_CVV_ERROR,
'S' => PAYMENT_PROCESS_CVV_ERROR,
'U' => PAYMENT_PROCESS_CVV_ERROR
);
var $_cvvCodeMessages = array(
'M' => 'CVV code matches',
'N' => 'CVV code does not match',
'P' => 'CVV code was not processed',
'S' => 'CVV code should have been present',
'U' => 'Issuer unable to process request',
);
var $_fieldMap = array('0' => 'code',
'2' => 'messageCode',
'3' => 'message',
'4' => 'approvalCode',
'5' => 'avsCode',
'6' => 'transactionId',
'7' => 'invoiceNumber',
'8' => 'description',
'9' => 'amount',
'12' => 'customerId',
'37' => 'md5Hash',
'38' => 'cvvCode'
);
/**
* To hold the MD5 hash returned
*
* @var string
* @access private
*/
var $_md5Hash;
function Payment_Process_Response_AuthorizeNet($rawResponse)
{
$this->Payment_Process_Response($rawResponse);
}
/**
* Parses the data received from the payment gateway
*
* @access public
*/
function parse()
{
$delim = $this->_request->getOption('x_delim_char');
$encap = $this->_request->getOption('x_encap_char');
$responseArray = explode($encap . $delim . $encap, $this->_rawResponse);
if ($responseArray === false) {
return array();
}
$count = count($responseArray) - 1;
if ($responseArray[0][0] == $encap) {
$responseArray[0] = substr($responseArray[0], 1);
}
if (substr($responseArray[$count], -1) == $encap) {
$responseArray[$count] = substr($responseArray[$count], 0, -1);
}
// Save some fields in private members
$map = array_flip($this->_fieldMap);
$this->_md5Hash = $responseArray[$map['md5Hash']];
$this->_amount = $responseArray[$map['amount']];
$this->_mapFields($responseArray);
// Adjust result code/message if needed based on raw code
switch ($this->messageCode) {
case 33:
// Something is missing so we send the raw message back
$this->_statusCodeMessages[33] = $this->message;
break;
case 11:
// Duplicate transactions
$this->code = PAYMENT_PROCESS_RESULT_DUPLICATE;
break;
case 4:
case 41:
case 250:
case 251:
// Fraud detected
$this->code = PAYMENT_PROCESS_RESULT_FRAUD;
break;
}
}
/**
* Parses the data received from the payment gateway callback
*
* @access public
* @author Philippe Jausions <Philippe.Jausions@11abacus.com>
*/
function parseCallback()
{
$this->code = $this->_rawResponse['x_response_code'];
$this->messageCode = $this->_rawResponse['x_response_reason_code'];
$this->message = $this->_rawResponse['x_response_reason_text'];
$this->approvalCode = $this->_rawResponse['x_auth_code'];
$this->avsCode = $this->_rawResponse['x_avs_code'];
$this->transactionId = $this->_rawResponse['x_trans_id'];
$this->invoiceNumber = $this->_rawResponse['x_invoice_num'];
$this->description = $this->_rawResponse['x_description'];
$this->_amount = $this->_rawResponse['x_amount'];
$this->customerId = $this->_rawResponse['x_cust_id'];
$this->_md5Hash = $this->_rawResponse['x_MD5_Hash'];
$this->cvvCode = $this->_rawResponse['x_cvv2_resp_code'];
$map = array_flip($GLOBALS['_Payment_Process_AuthorizeNet']);
$this->action = $map[strtoupper($this->_rawResponse['x_type'])];
}
/**
* Validates the legitimacy of the response
*
* To be able to validate the response, the md5Value option
* must have been set in the processor. If the md5Value is not set this
* function will fail gracefully, but this MAY CHANGE IN THE FUTURE!
*
* Check if the response is legitimate by matching MD5 hashes.
* To avoid MD5 mismatch while the key is being renewed
* the md5Value can be an array with 2 indexes: "new" and "old"
* respectively holding the new and old MD5 values.
*
* Note: If you're having problem passing this check: be aware that
* the login name is CASE-SENSITIVE!!! (even though you can log in
* using it all lowered case...)
*
* @return mixed TRUE if response is legitimate, FALSE if not, PEAR_Error on error
* @access public
* @author Philippe Jausions <Philippe.Jausions@11abacus.com>
*/
function isLegitimate()
{
$md5Value = $this->_request->getOption('md5Value');
if (!$md5Value) {
// For now fail gracefully if it is not set.
return true;
}
$fields = $this->_request->login . $this->transactionId
. $this->_amount;
if (is_array($md5Value)) {
if (strcasecmp($this->_md5Hash, md5($md5Value['new'] . $fields)) == 0 ||
strcasecmp($this->_md5Hash, md5($md5Value['old'] . $fields)) == 0) {
return true;
}
} elseif (strcasecmp($this->_md5Hash, md5($md5Value . $fields)) == 0) {
return true;
}
return false;
}
}
?>

@ -0,0 +1,474 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
/**
* Beanstream processor
*
* PHP versions 4 and 5
*
* LICENSE: This source file is subject to version 3.0 of the PHP license
* that is available through the world-wide-web at the following URI:
* http://www.php.net/license/3_0.txt. If you did not receive a copy of
* the PHP License and are unable to obtain it through the web, please
* send a note to license@php.net so we can mail you a copy immediately.
*
* @category Payment
* @package Payment_Process
* @author Mike Benoit <ipso@snappymail.ca> |
* @copyright 1997-2005 The PHP Group
* @license http://www.php.net/license/3_0.txt PHP License 3.0
* @version CVS: $Id: Beanstream.php,v 1.33 2005/11/01 18:55:29 jausions Exp $
* @link http://pear.php.net/package/Payment_Process
*/
require_once 'Payment/Process.php';
require_once 'Payment/Process/Common.php';
require_once 'Net/Curl.php';
/**
* Defines global variables
*/
$GLOBALS['_Payment_Process_Beanstream'] = array(
PAYMENT_PROCESS_ACTION_NORMAL => 'P',
PAYMENT_PROCESS_ACTION_AUTHONLY => 'PA',
PAYMENT_PROCESS_ACTION_POSTAUTH => 'PAC',
PAYMENT_PROCESS_ACTION_VOID => 'VP'
);
/**
* Payment_Process_Beanstream
*
* This is a processor for Beanstream's merchant payment gateway.
* (http://www.beanstream.com/)
*
* @package Payment_Process
* @author Mike Benoit <ipso@snappymail.ca>
* @version @version@
* @link http://www.beanstream.com/
*/
class Payment_Process_Beanstream extends Payment_Process_Common
{
/**
* Front-end -> back-end field map.
*
* This array contains the mapping from front-end fields (defined in
* the Payment_Process class) to the field names Beanstream requires.
*
* @see _prepare()
* @access private
*/
var $_fieldMap = array(
// Required
'customerId' => 'merchant_id',
'login' => 'username',
'password' => 'password',
'action' => 'trnType',
'invoiceNumber' => 'trnOrderNumber',
'amount' => 'trnAmount',
'name' => '',
'address' => 'ordAddress1',
'city' => 'ordCity',
'state' => 'ordProvince',
'country' => 'ordCountry',
'postalCode' => 'ordPostalCode',
'zip' => 'ordPostalCode',
'phone' => 'ordPhoneNumber',
'email' => 'ordEmailAddress',
'errorPage' => 'errorPage',
);
/**
* $_typeFieldMap
*
* @author Joe Stump <joe@joestump.net>
* @access protected
*/
var $_typeFieldMap = array(
'CreditCard' => array(
'firstName' => 'firstName',
'lastName' => 'lastName',
'cardNumber' => 'trnCardNumber',
'cvv' => 'trnCardCvd',
'expDate' => 'expDate'
),
);
/**
* Default options for this processor.
*
* @see Payment_Process::setOptions()
* @access private
*/
var $_defaultOptions = array(
'authorizeUri' => 'https://www.beanstream.com/scripts/process_transaction.asp',
'requestType' => 'BACKEND',
'cavEnabled' => 0,
'cavServiceVersion' => '1.2',
);
/**
* List of possible encapsulation characters
*
* @var string
* @access private
*/
var $_encapChars = '|~#$^*_=+-`{}![]:";<>?/&';
/**
* Has the transaction been processed?
*
* @type boolean
* @access private
*/
var $_processed = false;
/**
* The response body sent back from the gateway.
*
* @access private
*/
var $_responseBody = '';
/**
* Constructor.
*
* @param array $options Class options to set.
* @see Payment_Process::setOptions()
* @return void
*/
function __construct($options = false)
{
parent::__construct($options);
$this->_driver = 'Beanstream';
$this->_makeRequired('customerId','login', 'password', 'action', 'invoiceNumber');
}
/**
* Processes the transaction.
*
* Success here doesn't mean the transaction was approved. It means
* the transaction was sent and processed without technical difficulties.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
* @access public
*/
function &process()
{
// Sanity check
$result = $this->validate();
if (PEAR::isError($result)) {
return $result;
}
// Prepare the data
$result = $this->_prepare();
if (PEAR::isError($result)) {
return $result;
}
$fields = $this->_prepareQueryString();
if (PEAR::isError($fields)) {
return $fields;
}
// Don't die partway through
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
$curl = new Net_Curl($this->_options['authorizeUri']);
if (PEAR::isError($curl)) {
PEAR::popErrorHandling();
return $curl;
}
$curl->timeout = 300;
$curl->type = 'post';
$curl->fields = $fields;
$curl->userAgent = 'PEAR Payment_Process_Beanstream 0.1';
//$curl->verboseAll();
$result = $curl->execute();
if (PEAR::isError($result)) {
PEAR::popErrorHandling();
return $result;
} else {
$curl->close();
}
$this->_responseBody = trim($result);
$this->_processed = true;
// Restore error handling
PEAR::popErrorHandling();
$response = Payment_Process_Result::factory($this->_driver,
$this->_responseBody,
$this);
if (!PEAR::isError($response)) {
$response->parse();
}
$response->action = $this->action;
return $response;
}
/**
* Processes a callback from payment gateway
*
* Success here doesn't mean the transaction was approved. It means
* the callback was received and processed without technical difficulties.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
*/
function &processCallback()
{
$this->_responseBody = $_POST;
$this->_processed = true;
$response = &Payment_Process_Result::factory($this->_driver,
$this->_responseBody);
if (!PEAR::isError($response)) {
$response->_request = $this;
$response->parseCallback();
$r = $response->isLegitimate();
if (PEAR::isError($r)) {
return $r;
} elseif ($r === false) {
return PEAR::raiseError('Illegitimate callback from gateway.');
}
}
return $response;
}
/**
* Get (completed) transaction status.
*
* @return string Two-digit status returned from gateway.
*/
function getStatus()
{
return false;
}
/**
* Prepare the POST query string.
*
* You will need PHP_Compat::str_split() if you run this processor
* under PHP 4.
*
* @access private
* @return string The query string
*/
function _prepareQueryString()
{
$data = array_merge($this->_options, $this->_data);
foreach ($data as $key => $val) {
if (strlen($val) > 0 ) {
$return[] = $key.'='.urlencode($val);
}
}
$retval = implode('&', $return);
return $retval;
}
/**
* _handleName
*
* We need to combine firstName and lastName into a
* single name.
*
* @access private
*/
function _handleName()
{
$this->_data['trnCardOwner'] = $this->_payment->firstName.' '.$this->_payment->lastName;
$this->_data['ordName'] = $this->_payment->firstName.' '.$this->_payment->lastName;
}
/**
* _handleExpDate
*
* Convert ExpDate to seperate month/year
*
* @access private
*/
function _handleExpDate()
{
$split_expire_date = explode('/', $this->_payment->expDate);
$this->_data['trnExpMonth'] = $split_expire_date[0];
$this->_data['trnExpYear'] = substr( $split_expire_date[1], -2, 2);
}
}
class Payment_Process_Result_Beanstream extends Payment_Process_Result {
var $_statusCodeMap = array('1' => PAYMENT_PROCESS_RESULT_APPROVED,
'2' => PAYMENT_PROCESS_RESULT_DECLINED,
'3' => PAYMENT_PROCESS_RESULT_OTHER,
'4' => PAYMENT_PROCESS_RESULT_REVIEW
);
var $_avsCodeMap = array(
'A' => PAYMENT_PROCESS_AVS_MISMATCH,
'B' => PAYMENT_PROCESS_AVS_ERROR,
'E' => PAYMENT_PROCESS_AVS_ERROR,
'G' => PAYMENT_PROCESS_AVS_NOAPPLY,
'N' => PAYMENT_PROCESS_AVS_MISMATCH,
'P' => PAYMENT_PROCESS_AVS_NOAPPLY,
'R' => PAYMENT_PROCESS_AVS_ERROR,
'S' => PAYMENT_PROCESS_AVS_ERROR,
'U' => PAYMENT_PROCESS_AVS_ERROR,
'W' => PAYMENT_PROCESS_AVS_MISMATCH,
'X' => PAYMENT_PROCESS_AVS_MATCH,
'Y' => PAYMENT_PROCESS_AVS_MATCH,
'Z' => PAYMENT_PROCESS_AVS_MISMATCH
);
var $_avsCodeMessages = array(
'0' => 'Address verification not performed for this transaction',
'5' => 'Invalid AVS repsonse',
'0' => 'Address verification data contains edit error',
'A' => 'Address matches, postal code does not',
'B' => 'Address information not provided',
'E' => 'Address Verification System Error',
'G' => 'Non-U.S. Card Issuing Bank',
'N' => 'No match on street address nor postal code',
'P' => 'Address Verification System not applicable',
'R' => 'Retry - System unavailable or timeout',
'S' => 'Service not supported by issuer',
'U' => 'Address information unavailable',
'W' => '9-digit postal code matches, street address does not',
'X' => 'Address and 9-digit postal code match',
'Y' => 'Address and 5-digit postal code match',
'Z' => '5-digit postal code matches, street address does not'
);
var $_cvvCodeMap = array('1' => PAYMENT_PROCESS_CVV_MATCH,
'2' => PAYMENT_PROCESS_CVV_MISMATCH,
'3' => PAYMENT_PROCESS_CVV_ERROR,
'4' => PAYMENT_PROCESS_CVV_ERROR,
'5' => PAYMENT_PROCESS_CVV_ERROR,
'6' => PAYMENT_PROCESS_CVV_ERROR
);
var $_cvvCodeMessages = array(
1 => 'CVV code matches',
2 => 'CVV code does not match',
3 => 'CVV code was not processed',
4 => 'CVV code should have been present',
5 => 'Issuer unable to process request',
6 => 'CVV not provided',
);
var $_fieldMap = array('0' => 'code',
'2' => 'messageCode',
'3' => 'message',
'4' => 'approvalCode',
'5' => 'avsCode',
'6' => 'transactionId',
'7' => 'invoiceNumber',
'8' => 'description',
'9' => 'amount',
'12' => 'customerId',
'37' => 'md5Hash',
'38' => 'cvvCode'
);
function Payment_Process_Response_Beanstream($rawResponse)
{
$this->Payment_Process_Response($rawResponse);
}
/**
* Parses the data received from the payment gateway
*
* @access public
*/
function parse()
{
//get last line of response
$split_response = explode("\n", $this->_rawResponse );
$response_str = array_pop($split_response);
if ( preg_match('/trnApproved=(.*)/i', $response_str ) ) {
if ( isset($response_str) AND strlen($response_str) > 0 ) {
//Parse URL for variables.
$response_str_arr = explode('&', urldecode( $response_str ) );
if ( is_array($response_str_arr) ) {
foreach( $response_str_arr as $response_value ) {
$split_response_value = explode('=', $response_value, 2);
if ( isset($split_response_value[0]) AND isset($split_response_value[1]) ) {
$responseArray[trim($split_response_value[0])] = trim($split_response_value[1]);
}
}
unset($response_str_arr, $response_value, $split_response_value);
//var_dump($responseArray);
if ( !isset($responseArray) AND !is_array( $responseArray) ) {
$this->_returnCode = PAYMENT_PROCESS_RESULT_OTHER;
}
if ( isset($responseArray['trnApproved']) AND $responseArray['trnApproved'] == 1 ) {
$this->_returnCode = PAYMENT_PROCESS_RESULT_APPROVED;
} else {
$this->_returnCode = PAYMENT_PROCESS_RESULT_DECLINED;
}
if ( isset($responseArray['messageId']) ) {
$this->code = $responseArray['messageId'];
$this->messageCode = $responseArray['messageId'];
}
if ( isset($responseArray['errorType']) AND $responseArray['errorType'] == 'N' ) {
$this->message = $responseArray['messageText'] .' (Code: '. $responseArray['messageId'] .')';
} elseif ( $responseArray['errorType'] != 'N' AND isset($responseArray['errorFields']) ) {
$this->message = $responseArray['messageText'] .' Code('. $responseArray['messageId'] .')';
if ( isset($responseArray['errorFields']) AND $responseArray['errorFields'] != '' ) {
$this->message .= ' Error Fields('.$responseArray['errorFields'].')';
}
}
if ( isset($responseArray['authCode']) ) {
$this->approvalCode = $responseArray['authCode'];
}
if ( isset($responseArray['trnId']) ) {
$this->transactionId = $responseArray['trnId'];
}
if ( isset($responseArray['trnOrderNumber']) ) {
$this->invoiceNumber = $responseArray['trnOrderNumber'];
}
if ( isset($responseArray['cvdId']) ) {
$this->cvvCode = $responseArray['cvdId'];
if ( isset($this->_cvvCodeMessages[$this->cvvCode]) ) {
$this->cvvMessage = $this->_cvvCodeMessages[$this->cvvCode];
}
}
//$this->avsCode = '';
}
unset($location_url_arr);
}
} else {
$this->_returnCode = PAYMENT_PROCESS_RESULT_OTHER;
$this->message = 'Error parsing response.';
}
}
}
?>

@ -0,0 +1,506 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
/**
* Beanstream Batch EFT processor
*
* PHP versions 4 and 5
*
* LICENSE: This source file is subject to version 3.0 of the PHP license
* that is available through the world-wide-web at the following URI:
* http://www.php.net/license/3_0.txt. If you did not receive a copy of
* the PHP License and are unable to obtain it through the web, please
* send a note to license@php.net so we can mail you a copy immediately.
*
* @category Payment
* @package Payment_Process
* @author Mike Benoit <ipso@snappymail.ca> |
* @copyright 1997-2005 The PHP Group
* @license http://www.php.net/license/3_0.txt PHP License 3.0
* @version CVS: $Id: Beanstream.php,v 1.33 2005/11/01 18:55:29 jausions Exp $
* @link http://pear.php.net/package/Payment_Process
*/
require_once 'Payment/Process.php';
require_once 'Payment/Process/Common.php';
require_once 'Net/Curl.php';
/**
* Defines global variables
*/
$GLOBALS['_Payment_Process_BeanstreamEFT'] = array(
PAYMENT_PROCESS_ACTION_NORMAL => 'D',
PAYMENT_PROCESS_ACTION_AUTHONLY => NULL,
PAYMENT_PROCESS_ACTION_POSTAUTH => NULL,
PAYMENT_PROCESS_ACTION_VOID => 'VD'
);
/**
* Payment_Process_Beanstream
*
* This is a processor for Beanstream's merchant payment gateway.
* (http://www.beanstream.com/)
*
* @package Payment_Process
* @author Mike Benoit <ipso@snappymail.ca>
* @version @version@
* @link http://www.beanstream.com/
*/
class Payment_Process_BeanstreamEFT extends Payment_Process_Common
{
/**
* Front-end -> back-end field map.
*
* This array contains the mapping from front-end fields (defined in
* the Payment_Process class) to the field names Beanstream requires.
*
* @see _prepare()
* @access private
*/
var $_fieldMap = array(
// Required
'customerId' => 'loginCompany',
//'login' => 'loginUser',
//'password' => 'loginPass',
'password' => 'passCode',
'action' => 'trnType',
'invoiceNumber' => 'trnOrderNumber',
'amount' => 'trnAmount',
'processDate' => 'processDate',
'batchFile' => 'batchFile',
//'name' => 'name',
//'address' => '',
//'city' => '',
//'state' => '',
//'country' => '',
//'postalCode' => '',
//'zip' => '',
//'phone' => '',
//'email' => '',
//'errorPage' => 'errorPage',
);
/**
* $_typeFieldMap
*
* @author Joe Stump <joe@joestump.net>
* @access protected
*/
var $_typeFieldMap = array(
'ACH' => array(
'routingCode' => 'routingNumber',
'accountNumber' => 'accountNumber',
'accountCode' => 'accountCode',
'name' => 'ordName'
),
'EFT' => array(
'institutionCode' => 'institutionId',
'routingCode' => 'transitNumber',
'accountNumber' => 'accountNumber',
'name' => 'ordName'
),
);
/**
* Default options for this processor.
*
* @see Payment_Process::setOptions()
* @access private
*/
var $_defaultOptions = array(
'authorizeUri' => 'https://www.beanstream.com/scripts/batch_upload.asp',
//'requestType' => 'BACKEND',
//'cavEnabled' => 0,
'ServiceVersion' => '1.1',
);
/**
* List of possible encapsulation characters
*
* @var string
* @access private
*/
var $_encapChars = '|~#$^*_=+-`{}![]:";<>?/&';
/**
* Has the transaction been processed?
*
* @type boolean
* @access private
*/
var $_processed = false;
/**
* The response body sent back from the gateway.
*
* @access private
*/
var $_responseBody = '';
/**
* Constructor.
*
* @param array $options Class options to set.
* @see Payment_Process::setOptions()
* @return void
*/
function __construct($options = false)
{
parent::__construct($options);
$this->_driver = 'BeanstreamEFT';
//$this->_makeRequired('customerId','login', 'password', 'action', 'invoiceNumber');
$this->_makeRequired('customerId','password', 'action', 'invoiceNumber');
}
/**
* Prepare the batch data.
*
* This function handles the 'testTransaction' option, which is specific to
* this processor.
*/
function _prepare()
{
$result = parent::_prepare();
if ( $result !== TRUE ) {
return $result;
}
//Build batch file for each type of transaction type.
if ($this->_payment->getType() == 'EFT') {
$batch_fields = array('trnType', 'institutionId', 'transitNumber', 'accountNumber', 'trnAmount', 'trnOrderNumber', 'ordName' );
if ( is_array($batch_fields) ) {
$batch_data[] = substr( $this->_payment->getType(), 0, 1);
foreach( $batch_fields as $batch_field ) {
$batch_data[] = $this->_data[$batch_field];
}
}
} elseif ($this->_payment->getType() == 'ACH') {
$batch_fields = array('trnType', 'routingNumber', 'accountNumber', 'accountCode', 'trnAmount', 'trnOrderNumber', 'ordName' );
if ( is_array($batch_fields) ) {
$batch_data[] = substr( $this->_payment->getType(), 0, 1);
foreach( $batch_fields as $batch_field ) {
if ( $batch_field == 'accountCode' ) {
$batch_data[] = 'CC';
} else {
$batch_data[] = $this->_data[$batch_field];
}
}
}
}
if ( is_array($batch_data) ) {
$this->batchFile = implode(',', $batch_data);
}
return TRUE;
}
/**
* Processes the transaction.
*
* Success here doesn't mean the transaction was approved. It means
* the transaction was sent and processed without technical difficulties.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
* @access public
*/
function &process()
{
// Sanity check
$result = $this->validate();
if (PEAR::isError($result)) {
return $result;
}
// Prepare the data
$result = $this->_prepare();
if (PEAR::isError($result)) {
return $result;
}
$fields = $this->_prepareQueryString();
if (PEAR::isError($fields)) {
return $fields;
}
// Don't die partway through
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
//Must use GET for login information.
$curl = new Net_Curl($this->_options['authorizeUri'].'?'.$fields);
$curl->timeout = 300;
if (PEAR::isError($curl)) {
PEAR::popErrorHandling();
return $curl;
}
$temp_file_prefix = 'eft_';
if ( isset($this->_data['trnOrderNumber']) AND preg_match( '/^[A-Z0-9_\-]+$/i', $this->_data['trnOrderNumber'] ) ) {
$temp_file_prefix .= $this->_data['trnOrderNumber'].'_';
}
$temp_file = tempnam( sys_get_temp_dir(), $temp_file_prefix ).'.csv';
file_put_contents( $temp_file, $this->batchFile);
if ( class_exists('\CURLFile') ) {
$curl->fields = array('batchFile' => new \CURLFile( $temp_file ) ); //PHP v5.5+ method.
} else {
$curl->fields = array('batchFile' => '@'.$temp_file); //Pre PHP v5.5 method.
}
$curl->userAgent = 'PEAR Payment_Process_Beanstream 0.1';
//$curl->verboseAll();
$result = $curl->execute();
unlink($temp_file);
if (PEAR::isError($result)) {
PEAR::popErrorHandling();
return $result;
} else {
$curl->close();
}
$this->_responseBody = trim($result);
$this->_processed = true;
// Restore error handling
PEAR::popErrorHandling();
$response = Payment_Process_Result::factory($this->_driver,
$this->_responseBody,
$this);
if (!PEAR::isError($response)) {
$response->parse();
}
$response->action = $this->action;
return $response;
}
/**
* Processes a callback from payment gateway
*
* Success here doesn't mean the transaction was approved. It means
* the callback was received and processed without technical difficulties.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
*/
function &processCallback()
{
$this->_responseBody = $_POST;
$this->_processed = true;
$response = &Payment_Process_Result::factory($this->_driver,
$this->_responseBody);
if (!PEAR::isError($response)) {
$response->_request = $this;
$response->parseCallback();
$r = $response->isLegitimate();
if (PEAR::isError($r)) {
return $r;
} elseif ($r === false) {
return PEAR::raiseError('Illegitimate callback from gateway.');
}
}
return $response;
}
/**
* Get (completed) transaction status.
*
* @return string Two-digit status returned from gateway.
*/
function getStatus()
{
return false;
}
/**
* Prepare the POST query string.
*
* You will need PHP_Compat::str_split() if you run this processor
* under PHP 4.
*
* @access private
* @return string The query string
*/
function _prepareQueryString()
{
//$url_fields = array('ServiceVersion', 'loginCompany', 'loginUser', 'loginPass', 'processDate' );
$url_fields = array('ServiceVersion', 'loginCompany', 'passCode', 'processDate' );
$data = array_merge($this->_options, $this->_data);
foreach ($data as $key => $val) {
if ( in_array($key, $url_fields) AND strlen($val) > 0 ) {
//if ( strlen($val) > 0 ) {
$return[] = $key.'='.urlencode($val);
}
}
$retval = implode('&', $return);
return $retval;
}
/**
* Validates the charge amount.
*
* Charge amount must be 8 characters long, double-precision.
* Current min/max are rather arbitrarily set to $0.01 and $99999.99,
* respectively.
*
* @return boolean true on success, false otherwise
*/
function _validateAmount()
{
return Validate::number($this->amount, array(
'decimal' => '.',
'dec_prec' => 2,
'min' => 0.01,
'max' => 99999.99
));
}
/**
* _handleAmount
*
* Amounts must always be in pennies.
*
* @access private
*/
function _handleAmount()
{
$this->_data['trnAmount'] = $this->amount = $this->amount*100;
}
/**
* _handleProcessDate
*
* We need to make sure process date is in format YYYYMMDD and if its after 11AM it must be the next day.
*
* @access private
*/
function _handleProcessDate()
{
if ( isset($this->processDate) ) {
$epoch = (int)$this->processDate;
} else {
$this->processDate = FALSE;
$epoch = time();
}
if ( $epoch < time() ) {
$epoch = time();
}
$cutoff_hour = date('G', $epoch );
if ( $cutoff_hour > 10 ) { // 11AM
//Process date is next day
$epoch += 86400;
} else {
//Process date can be today.
}
$this->processDate = $this->_data['processDate'] = date('Ymd', $epoch );
}
}
class Payment_Process_Result_BeanstreamEFT extends Payment_Process_Result {
var $_statusCodeMap = array('1' => PAYMENT_PROCESS_RESULT_APPROVED,
'2' => PAYMENT_PROCESS_RESULT_OTHER,
'3' => PAYMENT_PROCESS_RESULT_OTHER,
'4' => PAYMENT_PROCESS_RESULT_REVIEW,
'5' => PAYMENT_PROCESS_RESULT_REVIEW,
'6' => PAYMENT_PROCESS_RESULT_REVIEW,
'7' => PAYMENT_PROCESS_RESULT_DECLINED,
'8' => PAYMENT_PROCESS_RESULT_REVIEW,
'9' => PAYMENT_PROCESS_RESULT_REVIEW,
'10' => PAYMENT_PROCESS_RESULT_REVIEW,
'11' => PAYMENT_PROCESS_RESULT_REVIEW,
'12' => PAYMENT_PROCESS_RESULT_REVIEW,
'13' => PAYMENT_PROCESS_RESULT_REVIEW,
);
var $_statusCodeMessages = array(
'1' => 'File successfully received',
'2' => 'Secure connection required',
'3' => 'Service version not supported',
'4' => 'Invalid login credentials',
'5' => 'Insufficient user permissions',
'6' => 'Batch Processing service not enabled',
'7' => 'Invalid processing date',
'8' => 'Service is busy importing another file. Try again later',
'9' => 'File greater than maximum allowable size',
'10' => 'Unexpected error',
'11' => 'No batch file received in request',
'12' => 'Merchant account status cannot be Disabled or Closed for operation',
'13' => 'Upload rejected. File name is limited to 32 characters in length, including file type extension',
);
var $_fieldMap = array('0' => 'code',
'2' => 'messageCode',
'3' => 'message',
'4' => 'approvalCode',
'5' => 'avsCode',
'6' => 'transactionId',
'7' => 'invoiceNumber',
'8' => 'description',
'9' => 'amount',
'12' => 'customerId',
'37' => 'md5Hash',
'38' => 'cvvCode'
);
function Payment_Process_Response_BeanstreamEFT($rawResponse)
{
$this->Payment_Process_Response($rawResponse);
}
/**
* Parses the data received from the payment gateway
*
* @access public
*/
function parse()
{
if ( preg_match('/<code>([\d]+)<\/code>/i', $this->_rawResponse, $code_match ) ) {
if ( isset($code_match[1]) ) {
$code = (int)$code_match[1];
$this->code = $code;
$this->messageCode = $code;
if ( $code == 1 ) {
$this->_returnCode = PAYMENT_PROCESS_RESULT_APPROVED;
if ( preg_match('/<batch_id>(.*)<\/batch_id>/i', $this->_rawResponse, $batch_id_match ) ) {
$this->approvalCode = $this->transactionId = $batch_id_match[1];
}
} else {
$this->_returnCode = PAYMENT_PROCESS_RESULT_DECLINED;
}
if ( preg_match('/<message>(.*)<\/message>/i', $this->_rawResponse, $message_match ) ) {
$this->message = $message_match[1] .' (Code: '. $code .')';
}
} else {
$this->_returnCode = PAYMENT_PROCESS_RESULT_OTHER;
$this->message = 'Error parsing response.';
}
} else {
$this->_returnCode = PAYMENT_PROCESS_RESULT_OTHER;
$this->message = 'Error parsing response.';
}
}
}
?>

@ -0,0 +1,635 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2004 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Robin Ericsson <lobbin@localhost.nu> |
// +----------------------------------------------------------------------+
//
// $Id: Bibit.php,v 1.6 2005/07/28 02:52:58 jstump Exp $
require_once('Payment/Process.php');
require_once('Payment/Process/Common.php');
require_once('Net/Curl.php');
require_once('XML/Util.php');
require_once('XML/XPath.php');
define('PAYMENT_PROCESS_ACTION_BIBIT_AUTH', 300);
define('PAYMENT_PROCESS_ACTION_BIBIT_REDIRECT', 400);
define('PAYMENT_PROCESS_ACTION_BIBIT_REFUND', 500);
define('PAYMENT_PROCESS_ACTION_BIBIT_CAPTURE', 600);
// Map actions
$GLOBALS['_Payment_Process_Bibit'] = array(
PAYMENT_PROCESS_ACTION_NORMAL => PAYMENT_PROCESS_ACTION_BIBIT_REDIRECT,
PAYMENT_PROCESS_ACTION_AUTHONLY => PAYMENT_PROCESS_ACTION_BIBIT_AUTH,
PAYMENT_PROCESS_ACTION_CREDIT => PAYMENT_PROCESS_ACTION_BIBIT_REFUND,
PAYMENT_PROCESS_ACTION_SETTLE => PAYMENT_PROCESS_ACTION_BIBIT_CAPTURE,
);
/**
* Payment_Process_Bibit
*
* This is a process for Bibit's merchant payment gateway.
* (http://www.bibit.com)
*
* *** WARNING ***
* This is BETA code, and hos not been fully tested. It is not recommended
* that you use it in a production environment without further testing.
*
* @package Payment_Process
* @author Robin Ericsson <lobbin@localhost.nu>
* @version @version@
*/
class Payment_Process_Bibit extends Payment_Process_Common {
/**
* Front-end -> back-end field map.
*
* This array contains the mapping from front-end fields (defined in
* the Payment_Process class) to the field names Bibit requires.
*
* @see _prepare()
* @access private
*/
var $_fieldMap = array(
// Required
'login' => 'x_login',
'password' => 'x_password',
'ordercode' => 'x_ordercode',
'description' => 'x_descr',
'amount' => 'x_amount',
'currency' => 'x_currency',
'exponent' => 'x_exponent',
'action' => 'x_action',
// Optional
'ordercontent' => 'x_ordercontent',
'shopper_ip_address' => 'shopperIPAddress',
'shopper_email_address' => 'shopperEmailAddress',
'session_id' => 'sessionId',
'authenticated_shopper_id' => 'authenticatedShopperID',
'shipping_address' => 'shippingAddress',
'payment_method_mask' => 'paymentMethodMask',
);
/**
* Default options for this processor.
*
* @see Payment_Process::setOptions()
* @access private
*/
var $_defaultOptions = array(
'authorizeUri' => 'https://secure.bibit.com/jsp/merchant/xml/paymentService.jsp',
'authorizeTestUri' => 'https://secure-test.bibit.com/jsp/merchant/xml/paymentService.jsp',
'x_version' => '1.4'
);
/**
* The reponse body sent back from the gateway.
*
* @access private
*/
var $_responseBody = '';
/**
* The orders unique code
*
* @access private
*/
var $ordercode = '';
/**
* The order amounts currency
*
* @access private
*/
var $currency = '';
/**
* The order amounts exponent
*
* @access private
*/
var $exponent = 0;
/**
* The orders content as displayed at bibit
*
* @access private
*/
var $ordercontent = '';
/**
* The ip-address the order comes from
*
* @access private
*/
var $shopper_ip_address;
/**
* The shoppers email-address
*
* @access private
*/
var $shopper_email_address;
/**
* The unique id of the users session
*
* @access private
*/
var $session_id;
/**
* Unique id of the authenticed shopper
*
* @access private
*/
var $authenticated_shopper_id;
/**
* Shipping address
*
* @access private
*/
var $shipping_address = array();
/**
* Payment method mask
*
* @access private
*/
var $payment_method_mask = array();
/**
* $_typeFieldMap
*
* @access protected
*/
var $_typeFieldMap = array(
'CreditCard' => array(
'cvv' => 'x_card_code',
'expDate' => 'x_exp_date',
'cardNumber' => 'x_card_num',
)
);
/**
* Constructor.
*
* @param array $options Class options to set.
* @see Payment_Process::setOptions()
* @return void
*/
function __construct($options = false)
{
parent::__construct();
$this->_driver = 'Bibit';
$this->_makeRequired('login', 'password', 'ordercode', 'description', 'amount', 'currency', 'exponent', 'cardNumber', 'expDate', 'action');
}
/**
* Process the transaction.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
*/
function &process()
{
// Sanity check
$result = $this->validate();
if(PEAR::isError($result)) {
return $result;
}
// Prepare the data
$result = $this->_prepare();
if (PEAR::isError($result)) {
return $result;
}
// Don't die partway through
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
$fields = $this->_prepareQueryString();
$curl = new Net_Curl(isset($this->_options['live']) ? $this->_options['authorizeUri'] : $this->_options['authorizeTestUri']);
if (PEAR::isError($curl)) {
PEAR::popErrorHandling();
return $curl;
}
$curl->type = 'PUT';
$curl->fields = $fields;
$curl->userAgent = 'PEAR Payment_Process_Bibit 0.1';
$curl->username = $this->_data['x_login'];
$curl->password = $this->_data['x_password'];
$result = &$curl->execute();
if (PEAR::isError($result)) {
PEAR::popErrorHandling();
return $result;
} else {
$curl->close();
}
$this->_responseBody = trim($result);
$this->_processed = true;
// Restore error handling
PEAR::popErrorHandling();
$response = &Payment_Process_Result::factory($this->_driver,
$this->_responseBody,
$this);
if (!PEAR::isError($response)) {
$response->parse();
}
return $response;
}
/**
* Prepare the PUT query xml.
*
* @access private
* @return string The query xml
*/
function _prepareQueryString()
{
$data = array_merge($this->_options,$this->_data);
$doc = XML_Util::getXMLDeclaration();
$doc .= '<!DOCTYPE paymentService PUBLIC "-//Bibit//DTD Bibit PaymentService v1//EN" "http://dtd.bibit.com/paymentService_v1.dtd">';
$doc .= XML_Util::createStartElement('paymentService', array('version' => $data['x_version'], 'merchantCode' => $data['x_login']));
if ($data['x_action'] == PAYMENT_PROCESS_ACTION_BIBIT_CAPTURE || $data['x_action'] == PAYMENT_PROCESS_ACTION_BIBIT_REFUND) {
$doc .= XML_Util::createStartElement('modify');
$doc .= XML_Util::createStartElement('orderModification', array('orderCode' => $data['x_ordercode']));
if ($data['x_action'] == PAYMENT_PROCESS_ACTION_BIBIT_CAPTURE) {
$doc .= XML_Util::createStartElement('capture');
$d = array();
$t = time() - 86400;
$d['dayOfMonth'] = date('d', $t);
$d['month'] = date('m', $t);
$d['year'] = date('Y', $t);
$d['hour'] = date('H', $t);
$d['minute'] = date('i', $t);
$d['second'] = date('s', $t);
$doc .= XML_Util::createTag('date', $d);
$doc .= XML_Util::createTag('amount', array('value' => $data['x_amount'],
'currencyCode' => $data['x_currency'],
'exponent' => $data['x_exponent']));
$doc .= XML_Util::createEndElement('capture');
} else if ($data['x_action'] == PAYMENT_PROCESS_ACTION_BIBIT_REFUND) {
$doc .= XML_Util::createStartElement('refund');
$doc .= XML_Util::createTag('amount', array('value' => $data['x_amount'],
'currencyCode' => $data['x_currency'],
'exponent' => $data['x_exponent']));
$doc .= XML_Util::createEndElement('refund');
}
$doc .= XML_Util::createEndElement('orderModification');
$doc .= XML_Util::createEndElement('modify');
} else {
$doc .= XML_Util::createStartElement('submit');
$doc .= XML_Util::createStartElement('order', array('orderCode' => $data['x_ordercode']));
$doc .= XML_Util::createTag('description', null, $data['x_descr']);
$doc .= XML_Util::createTag('amount', array('value' => $data['x_amount'],
'currencyCode' => $data['x_currency'],
'exponent' => $data['x_exponent']));
if (isset($data['x_ordercontent'])) {
$doc .= XML_Util::createStartElement('orderContent');
$doc .= XML_Util::createCDataSection($data['x_ordercontent']);
$doc .= XML_Util::createEndElement('orderContent');
}
if ($data['x_action'] == PAYMENT_PROCESS_ACTION_BIBIT_REDIRECT) {
if (is_array($data['paymentMethodMask']) && count($data['paymentMethodMask'] > 0)) {
$doc .= XML_Util::createStartElement('paymentMethodMask');
foreach($data['paymentMethodMask']['include'] as $code) {
$doc .= XML_Util::createTag('include', array('code' => $code));
}
foreach($data['paymentMethodMask']['exclude'] as $code) {
$doc .= XML_Util::createTag('exclude', array('code' => $code));
}
$doc .= XML_Util::createEndElement('paymentMethodMask');
}
} else if ($data['x_action'] == PAYMENT_PROCESS_ACTION_BIBIT_AUTH) {
$doc .= XML_Util::createStartElement('paymentDetails');
switch ($this->_payment->type) {
case PAYMENT_PROCESS_CC_VISA: $cc_type = 'VISA-SSL'; break;
case PAYMENT_PROCESS_CC_MASTERCARD: $cc_type = 'ECMC-SSL'; break;
case PAYMENT_PROCESS_CC_AMEX: $cc_type = 'AMEX-SSL'; break;
}
$doc .= XML_Util::createStartElement($cc_type);
if (isset($data['x_card_num'])) {
$doc .= XML_Util::createTag('cardNumber', null, $data['x_card_num']);
}
if (isset($data['x_exp_date'])) {
$doc .= XML_Util::createStartElement('expiryDate');
$doc .= XML_Util::createTag('date', array('month' => substr($data['x_exp_date'], 0, 2),
'year' => substr($data['x_exp_date'], 3, 4)));
$doc .= XML_Util::createEndElement('expiryDate');
}
if (isset($this->_payment->firstName) &&
isset($this->_payment->lastName)) {
$doc .= XML_Util::createTag('cardHolderName', null, $this->_payment->firstName.' '.$this->_payment->lastName);
}
if (isset($data['x_card_code'])) {
$doc .= XML_Util::createTag('cvc', null, $data['x_card_code']);
}
$doc .= XML_Util::createEndElement($cc_type);
if ((isset($data['shopperIPAddress']) || isset($data['sessionId']))
&& ($data['shopperIPAddress'] != '' || $data['sessionId'] != '')) {
$t = array();
if ($data['shopperIPAddress'] != '') {
$t['shopperIPAddress'] = $data['shopperIPAddress'];
}
if ($data['sessionId'] != '') {
$t['id'] = $data['sessionId'];
}
$doc .= XML_Util::createTag('session', $t);
unset($t);
}
$doc .= XML_Util::createEndElement('paymentDetails');
}
if ((isset($data['shopperEmailAddress']) && $data['shopperEmailAddress'] != '')
|| (isset($data['authenticatedShopperID']) && $data['authenticatedShopperID'] != '')) {
$doc .= XML_Util::createStartElement('shopper');
if ($data['shopperEmailAddress'] != '') {
$doc .= XML_Util::createTag('shopperEmailAddress', null, $data['shopperEmailAddress']);
}
if ($data['authenticatedShopperID'] != '') {
$doc .= XML_Util::createTag('authenticatedShopperID', null, $data['authenticatedShopperID']);
}
$doc .= XML_Util::createEndElement('shopper');
}
if (is_array($data['shippingAddress']) && count($data['shippingAddress']) > 0) {
$a = $data['shippingAddress'];
$doc .= XML_Util::createStartElement('shippingAddress');
$doc .= XML_Util::createStartElement('address');
$fields = array('firstName', 'lastName', 'street',
'houseName', 'houseNumber', 'houseNumberExtension',
'postalCode', 'city', 'state',
'countryCode', 'telephoneNumber');
foreach($fields as $field) {
if (isset($a[$field])) {
$doc .= XML_Util::createTag($field, null, $a[$field]);
}
}
$doc .= XML_Util::createEndElement('address');
$doc .= XML_Util::createEndElement('shippingAddress');
}
$doc .= XML_Util::createEndElement('order');
$doc .= XML_Util::createEndElement('submit');
}
$doc .= XML_Util::createEndElement('paymentService');
$doc1 = domxml_open_mem($doc);
return $doc;
}
/**
* Prepare the ordercontent
*
* Docs says max size is 10k
*
* @access private
*/
function _handleOrdercontent()
{
$specific = $this->_fieldMap['ordercontent'];
if ($this->ordercontent != '') {
$this->_data[$specific] = substr($this->ordercontent, 0, 10240);
}
}
/**
* Validate the merchant account login.
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validateLogin()
{
return Validate::string($this->login, array(
'format' => VALIDATE_ALPHA_UPPER,
'min_length' => 1
));
}
/**
* Validate the merchant account password.
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validatePassword()
{
return Validate::string($this->password, array(
'min_length' => 1
));
}
/**
* Validates the ordercode
*
* Docs says up to 64 characters, no spaces or specials characters allowed
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validateOrdercode()
{
return Validate::string($this->ordercode, array(
'min_length' => 1,
'max_length' => 64
));
}
/**
* Validate the order description.
*
* Docs says maximum length is 50 characters...
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validateDescription()
{
return Validate::string($this->description, array(
'min_length' => 1,
'max_length' => 50,
));
}
/**
* Validate the order amount.
*
* Should contain no digits, as those are set with the exponent option.
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validateAmount()
{
return Validate::number($this->amount, array(
'decimal' => false
));
}
/** Validate the order amount currency
*
* The abbrivation for a currency, usually 2-3 chars
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validateCurrency()
{
return Validate::string($this->currency, array(
'format' => VALIDATE_ALPHA_UPPER,
'min_length' => 2,
'max_length' => 3
));
}
/** Validate the exponent of the order amount
*
* Occording to the dtd, valid is 0, 2 or 3
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validateExponent()
{
switch ($this->exponent)
{
case 0:
case 2:
case 3:
return true;
default:
return false;
}
}
}
/**
* Payment_Process_Bibit_Result
*
*
* @package Payment_Process
* @author Robin Ericsson <lobbin@localhost.nu>
* @version @version@
*/
class Payment_Process_Result_Bibit extends Payment_Process_Result
{
var $_returnCode = PAYMENT_PROCESS_RESULT_DECLINED;
var $_lastEvent = NULL;
var $_fieldMap = array(
);
function __construct($rawResponse)
{
$this->_rawResponse = $rawResponse;
}
function getErrorCode()
{
return $this->_errorCode;
}
function getCode()
{
return $this->_returnCode;
}
function parse()
{
$doc = new XML_XPath();
$e = $doc->load($this->_rawResponse, 'string');
if (PEAR::isError($e)) {
$this->_returnCode = PAYMENT_PROCESS_RESULT_OTHER;
$this->message = 'Error parsing reply: '.$e->getMessage()."\n";
return;
}
$e = $doc->evaluate('//reply/error/attribute::code');
if (!PEAR::isError($e) && $e->next()) {
$this->_returnCode = PAYMENT_PROCESS_RESULT_OTHER;
$this->_errorCode = $e->getData();
$e = $doc->evaluate('//reply/error/text()');
$this->message = $e->getData();
return;
}
$orderType = $this->_request->_data['x_action'];
switch ($orderType) {
case PAYMENT_PROCESS_ACTION_BIBIT_AUTH:
$e = $doc->evaluate('//reply/orderStatus/payment/lastEvent/text()');
if (!PEAR::isError($e) && $e->next()) {
$this->_lastEvent = $e->getData();
}
$amount = $doc->evaluate('//reply/orderStatus/payment/amount/attribute::value');
if (!PEAR::isError($amount) && $amount->next()) {
if ($this->_lastEvent == 'AUTHORISED') {
$this->_returnCode = PAYMENT_PROCESS_RESULT_APPROVED;
$this->message = '';
return;
}
}
break;
case PAYMENT_PROCESS_ACTION_BIBIT_CAPTURE:
$amount = $doc->evaluate('//reply/ok/captureReceived/amount/attribute::value');
if (!PEAR::isError($amount) && $amount->next()) {
$this->_returnCode = PAYMENT_PROCESS_RESULT_APPROVED;
return;
}
break;
case PAYMENT_PROCESS_ACTION_BIBIT_REFUND:
$amount = $doc->evaluate('//reply/ok/refundReceived/amount/attribute::value');
if (!PEAR::isError($amount) && $amount->next()) {
$this->_returnCode = PAYMENT_PROCESS_RESULT_APPROVED;
return;
}
break;
}
}
}
?>

@ -0,0 +1,610 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
/**
* Holds code shared between all processors
*
* PHP versions 4 and 5
*
* LICENSE: This source file is subject to version 3.0 of the PHP license
* that is available through the world-wide-web at the following URI:
* http://www.php.net/license/3_0.txt. If you did not receive a copy of
* the PHP License and are unable to obtain it through the web, please
* send a note to license@php.net so we can mail you a copy immediately.
*
* @category Payment
* @package Payment_Process
* @author Ian Eure <ieure@php.net>
* @author Joe Stump <joe@joestump.net>
* @copyright 1997-2005 The PHP Group
* @license http://www.php.net/license/3_0.txt PHP License 3.0
* @version CVS: $Id: Common.php,v 1.32 2005/12/13 00:00:29 jstump Exp $
* @link http://pear.php.net/package/Payment_Process
*/
require_once('Payment/Process.php');
require_once('Payment/Process/Type.php');
class Payment_Process_Common {
// {{{ Private Properties
/**
* Options.
*
* @var array
* @see setOptions()
* @access private;
*/
var $_options = '';
/**
* Array of fields which are required.
*
* @var array
* @access private
* @see _makeRequired()
*/
var $_required = array();
/**
* Processor-specific data.
*
* @access private
* @var array
*/
var $_data = array();
/**
* $_driver
*
* @author Joe Stump <joe@joestump.net>
* @var string $_driver
* @access private
*/
var $_driver = null;
/**
* PEAR::Log instance
*
* @var object
* @access protected
* @see Log
*/
var $_log;
/**
* Mapping between API fields and processors'
*
* @var mixed $_typeFieldMap
* @access protected
*/
var $_typeFieldMap = array();
/**
* Reference to payment type
*
* An internal reference to the Payment_Process_Type that is currently
* being processed.
*
* @var mixed $_payment Instance of Payment_Type
* @access protected
* @see Payment_Process_Common::setPayment()
*/
var $_payment = null;
// }}}
// {{{ Public Properties
/**
* Your login name to use for authentication to the online processor.
*
* @var string
*/
var $login = '';
/**
* Your password to use for authentication to the online processor.
*
* @var string
*/
var $password = '';
/**
* Processing action.
*
* This should be set to one of the PAYMENT_PROCESS_ACTION_* constants.
*
* @var int
*/
var $action = '';
/**
* A description of the transaction (used by some processors to send
* information to the client, normally not a required field).
* @var string
*/
var $description = '';
/**
* The transaction amount.
*
* @var double
*/
var $amount = 0;
/**
* An invoice number.
*
* @var mixed string or int
*/
var $invoiceNumber = '';
/**
* Customer identifier
*
* @var mixed string or int
*/
var $customerId = '';
/**
* Transaction source.
*
* This should be set to one of the PAYMENT_PROCESS_SOURCE_* constants.
*
* @var int
*/
var $transactionSource;
// }}}
// {{{ __construct($options = false)
/**
* __construct
*
* PHP 5.x constructor
*
* @author Joe Stump <joe@joestump.net>
* @access public
*/
function __construct($options = false)
{
$this->setOptions($options);
}
// }}}
// {{{ setPayment(&$payment)
/**
* Sets payment
*
* Returns false if payment could not be set. This usually means the
* payment type is not valid or that the payment type is valid, but did
* not validate. It could also mean that the payment type is not supported
* by the given processor.
*
* @param mixed $payment Object of Payment_Process_Type
* @return bool
* @access public
* @author Joe Stump <joe@joestump.net>
*/
function setPayment(&$payment)
{
if (isset($this->_typeFieldMap[$payment->getType()]) &&
is_array($this->_typeFieldMap[$payment->getType()]) &&
count($this->_typeFieldMap[$payment->getType()])) {
$result = Payment_Process_Type::isValid($payment);
if (PEAR::isError($result)) {
return $result;
}
$this->_payment = $payment;
// Map over the payment specific fields. Check out
// $_typeFieldMap for more information.
$paymentType = $payment->getType();
foreach ($this->_typeFieldMap[$paymentType] as $generic => $specific) {
$func = '_handle'.ucfirst($generic);
if (method_exists($this, $func)) {
$result = $this->$func();
if (PEAR::isError($result)) {
return $result;
}
} else {
// TODO This may screw things up - the problem is that
// CC information is no longer member variables, so we
// can't overwrite it. You could always handle this
// with a _handle funciton. I don't think it will cause
// problems, but it could.
if (!isset($this->_data[$specific])) {
$this->_data[$specific] = $this->_payment->$generic;
}
}
}
return true;
}
return PEAR::raiseError('Invalid type field map');
}
// }}}
// {{{ setFrom($where)
/**
* Set many fields.
*
* @param array $where Associative array of data to set, in the format
* 'field' => 'value',
* @return void
*/
function setFrom($where)
{
foreach ($this->getFields() as $field) {
if (isset($where[$field])) {
$this->$field = $where[$field];
}
}
}
// }}}
// {{{ process()
/**
* Processes the transaction.
*
* This function should be overloaded by the processor.
*/
function process()
{
return PEAR::raiseError("process() is not implemented in this processor.", PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED);
}
// }}}
// {{{ &processCallback()
/**
* processCallback
*
* This should be overridden in driver classes. It will be used to process
* communications from gateways to your application. For instance, the
* Authorize.net gateway will post information about pending transactions
* to a URL you specify. This function should handle such requests
*
* @return object Payment_Process_Result on success, PEAR_Error on failure
*/
function &processCallback()
{
return PEAR::raiseError('processCallback() not implemented',
PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED);
}
// }}}
// {{{ validate()
/**
* validate
*
* Validates data before processing. This function may be overloaded by
* the processor.
*
* @return boolean true if validation succeeded, PEAR_Error if it failed.
*/
function validate()
{
foreach ($this->getFields() as $field) {
$func = '_validate'.ucfirst($field);
// Don't validate unset optional fields
if (! $this->isRequired($field) && !strlen($this->$field)) {
continue;
}
if (method_exists($this, $func)) {
$res = $this->$func();
if (PEAR::isError($res)) {
return $res;
} elseif (is_bool($res) && $res == false) {
return PEAR::raiseError('Validation of field "'.$field.'" failed.', PAYMENT_PROCESS_ERROR_INVALID);
}
}
}
return true;
}
// }}}
// {{{ set($field, $value)
/**
* Set a value.
*
* This will set a value, such as the credit card number. If the requested
* field is not part of the basic set of supported fields, it is set in
* $_options.
*
* @param string $field The field to set
* @param string $value The value to set
* @return void
*/
function set($field, $value)
{
if (!$this->fieldExists($field)) {
return PEAR::raiseError('Field "' . $field . '" does not exist.', PAYMENT_PROCESS_ERROR_INVALID);
}
$this->$field = $value;
return true;
}
// }}}
// {{{ isRequired($field)
/**
* Determine if a field is required.
*
* @param string $field Field to check
* @return boolean true if required, false if optional.
*/
function isRequired($field)
{
return (isset($this->_required[$field]));
}
// }}}
// {{{ fieldExists($field)
/**
* Determines if a field exists.
*
* @author Ian Eure <ieure@php.net>
* @param string $field Field to check
* @return boolean true if field exists, false otherwise
*/
function fieldExists($field)
{
return @in_array($field, $this->getFields());
}
// }}}
// {{{ getFields()
/**
* Get a list of fields.
*
* This function returns an array containing all the possible fields which
* may be set.
*
* @author Ian Eure <ieure@php.net>
* @access public
* @return array Array of valid fields.
*/
function getFields()
{
$vars = array_keys(get_class_vars(get_class($this)));
foreach ($vars as $idx => $field) {
if ($field[0] == '_') {
unset($vars[$idx]);
}
}
return $vars;
}
// }}}
// {{{ setOptions($options = false, $defaultOptions = false)
/**
* Set class options.
*
* @author Ian Eure <ieure@php.net>
* @param Array $options Options to set
* @param Array $defaultOptions Default options
* @return void
*/
function setOptions($options = false, $defaultOptions = false)
{
$defaultOptions = $defaultOptions ? $defaultOptions : $this->_defaultOptions; $this->_options = @array_merge($defaultOptions, $options);
}
// }}}
// {{{ getOption($option)
/**
* Get an option value.
*
* @author Ian Eure <ieure@php.net>
* @param string $option Option to get
* @return mixed Option value
*/
function getOption($option)
{
return @$this->_options[$option];
}
// }}}
// {{{ setOption($option,$value)
/**
* Set an option value
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @param string $option Option name to set
* @param mixed $value Value to set
*/
function setOption($option,$value)
{
return ($this->_options[$option] = $value);
}
// }}}
// {{{ getResult()
/**
* Gets transaction result.
*
* This function should be overloaded by the processor.
*/
function getResult()
{
return PEAR::raiseError("getResult() is not implemented in this processor.", PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED);
}
// }}}
// {{{ _isDefinedConstant($value, $class)
/**
* See if a value is a defined constant.
*
* This function checks to see if $value is defined in one of
* PAYMENT_PROCESS_{$class}_*. It's used to verify that e.g.
* $object->action is one of PAYMENT_PROCESS_ACTION_NORMAL,
* PAYMENT_PROCESS_ACTION_AUTHONLY etc.
*
* @access private
* @param mixed $value Value to check
* @param mixed $class Constant class to check
* @return boolean true if it is defined, false otherwise.
*/
function _isDefinedConst($value, $class)
{
$constClass = 'PAYMENT_PROCESS_'.strtoupper($class).'_';
$length = strlen($constClass);
$consts = get_defined_constants();
$found = false;
foreach ($consts as $constant => $constVal) {
if (strncmp($constClass, $constant, $length) === 0 &&
$constVal == $value) {
$found = true;
break;
}
}
return $found;
}
// }}}
// {{{ _makeRequired()
/**
* Mark a field (or fields) as being required.
*
* @param string $field Field name
* @param string ...
* @return boolean always true.
*/
function _makeRequired()
{
foreach (func_get_args() as $field) {
$this->_required[$field] = true;
}
return true;
}
// }}}
// {{{ _makeOptional()
/**
* Mark a field as being optional.
*
* @param string $field Field name
* @param ...
* @return boolean always true.
*/
function _makeOptional()
{
foreach (func_get_args() as $field) {
unset($this->_required[$field]);
}
return true;
}
// }}}
// {{{ _validateType()
/**
* Validates transaction type.
*
* @return boolean true on success, false on failure.
* @access private
*/
function _validateType()
{
return $this->_isDefinedConst($this->type, 'type');
}
// }}}
// {{{ _validateAction()
/**
* Validates transaction action.
*
* @return boolean true on success, false on failure.
* @access private
*/
function _validateAction()
{
return (isset($GLOBALS['_Payment_Process_'.$this->_driver][$this->action]));
}
// }}}
// {{{ _validateSource()
/**
* Validates transaction source.
*
* @return boolean true on success, false on failure.
* @access private
*/
function _validateSource()
{
return $this->_isDefinedConst($this->transactionSource, 'source');
}
// }}}
// {{{ _validateAmount()
/**
* Validates the charge amount.
*
* Charge amount must be 8 characters long, double-precision.
* Current min/max are rather arbitrarily set to $0.99 and $99999.99,
* respectively.
*
* @return boolean true on success, false otherwise
*/
function _validateAmount()
{
return Validate::number($this->amount, array(
'decimal' => '.',
'dec_prec' => 2,
'min' => 0.99,
'max' => 99999.99
));
}
// }}}
// {{{ _handleAction()
/**
* Handles action
*
* Actions are defined in $GLOBALS['_Payment_Process_DriverName'] and then
* handled here. We may decide to abstract the defines in the driver.
*
* @access private
*/
function _handleAction()
{
$this->_data[$this->_fieldMap['action']] = $GLOBALS['_Payment_Process_'.$this->_driver][$this->action];
}
// }}}
// {{{ _prepare()
/**
* Prepares the POST data.
*
* This function handles translating the data set in the front-end to the
* format needed by the back-end. The prepared data is stored in
* $this->_data. If a '_handleField' method exists in this class (e.g.
* '_handleCardNumber()'), that function is called and /must/ set
* $this->_data correctly. If no field-handler function exists, the data
* from the front-end is mapped into $_data using $this->_fieldMap.
*
* @return array Data to POST
* @access private
*/
function _prepare()
{
/*
* FIXME - because this only loops through stuff in the fieldMap, we
* can't have handlers for stuff which isn't specified in there.
* But the whole point of having a _handler() is that you need
* to do something more than simple mapping.
*/
foreach ($this->_fieldMap as $generic => $specific) {
$func = '_handle'.ucfirst($generic);
if (method_exists($this, $func)) {
$result = $this->$func();
if (PEAR::isError($result)) {
return $result;
}
} else {
// TODO This may screw things up - the problem is that
// CC information is no longer member variables, so we
// can't overwrite it. You could always handle this with
// a _handle funciton. I don't think it will cause problems,
// but it could.
if (!isset($this->_data[$specific])) {
if (isset($this->$generic)) {
$this->_data[$specific] = $this->$generic;
}
// Form of payments data overrides those set in the
// Payment_Process_Common.
if (isset($this->_payment->$generic)) {
$this->_data[$specific] = $this->_payment->$generic;
}
}
}
}
return true;
}
// }}}
}
?>

@ -0,0 +1,94 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2003 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Ian Eure <ieure@php.net> |
// +----------------------------------------------------------------------+
//
// $Id: Dummy.php,v 1.6 2004/03/22 20:35:58 ieure Exp $
require_once 'Payment/Process/Common.php';
/**
* Payment_PAYMENT_PROCESS_Dummy
*
* A dummy processor for offline testing. It can be made to return different
* result codes and messages for testing purposes.
*
* @package Payment_Process
* @category Payment
* @author Ian Eure <ieure@php.net>
* @version @version@
*/
class Payment_Process_Dummy extends Payment_Process_Common {
/**
* Default options for this class.
*
* @access private
* @type array
* @see Payment_Process::setOptions()
*/
var $_defaultOptions = array(
'randomResult' => true,
'returnCode' => PAYMENT_PROCESS_RESULT_APPROVED,
'returnMessage' => "Dummy payment approved"
);
var $_returnValues = array(
array(
'code' => PAYMENT_PROCESS_RESULT_APPROVED,
'message' => "Approved"
),
array(
'code' => PAYMENT_PROCESS_RESULT_DECLINED,
'message' => "Declined"
),
array(
'code' => PAYMENT_PROCESS_RESULT_OTHER,
'message' => "System error"
)
);
/**
* Process the (dummy) transaction
*
* @return mixed Payment_Process_Result instance or PEAR_Error
*/
function &process()
{
// Sanity check
if (PEAR::isError($res = $this->validate())) {
return($res);
}
if ($this->_options['randomResult']) {
srand(microtime());
$n = rand(0, count($this->_returnValues) - 1);
$code = &$this->_returnValues[$n]['code'];
$message = &$this->_returnValues[$n]['message'];
} else {
$code = &$this->_options['returnCode'];
$message = &$this->_options['returnMessage'];
}
return Payment_Process_Result::factory('Dummy');
}
}
class Payment_Process_Result_Dummy extends Payment_Process_Result {
function __construct()
{
}
}
?>

@ -0,0 +1,516 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
/**
* LinkPoint processor
*
* PHP versions 4 and 5
*
* LICENSE: This source file is subject to version 3.0 of the PHP license
* that is available through the world-wide-web at the following URI:
* http://www.php.net/license/3_0.txt. If you did not receive a copy of
* the PHP License and are unable to obtain it through the web, please
* send a note to license@php.net so we can mail you a copy immediately.
*
* @category Payment
* @package Payment_Process
* @author Joe Stump <joe@joestump.net>
* @copyright 1997-2005 The PHP Group
* @license http://www.php.net/license/3_0.txt PHP License 3.0
* @version CVS: $Revision: 1.13 $
* @link http://pear.php.net/package/Payment_Process
* @link http://www.linkpoint.net/
*/
require_once('Payment/Process.php');
require_once('Payment/Process/Common.php');
require_once('Net/Curl.php');
require_once('XML/Parser.php');
$GLOBALS['_Payment_Process_LinkPoint'] = array(
PAYMENT_PROCESS_ACTION_NORMAL => 'SALE',
PAYMENT_PROCESS_ACTION_AUTHONLY => 'PREAUTH',
PAYMENT_PROCESS_ACTION_POSTAUTH => 'POSTAUTH'
);
/**
* Payment_Process_LinkPoint
*
* This is a processor for LinkPoint's merchant payment gateway.
* (http://www.linkpoint.net/)
*
* *** WARNING ***
* This is BETA code, and has not been fully tested. It is not recommended
* that you use it in a production envorinment without further testing.
*
* @package Payment_Process
* @author Joe Stump <joe@joestump.net>
* @version @version@
*/
class Payment_Process_LinkPoint extends Payment_Process_Common
{
/**
* Front-end -> back-end field map.
*
* This array contains the mapping from front-end fields (defined in
* the Payment_Process class) to the field names DPILink requires.
*
* @see _prepare()
* @access private
*/
var $_fieldMap = array(
// Required
'login' => 'configfile',
'action' => 'ordertype',
'invoiceNumber' => 'oid',
'customerId' => 'x_cust_id',
'amount' => 'chargetotal',
'name' => '',
'zip' => 'zip',
// Optional
'company' => 'company',
'address' => 'address1',
'city' => 'city',
'state' => 'state',
'country' => 'country',
'phone' => 'phone',
'email' => 'email',
'ip' => 'ip',
);
/**
* $_typeFieldMap
*
* @author Joe Stump <joe@joestump.net>
* @access protected
*/
var $_typeFieldMap = array(
'CreditCard' => array(
'cardNumber' => 'cardnumber',
'cvv' => 'cvm',
'expDate' => 'expDate'
),
'eCheck' => array(
'routingCode' => 'routing',
'accountNumber' => 'account',
'type' => 'type',
'bankName' => 'bank',
'name' => 'name',
'driversLicense' => 'dl',
'driversLicenseState' => 'dlstate'
)
);
/**
* Default options for this processor.
*
* @see Payment_Process::setOptions()
* @access private
*/
var $_defaultOptions = array(
'host' => 'secure.linkpt.net',
'port' => '1129',
'result' => 'LIVE'
);
/**
* Has the transaction been processed?
*
* @type boolean
* @access private
*/
var $_processed = false;
/**
* The response body sent back from the gateway.
*
* @access private
*/
var $_responseBody = '';
/**
* Constructor.
*
* @param array $options Class options to set.
* @see Payment_Process::setOptions()
* @return void
*/
function __construct($options = false)
{
parent::__construct($options);
$this->_driver = 'LinkPoint';
}
/**
* Process the transaction.
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
*/
function &process()
{
if (!strlen($this->_options['keyfile']) ||
!file_exists($this->_options['keyfile'])) {
return PEAR::raiseError('Invalid key file');
}
// Sanity check
$result = $this->validate();
if (PEAR::isError($result)) {
return $result;
}
// Prepare the data
$result = $this->_prepare();
if (PEAR::isError($result)) {
return $result;
}
// Don't die partway through
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
$xml = $this->_prepareQueryString();
if (PEAR::isError($xml)) {
return $xml;
}
$url = 'https://'.$this->_options['host'].':'.$this->_options['port'].
'/LSGSXML';
$curl = new Net_Curl($url);
$result = $curl->create();
if (PEAR::isError($result)) {
return $result;
}
$curl->type = 'POST';
$curl->fields = $xml;
$curl->sslCert = $this->_options['keyfile'];
// LinkPoint's staging server has a boned certificate. If they are
// testing against staging we need to turn off SSL host verification.
if ($this->_options['host'] == 'staging.linkpt.net') {
$curl->verifyPeer = false;
$curl->verifyHost = 0;
}
$curl->userAgent = 'PEAR Payment_Process_LinkPoint 0.1';
$result = &$curl->execute();
if (PEAR::isError($result)) {
return PEAR::raiseError('cURL error: '.$result->getMessage());
} else {
$curl->close();
}
$this->_responseBody = trim($result);
$this->_processed = true;
// Restore error handling
PEAR::popErrorHandling();
$response = &Payment_Process_Result::factory($this->_driver,
$this->_responseBody,
$this);
if (!PEAR::isError($response)) {
$response->parse();
}
return $response;
}
/**
* Prepare the POST query string.
*
* @access private
* @return string The query string
*/
function _prepareQueryString()
{
$data = array_merge($this->_options,$this->_data);
$xml = '<!-- Payment_Process order -->'."\n";
$xml .= '<order>'."\n";
$xml .= '<merchantinfo>'."\n";
$xml .= ' <configfile>'.$data['configfile'].'</configfile>'."\n";
$xml .= ' <keyfile>'.$data['keyfile'].'</keyfile>'."\n";
$xml .= ' <host>'.$data['authorizeUri'].'</host>'."\n";
$xml .= ' <appname>PEAR Payment_Process</appname>'."\n";
$xml .= '</merchantinfo>'."\n";
$xml .= '<orderoptions>'."\n";
$xml .= ' <ordertype>'.$data['ordertype'].'</ordertype>'."\n";
$xml .= ' <result>'.$data['result'].'</result>'."\n";
$xml .= '</orderoptions>'."\n";
$xml .= '<payment>'."\n";
$xml .= ' <subtotal>'.$data['chargetotal'].'</subtotal>'."\n";
$xml .= ' <tax>0.00</tax>'."\n";
$xml .= ' <shipping>0.00</shipping>'."\n";
$xml .= ' <chargetotal>'.$data['chargetotal'].'</chargetotal>'."\n";
$xml .= '</payment>'."\n";
// Set payment method to eCheck if our payment type is eCheck.
// Default is Credit Card.
$data['x_method'] = 'CC';
switch ($this->_payment->getType())
{
case 'eCheck':
return PEAR::raiseError('eCheck not currently supported',
PAYMENT_PROCESS_ERROR_NOTIMPLEMENTED);
$xml .= '<telecheck>'."\n";
$xml .= ' <routing></routing>'."\n";
$xml .= ' <account></account>'."\n";
$xml .= ' <checknumber></checknumber>'."\n";
$xml .= ' <bankname></bankname>'."\n";
$xml .= ' <bankstate></bankstate>'."\n";
$xml .= ' <dl></dl>'."\n";
$xml .= ' <dlstate></dlstate>'."\n";
$xml .= ' <accounttype>pc|ps|bc|bs</accounttype>'."\n";
$xml .= '<telecheck>'."\n";
break;
case 'CreditCard':
$xml .= '<creditcard>'."\n";
$xml .= ' <cardnumber>'.$data['cardnumber'].'</cardnumber>'."\n";
list($month,$year) = explode('/',$data['expDate']);
if (strlen($year) == 4) {
$year = substr($year,2);
}
$month = sprintf('%02d',$month);
$xml .= ' <cardexpmonth>'.$month.'</cardexpmonth>'."\n";
$xml .= ' <cardexpyear>'.$year.'</cardexpyear>'."\n";
if (strlen($data['cvm'])) {
$xml .= ' <cvmvalue>'.$data['cvm'].'</cvmvalue>'."\n";
$xml .= ' <cvmindicator>provided</cvmindicator>'."\n";
}
$xml .= '</creditcard>'."\n";
}
if (isset($this->_payment->firstName) &&
isset($this->_payment->lastName)) {
$xml .= '<billing>'."\n";
$xml .= ' <userid>'.$this->_payment->customerId.'</userid>'."\n";
$xml .= ' <name>'.$this->_payment->firstName.' '.$this->_payment->lastName.'</name>'."\n";
$xml .= ' <company>'.$this->_payment->company.'</company>'."\n";
$xml .= ' <address1>'.$this->_payment->address.'</address1>'."\n";
$xml .= ' <city>'.$this->_payment->city.'</city>'."\n";
$xml .= ' <state>'.$this->_payment->state.'</state>'."\n";
$xml .= ' <zip>'.$this->_payment->zip.'</zip>'."\n";
$xml .= ' <country>'.$this->_payment->country.'</country>'."\n";
$xml .= ' <phone>'.$this->_payment->phone.'</phone>'."\n";
$xml .= ' <email>'.$this->_payment->email.'</email>'."\n";
$xml .= ' <addrnum>'.$this->_payment->address.'</addrnum>'."\n";
$xml .= '</billing>'."\n";
}
$xml .= '</order>'."\n";
return $xml;
}
}
/**
* Payment_Process_Result_LinkPoint
*
* LinkPoint result class
*
* @author Joe Stump <joe@joestump.net>
* @package Payment_Process
*/
class Payment_Process_Result_LinkPoint extends Payment_Process_Result
{
var $_statusCodeMap = array('APPROVED' => PAYMENT_PROCESS_RESULT_APPROVED,
'DECLINED' => PAYMENT_PROCESS_RESULT_DECLINED,
'FRAUD' => PAYMENT_PROCESS_RESULT_FRAUD);
/**
* LinkPoint status codes
*
* This array holds many of the common response codes. There are over 200
* response codes - so check the LinkPoint manual if you get a status
* code that does not match (see "Response Reason Codes & Response
* Reason Text" in the AIM manual).
*
* @see getStatusText()
* @access private
*/
var $_statusCodeMessages = array(
'APPROVED' => 'This transaction has been approved.',
'DECLINED' => 'This transaction has been declined.',
'FRAUD' => 'This transaction has been determined to be fraud.');
var $_avsCodeMap = array(
'YY' => PAYMENT_PROCESS_AVS_MATCH,
'YN' => PAYMENT_PROCESS_AVS_MISMATCH,
'YX' => PAYMENT_PROCESS_AVS_ERROR,
'NY' => PAYMENT_PROCESS_AVS_MISMATCH,
'XY' => PAYMENT_PROCESS_AVS_MISMATCH,
'NN' => PAYMENT_PROCESS_AVS_MISMATCH,
'NX' => PAYMENT_PROCESS_AVS_MISMATCH,
'XN' => PAYMENT_PROCESS_AVS_MISMATCH,
'XX' => PAYMENT_PROCESS_AVS_ERROR
);
var $_avsCodeMessages = array(
'YY' => 'Address matches, zip code matches',
'YN' => 'Address matches, zip code does not match',
'YX' => 'Address matches, zip code comparison not available',
'NY' => 'Address does not match, zip code matches',
'XY' => 'Address comparison not available, zip code matches',
'NN' => 'Address comparison does not match, zip code does not match',
'NX' => 'Address does not match, zip code comparison not available',
'XN' => 'Address comparison not available, zip code does not match',
'XX' => 'Address comparison not available, zip code comparison not available'
);
var $_cvvCodeMap = array('M' => PAYMENT_PROCESS_CVV_MATCH,
'N' => PAYMENT_PROCESS_CVV_MISMATCH,
'P' => PAYMENT_PROCESS_CVV_ERROR,
'S' => PAYMENT_PROCESS_CVV_ERROR,
'U' => PAYMENT_PROCESS_CVV_ERROR,
'X' => PAYMENT_PROCESS_CVV_ERROR
);
var $_cvvCodeMessages = array(
'M' => 'Card Code Match',
'N' => 'Card code does not match',
'P' => 'Not processed',
'S' => 'Merchant has indicated that the card code is not present on the card',
'U' => 'Issuer is not certified and/or has not proivded encryption keys',
'X' => 'No response from the credit card association was received'
);
var $_fieldMap = array('r_approved' => 'code',
'r_error' => 'message',
'r_code' => 'approvalCode',
'r_ordernum' => 'transactionId'
);
function Payment_Process_Response_LinkPoint($rawResponse)
{
$this->Payment_Process_Response($rawResponse);
}
/**
* parse
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @return void
*/
function parse()
{
$xml = new Payment_Processor_LinkPoint_XML_Parser();
$xml->parseString('<response>'.$this->_rawResponse.'</response>');
if (is_array($xml->response) && count($xml->response)) {
$this->avsCode = substr($xml->response['r_avs'],0,2);
$this->cvvCode = substr($xml->response['r_avs'],2,1);
$this->customerId = $this->_request->customerId;
$this->invoiceNumber = $this->_request->invoiceNumber;
$this->_mapFields($xml->response);
// switch to DECLINED since a duplicate isn't *really* fraud
if(eregi('duplicate',$this->message)) {
$this->messageCode = 'DECLINED';
}
}
}
}
/**
* Payment_Processor_LinkPoint_XML_Parser
*
* XML Parser for the LinkPoint response
*
* @author Joe Stump <joe@joestump.net>
* @package Payment_Process
*/
class Payment_Processor_LinkPoint_XML_Parser extends XML_Parser
{
/**
* $response
*
* @var array $response Raw response as an array
* @access public
*/
var $response = array();
/**
* $log
*
* @var string $tag Current tag
* @access private
*/
var $tag = null;
/**
* Payment_Processor_LinkPoint_XML_Parser
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @return void
* @see XML_Parser
*/
function __construct()
{
$this->XML_Parser();
}
/**
* startHandler
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @param resource $xp XML processor handler
* @param string $elem Name of XML entity
* @return void
*/
function startHandler($xp, $elem, &$attribs)
{
$this->tag = $elem;
}
/**
* endHandler
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @param resource $xp XML processor handler
* @param string $elem Name of XML entity
* @return void
*/
function endHandler($xp, $elem)
{
}
/**
* defaultHandler
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @param resource $xp XML processor handler
* @param string $data
* @return void
*/
function defaultHandler($xp,$data)
{
$this->response[strtolower($this->tag)] = $data;
}
}
?>

@ -0,0 +1,590 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2003 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Ian Eure <ieure@php.net> |
// +----------------------------------------------------------------------+
//
// $Id: Transfirst.php,v 1.3 2005/07/14 20:54:00 ieure Exp $
require_once('Payment/Process/Common.php');
require_once('Net/Curl.php');
// Transfirst transaction types
// Request authorization only - no funds are transferred.
define('PAYMENT_PROCESS_ACTION_TRANSFIRST_AUTH', 30);
// Transfer funds from a previous authorization.
define('PAYMENT_PROCESS_ACTION_TRANSFIRST_SETTLE', 40);
// Authorize & transfer funds
define('PAYMENT_PROCESS_ACTION_TRANSFIRST_AUTHSETTLE', 32);
// Debit the indicated amount to a previously-charged card.
define('PAYMENT_PROCESS_ACTION_TRANSFIRST_CREDIT', 20);
// Cancel authorization
define('PAYMENT_PROCESS_ACTION_TRANSFIRST_VOID', 61);
define('PAYMENT_PROCESS_RESULT_TRANSFIRST_APPROVAL', 00);
define('PAYMENT_PROCESS_RESULT_TRANSFIRST_DECLINE', 05);
define('PAYMENT_PROCESS_RESULT_TRANSFIRST_INVALIDAMOUNT', 13);
define('PAYMENT_PROCESS_RESULT_TRANSFIRST_INVALIDCARDNO', 14);
define('PAYMENT_PROCESS_RESULT_TRANSFIRST_REENTER', 19);
// Map actions
$GLOBALS['_Payment_Process_Transfirst'] = array(
PAYMENT_PROCESS_ACTION_NORMAL => PAYMENT_PROCESS_ACTION_TRANSFIRST_AUTHSETTLE,
PAYMENT_PROCESS_ACTION_AUTHONLY => PAYMENT_PROCESS_ACTION_TRANSFIRST_AUTH,
PAYMENT_PROCESS_ACTION_POSTAUTH => PAYMENT_PROCESS_ACTION_TRANSFIRST_SETTLE
);
/**
* Payment_Process_Transfirst
*
* This is a processor for TransFirst's merchant payment gateway, formerly known
* as DPILink. (http://www.transfirst.com/)
*
* *** WARNING ***
* This is BETA code. While I have tested it and it appears to work for me, I
* strongly recommend that you do additional testing before using it in
* production systems.
*
* @package Payment_Process
* @author Ian Eure <ieure@php.net>
* @version @version@
*/
class Payment_Process_Transfirst extends Payment_Process_Common {
/**
* Front-end -> back-end field map.
*
* This array contains the mapping from front-end fields (defined in
* the Payment_Process class) to the field names Transfirst requires.
*
* @see _prepare()
* @access private
*/
var $_fieldMap = array(
// Required
'login' => "DPIAccountNum",
'password' => "password",
'action' => "transactionCode",
'invoiceNumber' => "orderNum",
'customerId' => "customerNum",
'amount' => "transactionAmount",
'transactionSource' => "ECommerce",
// Credit Card Type
'cardNumber' => "cardAccountNum",
'expDate' => "expirationDate",
'zip' => "cardHolderZip",
// Common Type
// 'name' => "cardHolderName",
'address' => "cardHolderAddress",
'city' => "cardHolderCity",
'state' => "cardHolderState",
'phone' => "cardHolderPhone",
'email' => "cardHolderEmail"
);
/**
* Default options for this processor.
*
* @see Payment_Process::setOptions()
* @access private
*/
var $_defaultOptions = array(
'authorizeUri' => "https://epaysecure.transfirst.com/eLink/authpd.asp"
);
/**
* Has the transaction been processed?
*
* @type boolean
* @access private
*/
var $_processed = false;
/**
* The response body sent back from the gateway.
*
* @access private
*/
var $_responseBody = '';
/**
* Constructor.
*
* @param array $options Class options to set.
* @see Payment_Process::setOptions()
* @return void
*/
function __construct($options = false)
{
parent::__construct($options);
$this->_driver = 'Transfirst';
$this->_makeRequired('login', 'password', 'action', 'invoiceNumber', 'customerId', 'amount', 'cardNumber', 'expDate');
}
/**
* Prepare the data.
*
* This function handles the 'testTransaction' option, which is specific to
* this processor.
*/
function _prepare()
{
if ($this->_options['testTransaction']) {
$this->_data['testTransaction'] = $this->_options['testTransaction'];
}
$this->_handleCardHolderName();
return parent::_prepare();
}
/**
* Process the transaction.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
*/
function &process()
{
// Sanity check
if(PEAR::isError($res = $this->validate())) {
return($res);
}
// Prepare the data
$this->_prepare();
// Don't die partway through
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
$req = new Net_Curl($this->_options['authorizeUri']);
if (PEAR::isError($req)) {
PEAR::popErrorHandling();
return $req;
}
$req->type = 'POST';
$req->fields = $this->_prepareQueryString();
$req->userAgent = 'PEAR Payment_Process_Transfirst 0.1';
$res = &$req->execute();
$req->close();
if (PEAR::isError($res)) {
PEAR::popErrorHandling();
return $res;
}
$this->_processed = true;
// Restore error handling
PEAR::popErrorHandling();
$response = trim($res);
print "Response: {$response}\n";
$result = &Payment_Process_Result::factory('Transfirst', $response);
$result->_request = &$this;
$this->_result = &$result;
return $result;
/*
* HTTP_Request doesn't do SSL until PHP 4.3.0, but it
* might be useful later...
$req = new HTTP_Request($this->_authUri);
$this->_setPostData();
$req->sendRequest();
*/
}
/**
* Get (completed) transaction status.
*
* @return string Two-digit status returned from gateway.
*/
function getStatus()
{
if (!$this->_processed) {
return PEAR::raiseError('The transaction has not been processed yet.', PAYMENT_PROCESS_ERROR_INCOMPLETE);
}
return $this->_result->code;
}
/**
* Get transaction sequence.
*
* 'Sequence' is what Transfirst calls their transaction ID/approval code. This
* function returns that code from a processed transaction.
*
* @return mixed Sequence ID, or PEAR_Error if the transaction hasn't been
* processed.
*/
function getSequence()
{
if (!$this->_processed) {
return PEAR::raiseError('The transaction has not been processed yet.', PAYMENT_PROCESS_ERROR_INCOMPLETE);
}
return $this->_result->_sequenceNumber;
}
/**
* Prepare the POST query string.
*
* @access private
* @return string The query string
*/
function _prepareQueryString()
{
foreach($this->_data as $var => $value) {
if (strlen($value))
$tmp[] = urlencode($var).'='.urlencode($value);
}
return @implode('&', $tmp);
}
/*
function _setPostData(&$req)
{
foreach($this->_data as $var => $value) {
$req->addPostData($var, $value);
}
}
*/
/**
* Handle transaction source.
*
* @access private
*/
function _handleTransactionSource()
{
$specific = $this->_fieldMap['transactionSource'];
if ($this->transactionSource == PAYMENT_PROCESS_SOURCE_ONLINE) {
$this->_data[$specific] = 'Y';
} else {
$this->_data[$specific] = 'N';
}
}
/**
* Handle card expiration date.
*
* The gateway wants the date in the format MMYY, with no other chars.
*
* @access private
*/
function _handleExpDate()
{
$specific = $this->_fieldMap['expDate'];
if (isset($this->_data[$specific])) {
$this->_data[$specific] = str_replace('/', '', $this->_data[$specific]);
} else {
$this->_data[$specific] = str_replace('/', '', $this->expDate);
}
}
/**
* Map firstName & lastName
*
* P_P now has split firstName/lastName fields, instead of 'name.' This
* handles concatenating them into the Transfirst cardHolderName field.
*
* @return void
*/
function _handleCardHolderName()
{
$this->_data['cardHolderName'] = $this->firstName . ' ' . $this->lastName;
}
/**
* Validate the merchant account login.
*
* The Transfirst docs specify that the login is exactly eight digits.
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validateLogin()
{
return Validate::string($this->login, array(
'format' => VALIDATE_NUM,
'max_length' => 8,
'min_length' => 8
));
}
/**
* Validate the merchant account password.
*
* The Transfirst docs specify that the password is a string between 6 and 10
* characters in length.
*
* @access private
* @return boolean true if valid, false otherwise
*/
function _validatePassword()
{
return Validate::string($this->password, array(
'format' => VALIDATE_ALPHA . VALIDATE_NUM,
'min_length' => 6,
'max_length' => 10
));
}
/**
* Validate the invoice number.
*
* Invoice number must be a 5-character long alphanumeric string.
*
* @return boolean true on success, false otherwise
*/
function _validateInvoiceNumber()
{
return Validate::string($this->invoiceNumber, array(
'format' => VALIDATE_NUM . VALIDATE_ALPHA,
'min_length' => 5,
'max_length' => 5
));
}
/**
* Validate the invoice number.
*
* Invoice no. must be a 15-character long alphanumeric string.
*
* @return boolean true on success, false otherwise
*/
function _validateCustomerId()
{
return Validate::string($this->customerId, array(
'format' => VALIDATE_NUM . VALIDATE_ALPHA,
'min_length' => 15,
'max_length' => 15
));
}
/**
* Validate the zip code.
*
* Zip is only required if AVS is enabled.
*
* @return boolean true on success, false otherwise.
*/
function _validateZip()
{
if(strlen($this->zip) || $this->performAvs) {
return parent::_validateZip();
}
return true;
}
}
class Payment_Process_Result_Transfirst extends Payment_Process_Result {
/**
* Transfirst status codes.
*
* This array holds every possible status returned by the Transfirst gateway.
*
* See the Transfirst documentation for more details on each response.
*
* @see getStatusText()
* @access private
*/
var $_statusCodeMessages = array(
'00' => "Approved",
'01' => "Refer to issuer",
'02' => "Refer to issuer - Special condition",
'03' => "Invalid merchant ID",
'04' => "Pick up card",
'05' => "Declined",
'06' => "General error",
'07' => "Pick up card - Special condition",
'13' => "Invalid amount",
'14' => "Invalid card number",
'15' => "No such issuer",
'19' => "Re-enter transaction",
'21' => "Unable to back out transaction",
'28' => "File is temporarily unavailable",
'39' => "No credit account",
'41' => "Pick up card - Lost",
'43' => "Pick up card - Stolen",
'51' => "Insufficient funds",
'54' => "Expired card",
'57' => "Transaction not permitted - Card",
'61' => "Amount exceeds withdrawal limit",
'62' => "Invalid service code, restricted",
'65' => "Activity limit exceeded",
'76' => "Unable to locate, no match",
'77' => "Inconsistent data, rev. or repeat",
'78' => "No account",
'80' => "Invalid date",
'85' => "Card OK",
'91' => "Issuer or switch is unavailable",
'93' => "Violation, cannot complete",
'96' => "System malfunction",
'98' => "No matching transaction to void",
'99' => "System timeout",
'L0' => "General System Error - Contact Transfirst Account Exec.",
'L1' => "Invalid or missing account number",
'L2' => "Invalid or missing password",
'L3' => "Expiration Date is not formatted correctly",
'L4' => "Reference number not found",
'L6' => "Order number is required but missing",
'L7' => "Wrong transaction code",
'L8' => "Network timeout",
'L14' => "Invalid card number",
'S5' => "Already settled",
'S6' => "Not authorized",
'S7' => "Declined",
'V6' => "Invalid transaction type",
'V7' => "Declined",
'V8' => "Already voided",
'V9' => "Already posted"
);
var $_avsCodeMap = array(
'A' => "Address match",
'E' => "Ineligible",
'N' => "No match",
'R' => "Retry",
'S' => "Service unavailable",
'U' => "Address information unavailable",
'W' => "9-digit zip match",
'X' => "Address and 9-digit zip match",
'Y' => "Address and 5-digit zip match",
'Z' => "5-digit zip match"
);
/**
* Status code map
*
* This contains a map from the Processor-specific result codes to the generic
* P_P codes. Anything not defined here is treated as a DECLINED result by
* validate()
*
* @type array
* @access private
*/
var $_statusCodeMap = array(
'00' => PAYMENT_PROCESS_RESULT_APPROVED,
'05' => PAYMENT_PROCESS_RESULT_DECLINED,
'V7' => PAYMENT_PROCESS_RESULT_DECLINED
);
var $_aciCodes = array(
'A' => "CPS Qualified",
'E' => "CPS Qualified - Card Acceptor Data was submitted in the authorization request.",
'M' => "Reserved - The card was not present and no AVS request for International transactions",
'N' => "Not CPS Qualified",
'V' => "CPS Qualified ? Included an address verification request in the authorization request."
);
var $_authSourceCodes = array(
' ' => "Terminal doesn't support",
'0' => "Exception File",
'1' => "Stand in Processing, time-out response",
'2' => "Loss Control System (LCS) response provided",
'3' => "STIP, response provided, issuer suppress inquiry mode",
'4' => "STIP, response provided, issuer is down",
'5' => "Response provided by issuer",
'9' => "Automated referral service (ARS) stand-in"
);
var $_fieldMap = array(
0 => '_null', // TF Internal Message Format
1 => '_acctNo', // TF Account number
2 => '_transactionCode', // The transaction code from the request message passed by the original request.
3 => 'transactionId', // Assigned by TF used to uniquely identify transaction.
4 => '_mailOrder', // Mail Order Identifier
5 => '_ccAcctNo', // The credit card account number passed by the original request.
6 => '_ccExpDate', // The Expiration Date passed by the original request. The field is formatted YYMM (Year, Month)
7 => '_authAmount', // An eight-digit value, which denotes the dollar amount passed to TF, without a decimal. ( DDDDDDCC )
8 => '_authDate', // A six-digit value, which denotes the date the authorization, was attempted. The field is formatted YYMMDD. (Year, Month, Date)
9 => '_authTime', // A six-digit value, which denotes the time the authorization, was attempted. The field is formatted HHMMSS. (Hour, Minute, Second)
10 => 'messageCode', // A two-digit value, which indicates the result of the authorization request. Used to determine if the card was authorized, declined or timed out.
11 => 'customerId', // The Customer Number passed by the original request
12 => 'invoiceNumber', // The Order Number passed by the original request.
13 => '_urn', // A number that uniquely identifies an individual transaction. Assigned by TF and can be used when referencing a specific transaction.
14 => '_authResponse', // A number provided by the issuing bank indicating the authorization is valid and funds have been reserved for transfer to the merchants account at a later time.
15 => '_authSource', // A code that defines the source where an authorization was captured.
16 => '_authCharacteristic', // A code that defines the qualification level for the authorized transaction.
17 => 'approvalCode', // Assigned by Visa or MasterCard, used to uniquely identify and link together all related information and used to authorize and clear a transaction.
18 => '_validationCode', // Assigned by V.I.P. System that is used to determine the accuracy of the authorization data.
19 => '_sicCatCode', // A merchants industry classification. Example - Mail Order/Phone Order Merchants (Direct Market) = 5969.
20 => '_currencyCode', // 840 indicate US Currency to date this is the only valid value.
21 => 'avsCode', // A value that indicates the level of Address Verification that was validated.
22 => '_merchantStoreNo', // Identifies the specific terminal used at a location 1-4 Merchant store #, 5-8 specific terminal at store.
23 => 'cvvCode' // A two-digit value, indicating the result of the card verification based on the CVV2 code provided by the cardholder.
);
/**
* Constructor.
*
* @param string $rawResponse The raw response from the gateway
* @return mixed boolean true on success, PEAR_Error on failure
*/
function __construct($rawResponse)
{
$res = $this->_validateResponse($rawResponse);
if (!$res || PEAR::isError($res)) {
if (!$res) {
$res = PEAR::raiseError("Unable to validate response body");
}
return $res;
}
$this->_rawResponse = $rawResponse;
$res = $this->_parseResponse();
}
function getAuthSource()
{
return @$this->_authSourceCodes[$this->_authSource];
}
function getAuthCharacteristic()
{
return @$this->_aciCodes[$this->_authChar];
}
function getCode()
{
return $this->_statusCodeMap[$this->messageCode];
}
/**
* Parse Transfirst (DPILink) R1 response string.
*
* This function parses the response the gateway sends back, which is in
* pipe-delimited format.
*
* @return void
*/
function _parseResponse()
{
$this->_mapFields(explode('|', $this->_rawResponse));
}
/**
* Validate a R1 response.
*
* @return boolean
*/
function _validateResponse($resp)
{
if (strlen($resp) > 160)
return false;
// FIXME - add more tests
return true;
}
}
?>

@ -0,0 +1,382 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2003 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Joe Stump <joe@joestump.net> |
// | Robert Peake <robert.peake@trustcommerce.com> |
// +----------------------------------------------------------------------+
//
// $Id: TrustCommerce.php,v 1.5 2005/07/08 00:13:25 jstump Exp $
require_once('Payment/Process.php');
require_once('Payment/Process/Common.php');
require_once('Net/Curl.php');
$GLOBALS['_Payment_Process_TrustCommerce'] = array(
PAYMENT_PROCESS_ACTION_NORMAL => 'sale',
PAYMENT_PROCESS_ACTION_AUTHONLY => 'preauth',
PAYMENT_PROCESS_ACTION_POSTAUTH => 'postauth'
);
/**
* Payment_Process_TrustCommerce
*
* This is a processor for TrustCommerce's merchant payment gateway.
* (http://www.trustcommerce.com/)
*
* *** WARNING ***
* This is ALPHA code, and has not been fully tested. It is not recommended
* that you use it in a production envorinment without further testing.
*
* @package Payment_Process
* @author Robert Peake <robert.peake@trustcommerce.com>
* @version @version@
*/
class Payment_Process_TrustCommerce extends Payment_Process_Common {
/**
* Front-end -> back-end field map.
*
* This array contains the mapping from front-end fields (defined in
* the Payment_Process class) to the field names TrustCommerce requires.
*
* @see _prepare()
* @access private
*/
var $_fieldMap = array(
// Required
'login' => 'custid',
'password' => 'password',
'action' => 'action',
'amount' => 'amount',
//PostAuth
'transactionId' => 'transid',
// Optional
'name' => 'name',
'address' => 'address1',
'city' => 'city',
'state' => 'state',
'country' => 'country',
'phone' => 'phone',
'email' => 'email',
'zip' => 'zip',
'currency' => 'currency',
);
/**
* $_typeFieldMap
*
* @author Robert Peake <robert.peake@trustcommerce.com>
* @access protected
*/
var $_typeFieldMap = array(
'CreditCard' => array(
'cardNumber' => 'cc',
'cvv' => 'cvv',
'expDate' => 'exp'
),
'eCheck' => array(
'routingCode' => 'routing',
'accountNumber' => 'account',
'name' => 'name'
)
);
/**
* Default options for this processor.
*
* @see Payment_Process::setOptions()
* @access private
*/
var $_defaultOptions = array();
/**
* Has the transaction been processed?
*
* @type boolean
* @access private
*/
var $_processed = false;
/**
* The response body sent back from the gateway.
*
* @access private
*/
var $_responseBody = '';
/**
* Constructor.
*
* @param array $options Class options to set.
* @see Payment_Process::setOptions()
* @return void
*/
function __construct($options = false)
{
parent::__construct($options);
$this->_driver = 'TrustCommerce';
}
/**
* Process the transaction.
*
* @return mixed Payment_Process_Result on success, PEAR_Error on failure
*/
function &process()
{
// Sanity check
$result = $this->validate();
if(PEAR::isError($result)) {
return $result;
}
// Prepare the data
$result = $this->_prepare();
if (PEAR::isError($result)) {
return $result;
}
// Don't die partway through
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
$fields = $this->_prepareQueryString();
if(function_exists('tclink_send')) {
/** USE TCLINK **/
$result = tclink_send($fields);
$r_keys = array_keys($result);
for($i=0;$i<sizeof($r_keys);$i++) {
$key = $r_keys[$i];
$value = $result[$key];
$result_string .= $key.'='.$value."\n";
}
if (PEAR::isError($result_string)) {
PEAR::popErrorHandling();
return $result_string;
} else {
$result = $result_string;
}
} else {
/** USE CURL **/
$curl = new Net_Curl('https://vault.trustcommerce.com/trans/');
if (PEAR::isError($curl)) {
PEAR::popErrorHandling();
return $curl;
}
$curl->type = 'PUT';
$curl->fields = $fields;
$curl->userAgent = 'PEAR Payment_Process_TrustCommerce 0.1a';
$result = &$curl->execute();
if (PEAR::isError($result)) {
PEAR::popErrorHandling();
return $result;
} else {
$curl->close();
}
}
/** END TCLINK/CURL CASE STATEMENT **/
$this->_responseBody = trim($result);
$this->_processed = true;
// Restore error handling
PEAR::popErrorHandling();
$response = Payment_Process_Result::factory($this->_driver,
$this->_responseBody,
$this);
if (!PEAR::isError($response)) {
$response->parse();
}
return $response;
}
/**
* Get (completed) transaction status.
*
* @return boolean status.
*/
function getStatus()
{
return false;
}
/**
* Prepare the POST query string.
*
* @access private
* @return string The query string
*/
function _prepareQueryString()
{
$data = $this->_data;
/* expiration is expressed as mmyy */
$fulldate = $data['exp'];
$month = strtok($fulldate,'/');
$year = strtok('');
$exp = $month.substr($year,2,2);
$data['exp'] = $exp;
/* end expiration mangle */
/* amount is expressed in cents with leading zeroes */
$data['amount'] = $data['amount']*100;
if (strlen($data['amount']) == 1) {
$data['amount'] = "00".$data['amount'];
} else if(strlen($data['amount']) < 3) {
$data['amount'] = "0".$data['amount'];
} else if(strlen($data['amount']) > 8) {
$amount_message = 'Amount: '.$data['amount'].' too large.';
PEAR::pushErrorHandling(PEAR_ERROR_RETURN);
PEAR::raiseError($amount_message);
PEAR::popErrorHandling();
}
/* end amount mangle */
if ($this->_payment->getType() == 'CreditCard' &&
$this->action != PAYMENT_PROCESS_ACTION_POSTAUTH) {
$data['media'] = 'cc';
}
if ($this->_payment->getType() == 'eCheck') {
$data['media'] = 'ach';
}
$return = array();
$sets = array();
foreach ($data as $key => $val) {
if (strlen($val)) {
$return[$key] = $val;
$sets[] = $key.'='.urlencode($val);
}
}
$this->_options['authorizeUri'] = 'https://vault.trustcommerce.com/trans/?'.implode('&',$sets);
return $return;
}
}
class Payment_Process_Result_TrustCommerce extends Payment_Process_Result {
var $_statusCodeMap = array('approved' => PAYMENT_PROCESS_RESULT_APPROVED,
'accepted' => PAYMENT_PROCESS_RESULT_APPROVED,
'declined' => PAYMENT_PROCESS_RESULT_DECLINED,
'baddata' => PAYMENT_PROCESS_RESULT_OTHER,
'error' => PAYMENT_PROCESS_RESULT_OTHER);
/**
* TrustCommerce status codes
*
* This array holds response codes.
*
* @see getStatusText()
* @access private
*/
var $_statusCodeMessages = array(
'approved' => 'The transaction was successfully authorized.',
'accepted' => 'The transaction has been successfully accepted into the system.',
'decline' => 'The transaction was declined, see declinetype for further details.',
'baddata' => 'Invalid parameters passed, see error for further details.',
'error' => 'System error when processing the transaction, see errortype for details.',
);
var $_avsCodeMap = array(
'N' => PAYMENT_PROCESS_AVS_MISMATCH,
'U' => PAYMENT_PROCESS_AVS_NOAPPLY,
'G' => PAYMENT_PROCESS_AVS_NOAPPLY,
'R' => PAYMENT_PROCESS_AVS_ERROR,
'E' => PAYMENT_PROCESS_AVS_ERROR,
'S' => PAYMENT_PROCESS_AVS_ERROR,
'O' => PAYMENT_PROCESS_AVS_ERROR
);
var $_avsCodeMessages = array(
'X' => 'Exact match, 9 digit zipcode.',
'Y' => 'Exact match, 5 digit zipcode.',
'A' => 'Street address match only.',
'W' => '9 digit zipcode match only.',
'Z' => '5 digit zipcode match only.',
'N' => 'No mtach on street address or zipcode.',
'U' => 'AVS unavailable on this card.',
'G' => 'Non-US card issuer, AVS unavailable.',
'R' => 'Card issuer system currently down, try again later.',
'E' => 'Error, ineligible - not a mail/phone order.',
'S' => 'Service not supported.',
'O' => 'General decline or other error'
);
var $_cvvCodeMap = array('cvv' => PAYMENT_PROCESS_CVV_MISMATCH
);
var $_cvvCodeMessages = array( 'cvv' => 'The CVV number is not valid.'
);
var $_fieldMap = array('status' => 'code',
'avs' => 'avsCode',
'transid' => 'transactionId'
);
function Payment_Process_Response_TrustCommerce($rawResponse)
{
$this->Payment_Process_Response($rawResponse);
}
function parse()
{
$array = preg_split("/\n/",$this->_rawResponse,0,PREG_SPLIT_NO_EMPTY);
for($i=0;$i<sizeof($array);$i++)
{
$response_line = $array[$i];
$response_array = preg_split("/=/",$response_line);
$key = $response_array[0];
$value = $response_array[1];
$responseArray[$key] = $value;
}
$this->_mapFields($responseArray);
}
function _mapFields($responseArray)
{
foreach($this->_fieldMap as $key => $val) {
$this->$val = $responseArray[$key];
}
if (!isset($this->_statusCodeMessages[$this->messageCode]))
{
$message = $this->_statusCodeMessages[$responseArray['status']];
if($responseArray['error'])
{
$message .= "\nError type: ".$responseArray['error'].'.';
if($responseArray['offenders'])
{
$message .= "\nOffending fields: ".$responseArray['offenders'].'.';
}
}
$this->_statusCodeMessages[$this->messageCode] = $message;
}
}
}
?>

@ -0,0 +1,255 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2003 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Ian Eure <ieure@php.net> |
// | Joe Stump <joe@joestump.net> |
// +----------------------------------------------------------------------+
//
// $Id: Type.php,v 1.22 2006/01/24 23:21:49 ieure Exp $
define('PAYMENT_PROCESS_CC_VISA', 100);
define('PAYMENT_PROCESS_CC_MASTERCARD', 101);
define('PAYMENT_PROCESS_CC_AMEX', 102);
define('PAYMENT_PROCESS_CC_DISCOVER', 103);
define('PAYMENT_PROCESS_CC_JCB', 104);
define('PAYMENT_PROCESS_CC_DINERS', 105);
define('PAYMENT_PROCESS_CC_CARTEBLANCHE', 106);
define('PAYMENT_PROCESS_CC_ENROUTE', 107);
define('PAYMENT_PROCESS_CK_SAVINGS', 1000);
define('PAYMENT_PROCESS_CK_CHECKING', 1001);
/**
* Payment_Process_Type
*
* @author Joe Stump <joe@joestump.net>
* @category Payment
* @package Payment_Process
* @version @version@
*/
class Payment_Process_Type
{
// {{{ properties
/**
* $_type
*
* @var string $type Type of payment (ie. 'CreditCard' or 'eCheck')
*/
var $_type = null;
/**
* $firstName
*
* @var string $firstName
*/
var $firstName;
/**
* $lastName
*
* @var string $lastName
*/
var $lastName;
/**
* $company
*
* @var string $company
*/
var $company;
/**
* $address
*
* @var string $addres
*/
var $address;
/**
* $city
*
* @var string $city
*/
var $city;
/**
* $state
*
* @var string $state State/Province of customer
*/
var $state;
/**
* $zip
*
* @var string $zip Zip/Postal code of customer
*/
var $zip;
/**
* $country
*
* @var string $country Country code of customer (ie. US)
*/
var $country;
/**
* $phone
*
* @var string $phone Phone number of customer
*/
var $phone;
/**
* $fax
*
* @var string $fax Fax number of customer
*/
var $fax;
/**
* $city
*
* @var string $email Email address of customer
*/
var $email;
/**
* $ipAddress
*
* @var string $ipAddress Remote IP address of customer
*/
var $ipAddress;
// }}}
// {{{ __construct()
function __construct()
{
}
// }}}
// {{{ &factory($type)
/**
* factory
*
* Creates and returns an instance of a payment type. If an error occurs
* a PEAR_Error is returned.
*
* @author Joe Stump <joe@joestump.net>
* @param string $type
* @return mixed
*/
// static function, avoid PHP strict error.
static function &factory($type)
{
$class = 'Payment_Process_Type_'.$type;
$file = 'Payment/Process/Type/'.$type.'.php';
if (include_once($file)) {
if (class_exists($class)) {
$ret = new $class();
return $ret;
}
}
$ret = PEAR::raiseError('Invalid Payment_Process_Type: '.$type);
return $ret;
}
// }}}
// {{{ isValid()
/**
* isValid
*
* Validate a payment type object
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @param mixed $obj Type object to validate
* @return mixed true on success, PEAR_Error on failure
*/
static function isValid($obj)
{
if (!is_a($obj,'Payment_Process_Type')) {
return PEAR::raiseError('Not a valid payment type');
}
$vars = get_object_vars($obj);
foreach ($vars as $validate => $value) {
$method = '_validate'.ucfirst($validate);
if (method_exists($obj, $method)) {
$result = $obj->$method();
if (PEAR::isError($result)) {
return $result;
}
}
}
return true;
}
// }}}
// {{{ getType()
/**
* getType
*
* @author Joe Stump <joe@joestump.net>
* @access public
* @return string
*/
function getType()
{
return $this->_type;
}
// }}}
// {{{ _validateEmail()
/**
* Validate an email address.
*
* @author Ian Eure <ieure@php.net>
* @access private
* @return boolean true on success, false on failure.
*/
function _validateEmail()
{
if (isset($this->email) && strlen($this->email)) {
return Validate::email($this->email, false);
}
return true;
}
// }}}
// {{{ _validateZip()
/**
* Validate the zip code.
*
* This only validates U.S. zipcodes; country must be set to 'us' for zip to
* be validated.
*
* @author Ian Eure <ieure@php.net>
* @access private
* @return boolean true on success, false otherwise
* @todo use Validate_*::postalCode() method
*/
function _validateZip()
{
if (isset($this->zip) && strtolower($this->country) == 'us') {
# return ereg('^[0-9]{5}(-[0-9]{4})?$', $this->zip);
return preg_match('/^[0-9]{5}(-[0-9]{4})?$/', $this->zip);
}
return true;
}
// }}}
}
?>

@ -0,0 +1,82 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2003 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Ian Eure <ieure@php.net> |
// | Joe Stump <joe@joestump.net> |
// +----------------------------------------------------------------------+
//
// $Id: eCheck.php,v 1.9 2005/09/07 22:50:35 jstump Exp $
/**
* Payment_Process_Type_eCheck
*
* @author Joe Stump <joe@joestump.net>
* @package Payment_Process
*/
class Payment_Process_Type_ACH extends Payment_Process_Type
{
/**
* $_type
*
* @var string $_type
*/
var $_type = 'ACH';
/**
* $type
*
* @var $type
*/
var $type;
var $accountNumber;
var $routingCode;
var $accountCode;
var $name;
function __construct()
{
}
function _validateAccountNumber()
{
if (!isset($this->accountNumber)) {
return PEAR::raiseError('Account number is required');
}
return true;
}
function _validateRoutingCode()
{
if (!isset($this->routingCode)) {
return PEAR::raiseError('Routing code is required');
}
return true;
}
function _validateName()
{
if (!isset($this->routingCode)) {
return PEAR::raiseError('Name is required');
}
return true;
}
}
?>

@ -0,0 +1,210 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
/**
* Represents a credit card type of payment
*
* PHP versions 4 and 5
*
* LICENSE: This source file is subject to version 3.0 of the PHP license
* that is available through the world-wide-web at the following URI:
* http://www.php.net/license/3_0.txt. If you did not receive a copy of
* the PHP License and are unable to obtain it through the web, please
* send a note to license@php.net so we can mail you a copy immediately.
*
* @category Payment
* @package Payment_Process
* @author Ian Eure <ieure@php.net>
* @author Joe Stump <joe@joestump.net>
* @author Philippe Jausions <Philippe.Jausions@11abacus.com>
* @copyright 1997-2005 The PHP Group
* @license http://www.php.net/license/3_0.txt PHP License 3.0
* @version CVS: $Id: CreditCard.php,v 1.14 2005/11/01 19:15:59 jausions Exp $
* @link http://pear.php.net/package/Payment_Process
* @see Validate_Finance_CreditCard
*/
/**
* Payment_Process_Type_CreditCard
*
* @author Joe Stump <joe@joestump.net>
* @package Payment_Process
*/
class Payment_Process_Type_CreditCard extends Payment_Process_Type
{
/**
* Self-identifying payment type
*
* @var string $_type
*/
var $_type = 'CreditCard';
/**
* Credit card type
*
* @var int $type one of PAYMENT_PROCESS_CC_* constant
*/
var $type;
/**
* Credit card number
*
* @var string $cardNumber
*/
var $cardNumber;
/**
* Card Verification Value
*
* a.k.a CVV2, CVC, CID
*
* @var int $cvv
*/
var $cvv;
/**
* Card expiry date
*
* @var string $expDate expiry date in MM/YYYY format
*/
var $expDate;
function __construct()
{
require_once 'Validate/Finance/CreditCard.php';
parent::__construct();
}
/**
* _validateCardNumber
*
* Uses Validate_Finance_CreditCard to validate the card number.
*
* @author Joe Stump <joe@joestump.net>
* @return mixed PEAR_Error on failure, TRUE on success
* @see Payment_Process_Type_CreditCard::_getValidateTypeMap()
* @see Validate_Finance_CreditCard
*/
function _validateCardNumber()
{
if (!Validate_Finance_CreditCard::number($this->cardNumber, $this->_mapType())) {
return PEAR::raiseError('Invalid credit card number');
}
return true;
}
/**
* Validates the credit card type
*
* Uses Validate_Finance_CreditCard to validate the type.
*
* @author Joe Stump <joe@joestump.net>
* @return mixed PEAR_Error on failure, TRUE on success
* @see Payment_Process_Type_CreditCard::_getValidateTypeMap()
* @see Validate_Finance_CreditCard
*/
function _validateType()
{
if (!($type = $this->_mapType())) {
return PEAR::raiseError('Invalid type map provided in driver');
}
if (!Validate_Finance_CreditCard::type($this->cardNumber, $type)) {
return PEAR::raiseError('Credit card type not recognized or does not match the card number given');
}
return true;
}
/**
* Validates the card verification value
*
* @return bool PEAR_Error is CVV was set and is not valid, TRUE otherwise
* @access protected
*/
function _validateCvv()
{
if (strlen($this->cvv) == 0) {
return true;
}
if (!($type = $this->_mapType())) {
return PEAR::raiseError('Invalid type map provided in driver');
}
if (!Validate_Finance_CreditCard::cvv($this->cvv, $type)) {
return PEAR::raiseError('CVV code is invalid or does not match the card type');
}
return true;
}
/**
* Validate the card's expiration date.
*
* @return boolean true on success, false otherwise
* @access protected
* @author Joe Stump <joe@joestump.net>
* @todo Fix YxK issues; an expyear of '99' will come up as valid.
*/
function _validateExpDate()
{
list($month, $year) = explode('/', $this->expDate);
if (!is_numeric($month) || !is_numeric($year)) {
return PEAR::raiseError('Invalid expiration date provided');
}
$monthOptions = array('min' => 1,
'max' => 12,
'decimal' => false);
$date = getdate();
$yearOptions = array('min' => $date['year'],
'decimal' => false);
if (Validate::number($month, $monthOptions) &&
Validate::number($year, $yearOptions)) {
if (($month >= $date['mon'] && $year == $date['year']) ||
($year > $date['year'])) {
return true;
}
}
return PEAR::raiseError('Invalid expiration date provided');
}
/**
* Maps a PAYMENT_PROCESS_CC_* constant with a with a value suitable
* to Validate_Finance_CreditCard package
*
* @return string|boolean card type name or FALSE on error
* @access private
*/
function _mapType()
{
switch ($this->type) {
case PAYMENT_PROCESS_CC_MASTERCARD:
return 'MasterCard';
case PAYMENT_PROCESS_CC_VISA:
return 'Visa';
case PAYMENT_PROCESS_CC_AMEX:
return 'Amex';
case PAYMENT_PROCESS_CC_DISCOVER:
return 'Discover';
case PAYMENT_PROCESS_CC_JCB:
return 'JCB';
case PAYMENT_PROCESS_CC_DINERS:
return 'Diners';
case PAYMENT_PROCESS_CC_ENROUTE:
return 'EnRoute';
case PAYMENT_PROCESS_CC_CARTEBLANCHE:
return 'CarteBlanche';
default:
return false;
}
}
}
?>

@ -0,0 +1,91 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2003 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Ian Eure <ieure@php.net> |
// | Joe Stump <joe@joestump.net> |
// +----------------------------------------------------------------------+
//
// $Id: eCheck.php,v 1.9 2005/09/07 22:50:35 jstump Exp $
/**
* Payment_Process_Type_eCheck
*
* @author Joe Stump <joe@joestump.net>
* @package Payment_Process
*/
class Payment_Process_Type_EFT extends Payment_Process_Type
{
/**
* $_type
*
* @var string $_type
*/
var $_type = 'EFT';
/**
* $type
*
* @var $type
*/
var $type;
var $accountNumber;
var $routingCode;
var $institutionCode;
var $name;
function __construct()
{
}
function _validateAccountNumber()
{
if (!isset($this->accountNumber)) {
return PEAR::raiseError('Account number is required');
}
return true;
}
function _validateInstituionCode()
{
if (!isset($this->accountNumber)) {
return PEAR::raiseError('Institution code is required');
}
return true;
}
function _validateRoutingCode()
{
if (!isset($this->routingCode)) {
return PEAR::raiseError('Routing code is required');
}
return true;
}
function _validateName()
{
if (!isset($this->routingCode)) {
return PEAR::raiseError('Name is required');
}
return true;
}
}
?>

@ -0,0 +1,82 @@
<?php
/* vim: set expandtab tabstop=4 shiftwidth=4: */
// +----------------------------------------------------------------------+
// | PHP version 4 |
// +----------------------------------------------------------------------+
// | Copyright (c) 1997-2003 The PHP Group |
// +----------------------------------------------------------------------+
// | This source file is subject to version 3.0 of the PHP license, |
// | that is bundled with this package in the file LICENSE, and is |
// | available through the world-wide-web at |
// | http://www.php.net/license/3_0.txt. |
// | If you did not receive a copy of the PHP license and are unable to |
// | obtain it through the world-wide-web, please send a note to |
// | license@php.net so we can mail you a copy immediately. |
// +----------------------------------------------------------------------+
// | Authors: Ian Eure <ieure@php.net> |
// | Joe Stump <joe@joestump.net> |
// +----------------------------------------------------------------------+
//
// $Id: eCheck.php,v 1.9 2005/09/07 22:50:35 jstump Exp $
/**
* Payment_Process_Type_eCheck
*
* @author Joe Stump <joe@joestump.net>
* @package Payment_Process
*/
class Payment_Process_Type_eCheck extends Payment_Process_Type
{
/**
* $_type
*
* @var string $_type
*/
var $_type = 'eCheck';
/**
* $type
*
* @var $type
*/
var $type;
var $accountNumber;
var $routingCode;
var $bankName;
var $driversLicense;
var $driversLicenseState;
function __construct()
{
}
function _validateAccountNumber()
{
if (!isset($this->accountNumber)) {
return PEAR::raiseError('Account number is required');
}
return true;
}
function _validateRoutingCode()
{
if (!isset($this->routingCode)) {
return PEAR::raiseError('Routing code is required');
}
return true;
}
function _validateBankName()
{
if (!isset($this->bankName)) {
return PEAR::raiseError('Bank name is required');
}
return true;
}
}
?>