Merge pull request #4143 from turbo124/v2

Gateway fixes
This commit is contained in:
David Bomba 2020-10-09 22:13:58 +11:00 committed by GitHub
commit 5cd1acd484
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
15 changed files with 227 additions and 24 deletions

View File

@ -34,7 +34,7 @@ class EmailTemplateDefaults
return self::emailPaymentTemplate();
break;
case 'email_template_payment_partial':
return self::emailPaymentTemplate();
return self::emailPaymentPartialTemplate();
break;
case 'email_template_statement':
return self::emailStatementTemplate();
@ -73,7 +73,7 @@ class EmailTemplateDefaults
return self::emailPaymentSubject();
break;
case 'email_subject_payment_partial':
return self::emailPaymentSubject();
return self::emailPaymentPartialSubject();
break;
case 'email_subject_statement':
return self::emailStatementSubject();
@ -140,13 +140,11 @@ class EmailTemplateDefaults
]);
return $converter->convertToHtml(self::transformText('quote_message'));
//return Parsedown::instance()->line(self::transformText('quote_message'));
}
public static function emailPaymentSubject()
{
return ctrans('texts.payment_subject');
//return Parsedown::instance()->line(self::transformText('payment_subject'));
}
public static function emailPaymentTemplate()
@ -158,7 +156,11 @@ class EmailTemplateDefaults
return $converter->convertToHtml(self::transformText('payment_message'));
// return Parsedown::instance()->line(self::transformText('payment_message'));
}
public static function emailPaymentPartialSubject()
{
return ctrans('texts.payment_subject');
}
public static function emailReminder1Subject()
@ -201,17 +203,17 @@ class EmailTemplateDefaults
public static function emailReminderEndlessTemplate()
{
return Parsedown::instance()->line('Endless Email Reminder Text');
return ctrans('Endless Email Reminder Text');
}
public static function emailStatementSubject()
{
return Parsedown::instance()->line('Statement Subject needs texts record!');
return ctrans('Statement Subject needs texts record!');
}
public static function emailStatementTemplate()
{
return Parsedown::instance()->line('Statement Templates needs texts record!');
return ctrans('Statement Templates needs texts record!');
}
private static function transformText($string)

View File

@ -433,6 +433,8 @@ class BaseController extends Controller
$data['hash'] = md5(public_path('main.dart.js'));
$this->buildCache();
return view('index.index', $data);
}

View File

@ -22,6 +22,7 @@ use App\Utils\Traits\MakesDates;
use App\Utils\Traits\MakesHash;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Str;
/**
* Class InvitationController.
@ -33,9 +34,10 @@ class InvitationController extends Controller
public function router(string $entity, string $invitation_key)
{
$key = $entity.'_id';
$entity_obj = 'App\Models\\'.ucfirst($entity).'Invitation';
$entity_obj = 'App\Models\\'.ucfirst(Str::camel($entity)).'Invitation'; //todo sensitive to the route parameters here
$invitation = $entity_obj::whereRaw('BINARY `key`= ?', [$invitation_key])
->with('contact.client')

View File

@ -55,7 +55,7 @@ class Kernel extends HttpKernel
'throttle:60,1',
'bindings',
'query_logging',
\App\Http\Middleware\StartupCheck::class,
//\App\Http\Middleware\StartupCheck::class,
\App\Http\Middleware\Cors::class,
],
'contact' => [
@ -71,7 +71,7 @@ class Kernel extends HttpKernel
\Illuminate\View\Middleware\ShareErrorsFromSession::class,
\App\Http\Middleware\VerifyCsrfToken::class,
\Illuminate\Routing\Middleware\SubstituteBindings::class,
\App\Http\Middleware\StartupCheck::class,
//\App\Http\Middleware\StartupCheck::class,
\App\Http\Middleware\QueryLogging::class,
],
'shop' => [

View File

@ -11,6 +11,7 @@
namespace App\Http\Middleware;
use App\DataMapper\EmailTemplateDefaults;
use App\Models\Account;
use App\Models\Language;
use App\Utils\CurlUtils;
@ -30,7 +31,7 @@ class StartupCheck
{
/**
* Handle an incoming request.
*
* @deprecated
* @param Request $request
* @param Closure $next
*
@ -45,6 +46,7 @@ class StartupCheck
foreach ($cached_tables as $name => $class) {
if ($request->has('clear_cache') || ! Cache::has($name)) {
// check that the table exists in case the migration is pending
if (! Schema::hasTable((new $class())->getTable())) {
continue;
@ -65,8 +67,56 @@ class StartupCheck
}
}
/*Build template cache*/
if ($request->has('clear_cache') || ! Cache::has('templates'))
$this->buildTemplates();
$response = $next($request);
return $response;
}
private function buildTemplates($name = 'templates')
{
$data = [
'invoice' => [
'subject' => EmailTemplateDefaults::emailInvoiceSubject(),
'body' => EmailTemplateDefaults::emailInvoiceTemplate(),
],
'quote' => [
'subject' => EmailTemplateDefaults::emailQuoteSubject(),
'body' => EmailTemplateDefaults::emailQuoteTemplate(),
],
'payment' => [
'subject' => EmailTemplateDefaults::emailPaymentSubject(),
'body' => EmailTemplateDefaults::emailPaymentTemplate(),
],
'reminder1' => [
'subject' => EmailTemplateDefaults::emailReminder1Subject(),
'body' => EmailTemplateDefaults::emailReminder1Template(),
],
'reminder2' => [
'subject' => EmailTemplateDefaults::emailReminder2Subject(),
'body' => EmailTemplateDefaults::emailReminder2Template(),
],
'reminder3' => [
'subject' => EmailTemplateDefaults::emailReminder3Subject(),
'body' => EmailTemplateDefaults::emailReminder3Template(),
],
'reminder_endless' => [
'subject' => EmailTemplateDefaults::emailReminderEndlessSubject(),
'body' => EmailTemplateDefaults::emailReminderEndlessTemplate(),
],
'statement' => [
'subject' => EmailTemplateDefaults::emailStatementSubject(),
'body' => EmailTemplateDefaults::emailStatementTemplate(),
],
];
Cache::forever($name, $data);
}
}

View File

@ -100,7 +100,7 @@ class Gateway extends StaticModel
* Returns an array of methods and the gatewaytypes possible
*
* @return array
*/
*///todo remove methods replace with gatewaytype:: and then nest refund / token billing
public function getMethods()
{
switch ($this->id) {

View File

@ -53,6 +53,8 @@ class CheckoutComPaymentDriver extends BaseDriver
/** Instance of \Checkout\CheckoutApi */
public $gateway;
public $payment_method; //the gateway type id
public static $methods = [
GatewayType::CREDIT_CARD => '',
];
@ -100,6 +102,9 @@ class CheckoutComPaymentDriver extends BaseDriver
*/
public function viewForType($gateway_type_id)
{
$this->payment_method = $gateway_type_id;
if ($gateway_type_id == GatewayType::CREDIT_CARD) {
return 'gateways.checkout.credit_card';
}
@ -355,13 +360,43 @@ class CheckoutComPaymentDriver extends BaseDriver
public function saveCard($state)
{
//some cards just can't be tokenized....
if(!$state['payment_response']->source['id'])
return;
// [id] => src_hck5nsv3fljehbam2cvdm7fioa
// [type] => card
// [expiry_month] => 10
// [expiry_year] => 2022
// [scheme] => Visa
// [last4] => 4242
// [fingerprint] => 688192847DB9AE8A26C53776D036D5B8AD2CEAF1D5A8F5475F542B021041EFA1
// [bin] => 424242
// [card_type] => Credit
// [card_category] => Consumer
// [issuer] => JPMORGAN CHASE BANK NA
// [issuer_country] => US
// [product_id] => A
// [product_type] => Visa Traditional
// [avs_check] => S
// [cvv_check] => Y
// [payouts] => 1
// [fast_funds] => d
$payment_meta = new \stdClass;
$payment_meta->exp_month = (string)$state['payment_response']->source['expiry_month'];
$payment_meta->exp_year = (string)$state['payment_response']->source['expiry_year'];
$payment_meta->brand = (string)$state['payment_response']->source['scheme'];
$payment_meta->last4 = (string)$state['payment_response']->source['last4'];
$payment_meta->type = $this->payment_method;
$company_gateway_token = new ClientGatewayToken();
$company_gateway_token->company_id = $this->client->company->id;
$company_gateway_token->client_id = $this->client->id;
$company_gateway_token->token = $state['payment_response']->source['id'];
$company_gateway_token->company_gateway_id = $this->company_gateway->id;
$company_gateway_token->gateway_type_id = $state['payment_method_id'];
$company_gateway_token->meta = $state['payment_response']->source;
$company_gateway_token->meta = $payment_meta;
$company_gateway_token->save();
if ($this->client->gateway_tokens->count() == 1) {

View File

@ -53,7 +53,8 @@ class AutoBillInvoice extends AbstractService
if ((int)$this->invoice->balance == 0)
return $this->invoice->service()->markPaid()->save();
$this->applyCreditPayment(); //if the credits cover the payments, we stop here, build the payment with credits and exit early
//if the credits cover the payments, we stop here, build the payment with credits and exit early
$this->applyCreditPayment();
/* Determine $amount */
if ($this->invoice->partial > 0)
@ -70,7 +71,7 @@ class AutoBillInvoice extends AbstractService
return $this->invoice;
/* $gateway fee */
$fee = $gateway_token->gateway->calcGatewayFee($this->invoice->partial);
$fee = $gateway_token->gateway->calcGatewayFee($amount);
/* Build payment hash */
$payment_hash = PaymentHash::create([
@ -98,7 +99,7 @@ class AutoBillInvoice extends AbstractService
info("finalizing");
info(print_r($this->used_credit,1));
$amount = array_sum(array_column($this->used_credit, 'amount'));
info("amount {$amount}");
info("amount {$amount}");
$payment = PaymentFactory::create($this->invoice->company_id, $this->invoice->user_id);
$payment->amount = $amount;

View File

@ -55,12 +55,19 @@ class RecurringService
if($this->recurring_entity->remaining_cycles == 0)
return $this;
$this->recurring_entity->status_id = RecurringInvoice::STATUS_ACTIVE;
$this->createInvitations()->setStatus(RecurringInvoice::STATUS_ACTIVE);
return $this;
}
public function setStatus($status)
{
$this->recurring_entity->status_id = $status;
return $this;
}
/**
* Applies the invoice number.
* @return $this InvoiceService object

View File

@ -35,11 +35,33 @@ class ClientGatewayTokenTransformer extends EntityTransformer
'gateway_type_id' => (string) $cgt->gateway_type_id ?: '',
'company_gateway_id' => (string) $this->encodePrimaryKey($cgt->company_gateway_id) ?: '',
'is_default' => (bool) $cgt->is_default,
'meta' => $cgt->meta,
'meta' => $this->typeCastMeta($cgt->meta),
'created_at' => (int) $cgt->created_at,
'updated_at' => (int) $cgt->updated_at,
'archived_at' => (int) $cgt->deleted_at,
'is_deleted' => (bool) $cgt->is_deleted,
];
}
private function typeCastMeta($meta)
{
$casted = new \stdClass;
if(property_exists($meta, 'exp_month'))
$casted->exp_month = (string)$meta->exp_month;
if(property_exists($meta, 'exp_year'))
$casted->exp_year = (string)$meta->exp_year;
if(property_exists($meta, 'brand'))
$casted->brand = (string)$meta->brand;
if(property_exists($meta, 'last4'))
$casted->last4 = (string)$meta->last4;
if(property_exists($meta, 'type'))
$casted->type = (int)$meta->type;
return $casted;
}
}

View File

@ -121,7 +121,7 @@ class HtmlEngine
$data['$entity.terms'] = ['value' => $this->entity->terms ?: ' ', 'label' => ctrans('texts.invoice_terms')];
$data['$terms'] = &$data['$entity.terms'];
$data['$view_link'] = ['value' => '<a href="'.$this->invitation->getLink().'">'.ctrans('texts.view_invoice').'</a>', 'label' => ctrans('texts.view_invoice')];
// $data['$view_link'] = ['value' => $this->invitation->getLink(), 'label' => ctrans('texts.view_invoice')];
$data['$view_url'] = ['value' => $this->invitation->getLink(), 'label' => ctrans('texts.view_invoice')];
}
if ($this->entity_string == 'quote') {

View File

@ -104,6 +104,9 @@ class Statics
})->sortBy(function ($currency) {
return $currency->name;
})->values();
$data['templates'] = Cache::get('templates');
}
return $data;

View File

@ -11,8 +11,11 @@
namespace App\Utils\Traits;
use App\DataMapper\EmailTemplateDefaults;
use App\Utils\Ninja;
use App\Utils\SystemHealth;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Schema;
trait AppSetup
{
@ -26,4 +29,79 @@ trait AppSetup
return $check['system_health'] == 'true';
}
public function buildCache()
{
$cached_tables = config('ninja.cached_tables');
foreach ($cached_tables as $name => $class) {
if (request()->has('clear_cache') || ! Cache::has($name)) {
// check that the table exists in case the migration is pending
if (! Schema::hasTable((new $class())->getTable())) {
continue;
}
if ($name == 'payment_terms') {
$orderBy = 'num_days';
} elseif ($name == 'fonts') {
$orderBy = 'sort_order';
} elseif (in_array($name, ['currencies', 'industries', 'languages', 'countries', 'banks'])) {
$orderBy = 'name';
} else {
$orderBy = 'id';
}
$tableData = $class::orderBy($orderBy)->get();
if ($tableData->count()) {
Cache::forever($name, $tableData);
}
}
}
/*Build template cache*/
if (request()->has('clear_cache') || ! Cache::has('templates'))
$this->buildTemplates();
}
private function buildTemplates($name = 'templates')
{
$data = [
'invoice' => [
'subject' => EmailTemplateDefaults::emailInvoiceSubject(),
'body' => EmailTemplateDefaults::emailInvoiceTemplate(),
],
'quote' => [
'subject' => EmailTemplateDefaults::emailQuoteSubject(),
'body' => EmailTemplateDefaults::emailQuoteTemplate(),
],
'payment' => [
'subject' => EmailTemplateDefaults::emailPaymentSubject(),
'body' => EmailTemplateDefaults::emailPaymentTemplate(),
],
'reminder1' => [
'subject' => EmailTemplateDefaults::emailReminder1Subject(),
'body' => EmailTemplateDefaults::emailReminder1Template(),
],
'reminder2' => [
'subject' => EmailTemplateDefaults::emailReminder2Subject(),
'body' => EmailTemplateDefaults::emailReminder2Template(),
],
'reminder3' => [
'subject' => EmailTemplateDefaults::emailReminder3Subject(),
'body' => EmailTemplateDefaults::emailReminder3Template(),
],
'reminder_endless' => [
'subject' => EmailTemplateDefaults::emailReminderEndlessSubject(),
'body' => EmailTemplateDefaults::emailReminderEndlessTemplate(),
],
'statement' => [
'subject' => EmailTemplateDefaults::emailStatementSubject(),
'body' => EmailTemplateDefaults::emailStatementTemplate(),
],
];
Cache::forever($name, $data);
}
}

View File

@ -64,16 +64,17 @@
"laravel/ui": "^3.0"
},
"require-dev": {
"wildbit/postmark-php": "^4.0",
"anahkiasen/former": "^4.2",
"barryvdh/laravel-debugbar": "^3.4",
"brianium/paratest": "^5.0",
"darkaonline/l5-swagger": "^8.0",
"facade/ignition": "^2.3.6",
"filp/whoops": "^2.7",
"fzaninotto/faker": "^1.9.1",
"mockery/mockery": "^1.3.1",
"nunomaduro/collision": "^5.0",
"phpunit/phpunit": "^9.0",
"fzaninotto/faker": "^1.9.1",
"facade/ignition": "^2.3.6"
"wildbit/postmark-php": "^4.0"
},
"autoload": {
"psr-4": {

View File

@ -1,5 +1,5 @@
{
"video": false,
"baseUrl": "http://invoiceninja.wip/",
"baseUrl": "http://ninja.test:8000/",
"chromeWebSecurity": false
}