1
0
mirror of https://github.com/invoiceninja/invoiceninja.git synced 2024-11-10 13:12:50 +01:00

Merge remote-tracking branch 'upstream/develop' into develop

This commit is contained in:
David Bomba 2016-05-03 20:47:37 +10:00
commit b36be7646c
51 changed files with 398 additions and 407 deletions

View File

@ -34,6 +34,13 @@ class AccountApiController extends BaseAPIController
$this->accountRepo = $accountRepo;
}
public function ping()
{
$headers = Utils::getApiHeaders();
return Response::make(RESULT_SUCCESS, 200, $headers);
}
public function register(RegisterRequest $request)
{

View File

@ -306,7 +306,7 @@ class AppController extends BaseController
public function stats()
{
if (Input::get('password') != env('RESELLER_PASSWORD')) {
if ( ! hash_equals(Input::get('password'), env('RESELLER_PASSWORD'))) {
sleep(3);
return '';
}

View File

@ -3,6 +3,7 @@
use Session;
use Utils;
use Auth;
use Log;
use Input;
use Response;
use Request;
@ -66,11 +67,33 @@ class BaseAPIController extends Controller
} else {
$this->manager->setSerializer(new ArraySerializer());
}
if (Utils::isNinjaDev()) {
\DB::enableQueryLog();
}
}
protected function returnList($query)
protected function handleAction($request)
{
$entity = $request->entity();
$action = $request->action;
$repo = Utils::toCamelCase($this->entityType) . 'Repo';
$this->$repo->$action($entity);
return $this->itemResponse($entity);
}
protected function listResponse($query)
{
//\DB::enableQueryLog();
$transformerClass = EntityModel::getTransformerName($this->entityType);
$transformer = new $transformerClass(Auth::user()->account, Input::get('serializer'));
$include = $transformer->getDefaultIncludes();
$include = $this->getRequestIncludes($include);
$query->with($include);
if ($clientPublicId = Input::get('client_id')) {
$filter = function($query) use ($clientPublicId) {
$query->where('public_id', '=', $clientPublicId);
@ -86,12 +109,18 @@ class BaseAPIController extends Controller
}
}
$transformerClass = EntityModel::getTransformerName($this->entityType);
$transformer = new $transformerClass(Auth::user()->account, Input::get('serializer'));
$data = $this->createCollection($query, $transformer, $this->entityType);
//return \DB::getQueryLog();
return $this->response($data);
}
protected function itemResponse($item)
{
$transformerClass = EntityModel::getTransformerName($this->entityType);
$transformer = new $transformerClass(Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($item, $transformer, $this->entityType);
return $this->response($data);
}
@ -112,8 +141,9 @@ class BaseAPIController extends Controller
}
if (is_a($query, "Illuminate\Database\Eloquent\Builder")) {
$limit = min(MAX_API_PAGE_SIZE, Input::get('per_page', DEFAULT_API_PAGE_SIZE));
$resource = new Collection($query->get(), $transformer, $entityType);
$resource->setPaginator(new IlluminatePaginatorAdapter($query->paginate()));
$resource->setPaginator(new IlluminatePaginatorAdapter($query->paginate($limit)));
} else {
$resource = new Collection($query, $transformer, $entityType);
}
@ -123,6 +153,12 @@ class BaseAPIController extends Controller
protected function response($response)
{
if (Utils::isNinjaDev()) {
$count = count(\DB::getQueryLog());
Log::info(Request::method() . ' - ' . Request::url() . ": $count queries");
//Log::info(print_r(\DB::getQueryLog(), true));
}
$index = Request::get('index') ?: 'data';
if ($index == 'none') {
@ -155,10 +191,9 @@ class BaseAPIController extends Controller
}
protected function getIncluded()
protected function getRequestIncludes($data)
{
$data = ['user'];
$data[] = 'user';
$included = Request::get('include');
$included = explode(',', $included);

View File

@ -24,28 +24,4 @@ class BaseController extends Controller
$this->layout = View::make($this->layout);
}
}
protected function authorizeCreate() {
$this->authorize('create', $this->entityType);
}
/*
protected function authorizeUpdate($entity) {
$this->authorize('edit', $entity);
}
*/
protected function authorizeUpdate($input){
$creating = empty($input['public_id']) || $input['public_id'] == '-1';
if($creating){
$this->authorize('create', $this->entityType);
}
else{
$className = Utils::getEntityName($this->entityType);
$object = call_user_func(array("App\\Models\\{$className}", 'scope'), $input['public_id'])->firstOrFail();
$this->authorize('edit', $object);
}
}
}

View File

@ -10,29 +10,19 @@ use App\Ninja\Repositories\ClientRepository;
use App\Http\Requests\CreateClientRequest;
use App\Http\Controllers\BaseAPIController;
use App\Ninja\Transformers\ClientTransformer;
use App\Services\ClientService;
use App\Http\Requests\UpdateClientRequest;
class ClientApiController extends BaseAPIController
{
protected $clientRepo;
protected $clientService;
protected $entityType = ENTITY_CLIENT;
public function __construct(ClientRepository $clientRepo, ClientService $clientService)
public function __construct(ClientRepository $clientRepo)
{
parent::__construct();
$this->clientRepo = $clientRepo;
$this->clientService = $clientService;
}
public function ping()
{
$headers = Utils::getApiHeaders();
return Response::make('', 200, $headers);
}
/**
@ -54,7 +44,6 @@ class ClientApiController extends BaseAPIController
public function index()
{
$clients = Client::scope()
->with($this->getIncluded())
->orderBy('created_at', 'desc')
->withTrashed();
@ -65,7 +54,7 @@ class ClientApiController extends BaseAPIController
});
}
return $this->returnList($clients);
return $this->listResponse($clients);
}
/**
@ -93,14 +82,7 @@ class ClientApiController extends BaseAPIController
{
$client = $this->clientRepo->save($request->input());
$client = Client::scope($client->public_id)
->with('country', 'contacts', 'industry', 'size', 'currency')
->first();
$transformer = new ClientTransformer(Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($client, $transformer, ENTITY_CLIENT);
return $this->response($data);
return $this->itemResponse($client);
}
/**
@ -127,51 +109,15 @@ class ClientApiController extends BaseAPIController
public function update(UpdateClientRequest $request, $publicId)
{
if ($request->action == ACTION_ARCHIVE) {
$client = Client::scope($publicId)->withTrashed()->first();
if(!$client)
return $this->errorResponse(['message'=>'Record not found'], 400);
$this->clientRepo->archive($client);
$transformer = new ClientTransformer(Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($client, $transformer, ENTITY_CLIENT);
return $this->response($data);
if ($request->action) {
return $this->handleAction($request);
}
else if ($request->action == ACTION_RESTORE){
$client = Client::scope($publicId)->withTrashed()->first();
if(!$client)
return $this->errorResponse(['message'=>'Client not found.'], 400);
$this->clientRepo->restore($client);
$transformer = new ClientTransformer(Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($client, $transformer, ENTITY_CLIENT);
return $this->response($data);
}
$data = $request->input();
$data['public_id'] = $publicId;
$this->clientRepo->save($data);
$client = $this->clientRepo->save($data, $request->entity());
$client = Client::scope($publicId)
->with('country', 'contacts', 'industry', 'size', 'currency')
->first();
if(!$client)
return $this->errorResponse(['message'=>'Client not found.'],400);
$transformer = new ClientTransformer(Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($client, $transformer, ENTITY_CLIENT);
return $this->response($data);
return $this->itemResponse($client);
}

View File

@ -32,7 +32,7 @@ class ExpenseApiController extends BaseAPIController
->withTrashed()
->orderBy('created_at','desc');
return $this->returnList($expenses);
return $this->listResponse($expenses);
}
public function update()

View File

@ -146,7 +146,7 @@ class ExpenseController extends BaseController
$data = $request->input();
$data['documents'] = $request->file('documents');
$expense = $this->expenseService->save($data);
$expense = $this->expenseService->save($data, $request->entity());
Session::flash('message', trans('texts.updated_expense'));

View File

@ -19,6 +19,7 @@ use App\Ninja\Repositories\InvoiceRepository;
use App\Ninja\Mailers\ContactMailer as Mailer;
use App\Http\Controllers\BaseAPIController;
use App\Ninja\Transformers\InvoiceTransformer;
use App\Http\Requests\InvoiceRequest;
use App\Http\Requests\CreateInvoiceAPIRequest;
use App\Http\Requests\UpdateInvoiceAPIRequest;
use App\Services\InvoiceService;
@ -60,10 +61,10 @@ class InvoiceApiController extends BaseAPIController
{
$invoices = Invoice::scope()
->withTrashed()
->with(array_merge(['invoice_items'], $this->getIncluded()))
->with('invoice_items')
->orderBy('created_at', 'desc');
return $this->returnList($invoices);
return $this->listResponse($invoices);
}
/**
@ -83,17 +84,9 @@ class InvoiceApiController extends BaseAPIController
* )
*/
public function show($publicId)
public function show(InvoiceRequest $request)
{
$invoice = Invoice::scope($publicId)->withTrashed()->first();
if(!$invoice)
return $this->errorResponse(['message'=>'Invoice does not exist!'], 404);
$transformer = new InvoiceTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($invoice, $transformer, 'invoice');
return $this->response($data);
return $this->itemResponse($request->entity());
}
/**
@ -188,11 +181,11 @@ class InvoiceApiController extends BaseAPIController
}
}
$invoice = Invoice::scope($invoice->public_id)->with('client', 'invoice_items', 'invitations')->first();
$transformer = new InvoiceTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($invoice, $transformer, 'invoice');
return $this->response($data);
$invoice = Invoice::scope($invoice->public_id)
->with('client', 'invoice_items', 'invitations')
->first();
return $this->itemResponse($invoice);
}
private function prepareData($data, $client)
@ -278,36 +271,21 @@ class InvoiceApiController extends BaseAPIController
$item[$key] = $val;
}
}
return $item;
}
public function emailInvoice()
public function emailInvoice(InvoiceRequest $request)
{
$data = Input::all();
$error = null;
$invoice = $request->entity();
$invoice = Invoice::scope($data['id'])->withTrashed()->first();
if(!$invoice)
return $this->errorResponse(['message'=>'Invoice does not exist.'], 400);
$this->mailer->sendInvoice($invoice, false, false);
if($error) {
return $this->errorResponse(['message'=>'There was an error sending the invoice'], 400);
}
else {
$response = json_encode(RESULT_SUCCESS, JSON_PRETTY_PRINT);
}
$this->mailer->sendInvoice($invoice);
$response = json_encode(RESULT_SUCCESS, JSON_PRETTY_PRINT);
$headers = Utils::getApiHeaders();
return Response::make($response, $error ? 400 : 200, $headers);
return Response::make($response, 200, $headers);
}
/**
* @SWG\Put(
* path="/invoices",
@ -331,32 +309,12 @@ class InvoiceApiController extends BaseAPIController
*/
public function update(UpdateInvoiceAPIRequest $request, $publicId)
{
if ($request->action == ACTION_ARCHIVE) {
$invoice = Invoice::scope($publicId)->firstOrFail();
$this->invoiceRepo->archive($invoice);
$transformer = new InvoiceTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($invoice, $transformer, 'invoice');
return $this->response($data);
}
else if ($request->action == ACTION_CONVERT) {
$quote = Invoice::scope($publicId)->firstOrFail();
if ($request->action == ACTION_CONVERT) {
$quote = $request->entity();
$invoice = $this->invoiceRepo->cloneInvoice($quote, $quote->id);
$transformer = new InvoiceTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($invoice, $transformer, 'invoice');
return $this->response($data);
}
else if ($request->action == ACTION_RESTORE) {
$invoice = Invoice::scope($publicId)->withTrashed()->firstOrFail();
$this->invoiceRepo->restore($invoice);
$transformer = new InvoiceTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($invoice, $transformer, 'invoice');
return $this->response($data);
return $this->itemResponse($invoice);
} elseif ($request->action) {
return $this->handleAction($request);
}
else if ($request->action == ACTION_CLONE) {
@ -370,13 +328,13 @@ class InvoiceApiController extends BaseAPIController
}
$data = $request->input();
$data['public_id'] = $publicId;
$this->invoiceService->save($data);
$this->invoiceService->save($data, $request->entity());
$invoice = Invoice::scope($publicId)->with('client', 'invoice_items', 'invitations')->firstOrFail();
$transformer = new InvoiceTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($invoice, $transformer, 'invoice');
return $this->response($data);
$invoice = Invoice::scope($publicId)
->with('client', 'invoice_items', 'invitations')
->firstOrFail();
return $this->itemResponse($invoice);
}
/**

View File

@ -396,9 +396,7 @@ class InvoiceController extends BaseController
{
$data = $request->input();
$data['documents'] = $request->file('documents');
$this->authorizeUpdate($data);
$action = Input::get('action');
$entityType = Input::get('entityType');
@ -435,13 +433,11 @@ class InvoiceController extends BaseController
{
$data = $request->input();
$data['documents'] = $request->file('documents');
$this->authorizeUpdate($data);
$action = Input::get('action');
$entityType = Input::get('entityType');
$invoice = $this->invoiceService->save($data);
$invoice = $this->invoiceService->save($data, $request->entity());
$entityType = $invoice->getEntityType();
$message = trans("texts.updated_{$entityType}");
Session::flash('message', $message);

View File

@ -12,6 +12,8 @@ use App\Ninja\Repositories\PaymentRepository;
use App\Http\Controllers\BaseAPIController;
use App\Ninja\Transformers\PaymentTransformer;
use App\Ninja\Transformers\InvoiceTransformer;
use App\Http\Requests\UpdatePaymentRequest;
use App\Http\Requests\CreatePaymentAPIRequest;
class PaymentApiController extends BaseAPIController
{
@ -47,10 +49,10 @@ class PaymentApiController extends BaseAPIController
{
$payments = Payment::scope()
->withTrashed()
->with(array_merge(['client.contacts', 'invitation', 'user', 'invoice'], $this->getIncluded()))
->with(['client.contacts', 'invitation', 'user', 'invoice'])
->orderBy('created_at', 'desc');
return $this->returnList($payments);
return $this->listResponse($payments);
}
/**
@ -75,39 +77,17 @@ class PaymentApiController extends BaseAPIController
* )
*/
public function update(Request $request, $publicId)
public function update(UpdatePaymentRequest $request, $publicId)
{
$data = Input::all();
if ($request->action) {
return $this->handleAction($request);
}
$data = $request->input();
$data['public_id'] = $publicId;
$error = false;
if ($request->action == ACTION_ARCHIVE) {
$payment = Payment::scope($publicId)->withTrashed()->firstOrFail();
$this->paymentRepo->archive($payment);
$transformer = new PaymentTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($payment, $transformer, 'invoice');
return $this->response($data);
}
$payment = $this->paymentRepo->save($data);
if ($error) {
return $error;
}
/*
$invoice = Invoice::scope($data['invoice_id'])->with('client', 'invoice_items', 'invitations')->with(['payments' => function($query) {
$query->withTrashed();
}])->withTrashed()->first();
*/
$transformer = new PaymentTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($payment, $transformer, 'invoice');
return $this->response($data);
$payment = $this->paymentRepo->save($data, $request->entity());
return $this->itemResponse($payment);
}
@ -132,49 +112,15 @@ class PaymentApiController extends BaseAPIController
* )
* )
*/
public function store()
public function store(CreatePaymentAPIRequest $request)
{
$data = Input::all();
$error = false;
if (isset($data['invoice_id'])) {
$invoice = Invoice::scope($data['invoice_id'])->with('client')->first();
if ($invoice) {
$data['invoice_id'] = $invoice->id;
$data['client_id'] = $invoice->client->id;
} else {
$error = trans('validation.not_in', ['attribute' => 'invoice_id']);
}
} else {
$error = trans('validation.not_in', ['attribute' => 'invoice_id']);
}
if (!isset($data['transaction_reference'])) {
$data['transaction_reference'] = '';
}
if ($error) {
return $error;
}
$payment = $this->paymentRepo->save($data);
$payment = $this->paymentRepo->save($request->input());
if (Input::get('email_receipt')) {
$this->contactMailer->sendPaymentConfirmation($payment);
}
/*
$invoice = Invoice::scope($invoice->public_id)->with('client', 'invoice_items', 'invitations')->with(['payments' => function($query) {
$query->withTrashed();
}])->first();
*/
$transformer = new PaymentTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($payment, $transformer, 'invoice');
return $this->response($data);
return $this->itemResponse($payment);
}
/**
@ -207,11 +153,6 @@ class PaymentApiController extends BaseAPIController
$this->paymentRepo->delete($payment);
/*
$invoice = Invoice::scope($invoiceId)->with('client', 'invoice_items', 'invitations')->with(['payments' => function($query) {
$query->withTrashed();
}])->first();
*/
$transformer = new PaymentTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($payment, $transformer, 'invoice');

View File

@ -603,7 +603,7 @@ class PaymentController extends BaseController
public function update(UpdatePaymentRequest $request)
{
$payment = $this->paymentRepo->save($request->input());
$payment = $this->paymentRepo->save($request->input(), $request->entity());
Session::flash('message', trans('texts.updated_payment'));

View File

@ -1,34 +1,20 @@
<?php namespace App\Http\Controllers;
use App\Ninja\Repositories\ProductRepository;
use App\Ninja\Transformers\ProductTransformer;
use Auth;
use Str;
use DB;
use Datatable;
use Utils;
use URL;
use View;
use Input;
use Session;
use Redirect;
use App\Models\Product;
use App\Models\TaxRate;
use App\Services\ProductService;
use App\Ninja\Repositories\ProductRepository;
use App\Http\Requests\CreateProductRequest;
use App\Http\Requests\UpdateProductRequest;
class ProductApiController extends BaseAPIController
{
protected $productService;
protected $productRepo;
protected $entityType = ENTITY_PRODUCT;
public function __construct(ProductService $productService, ProductRepository $productRepo)
public function __construct(ProductRepository $productRepo)
{
parent::__construct();
$this->productService = $productService;
$this->productRepo = $productRepo;
}
@ -38,61 +24,31 @@ class ProductApiController extends BaseAPIController
->withTrashed()
->orderBy('created_at', 'desc');
return $this->returnList($products);
return $this->listResponse($products);
}
public function getDatatable()
public function store(CreateProductRequest $request)
{
return $this->productService->getDatatable(Auth::user()->account_id);
$product = $this->productRepo->save($request->input());
return $this->itemResponse($product);
}
public function store()
public function update(UpdateProductRequest $request, $publicId)
{
return $this->save();
}
public function update(\Illuminate\Http\Request $request, $publicId)
{
if ($request->action == ACTION_ARCHIVE) {
$product = Product::scope($publicId)->withTrashed()->firstOrFail();
$this->productRepo->archive($product);
$transformer = new ProductTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($product, $transformer, 'products');
return $this->response($data);
if ($request->action) {
return $this->handleAction($request);
}
else
return $this->save($publicId);
$data = $request->input();
$data['public_id'] = $publicId;
$product = $this->productRepo->save($data, $request->entity());
return $this->itemResponse($product);
}
public function destroy($publicId)
{
//stub
}
private function save($productPublicId = false)
{
if ($productPublicId) {
$product = Product::scope($productPublicId)->firstOrFail();
} else {
$product = Product::createNew();
}
$product->product_key = trim(Input::get('product_key'));
$product->notes = trim(Input::get('notes'));
$product->cost = trim(Input::get('cost'));
//$product->default_tax_rate_id = Input::get('default_tax_rate_id');
$product->save();
$transformer = new ProductTransformer(\Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($product, $transformer, 'products');
return $this->response($data);
}
}

View File

@ -42,10 +42,9 @@ class TaskApiController extends BaseAPIController
{
$payments = Task::scope()
->withTrashed()
->with($this->getIncluded())
->orderBy('created_at', 'desc');
return $this->returnList($payments);
return $this->listResponse($payments);
}
/**

View File

@ -1,26 +1,20 @@
<?php namespace App\Http\Controllers;
use App\Services\TaxRateService;
use App\Ninja\Repositories\TaxRateRepository;
use App\Ninja\Transformers\TaxRateTransformer;
use Auth;
use App\Models\TaxRate;
use App\Ninja\Repositories\TaxRateRepository;
use App\Http\Requests\CreateTaxRateRequest;
use App\Http\Requests\UpdateTaxRateRequest;
class TaxRateApiController extends BaseAPIController
{
protected $taxRateService;
protected $taxRateRepo;
protected $entityType = ENTITY_TAX_RATE;
public function __construct(TaxRateService $taxRateService, TaxRateRepository $taxRateRepo)
public function __construct(TaxRateRepository $taxRateRepo)
{
parent::__construct();
$this->taxRateService = $taxRateService;
$this->taxRateRepo = $taxRateRepo;
}
@ -29,38 +23,32 @@ class TaxRateApiController extends BaseAPIController
$taxRates = TaxRate::scope()
->withTrashed()
->orderBy('created_at', 'desc');
return $this->returnList($taxRates);
return $this->listResponse($taxRates);
}
public function store(CreateTaxRateRequest $request)
{
return $this->save($request);
$taxRate = $this->taxRateRepo->save($request->input());
return $this->itemResponse($taxRate);
}
public function update(UpdateTaxRateRequest $request, $taxRatePublicId)
public function update(UpdateTaxRateRequest $request, $publicId)
{
$taxRate = TaxRate::scope($taxRatePublicId)->firstOrFail();
if ($request->action == ACTION_ARCHIVE) {
$this->taxRateRepo->archive($taxRate);
$transformer = new TaxRateTransformer(Auth::user()->account, $request->serializer);
$data = $this->createItem($taxRate, $transformer, 'tax_rates');
return $this->response($data);
} else {
return $this->save($request, $taxRate);
if ($request->action) {
return $this->handleAction($request);
}
$data = $request->input();
$data['public_id'] = $publicId;
$taxRate = $this->taxRateRepo->save($data, $request->entity());
return $this->itemResponse($taxRate);
}
private function save($request, $taxRate = false)
public function destroy($publicId)
{
$taxRate = $this->taxRateRepo->save($request->input(), $taxRate);
$transformer = new TaxRateTransformer(\Auth::user()->account, $request->serializer);
$data = $this->createItem($taxRate, $transformer, 'tax_rates');
return $this->response($data);
//stub
}
}

View File

@ -75,9 +75,7 @@ class TaxRateController extends BaseController
public function update(UpdateTaxRateRequest $request, $publicId)
{
$taxRate = TaxRate::scope($publicId)->firstOrFail();
$this->taxRateRepo->save($request->input(), $taxRate);
$this->taxRateRepo->save($request->input(), $request->entity());
Session::flash('message', trans('texts.updated_tax_rate'));
return Redirect::to('settings/' . ACCOUNT_TAX_RATES);

View File

@ -30,7 +30,7 @@ class UserApiController extends BaseAPIController
->withTrashed()
->orderBy('created_at', 'desc');
return $this->returnList($users);
return $this->listResponse($users);
}
/*
@ -42,11 +42,6 @@ class UserApiController extends BaseAPIController
public function update(UpdateUserRequest $request, $userPublicId)
{
/*
// temporary fix for ids starting at 0
$userPublicId -= 1;
$user = User::scope($userPublicId)->firstOrFail();
*/
$user = Auth::user();
if ($request->action == ACTION_ARCHIVE) {

View File

@ -49,11 +49,10 @@ class VendorApiController extends BaseAPIController
public function index()
{
$vendors = Vendor::scope()
->with($this->getIncluded())
->withTrashed()
->orderBy('created_at', 'desc');
return $this->returnList($vendors);
return $this->listResponse($vendors);
}
/**
@ -85,8 +84,6 @@ class VendorApiController extends BaseAPIController
->with('country', 'vendorcontacts', 'industry', 'size', 'currency')
->first();
$transformer = new VendorTransformer(Auth::user()->account, Input::get('serializer'));
$data = $this->createItem($vendor, $transformer, ENTITY_VENDOR);
return $this->response($data);
return $this->itemResponse($vendor);
}
}

View File

@ -182,7 +182,7 @@ class VendorController extends BaseController
*/
public function update(UpdateVendorRequest $request)
{
$vendor = $this->vendorService->save($request->input());
$vendor = $this->vendorService->save($request->input(), $request->entity());
Session::flash('message', trans('texts.updated_vendor'));

View File

@ -0,0 +1,48 @@
<?php namespace App\Http\Requests;
use App\Models\Invoice;
class CreatePaymentAPIRequest extends PaymentRequest
{
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return $this->user()->can('create', ENTITY_PAYMENT);
}
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
if ( ! $this->invoice_id || ! $this->amount) {
return [
'invoice_id' => 'required',
'amount' => 'required',
];
}
$invoice = Invoice::scope($this->invoice_id)->firstOrFail();
$this->merge([
'invoice_id' => $invoice->id,
'client_id' => $invoice->client->id,
]);
$rules = array(
'amount' => "required|less_than:{$invoice->balance}|positive",
);
if ($this->payment_type_id == PAYMENT_TYPE_CREDIT) {
$rules['payment_type_id'] = 'has_credit:' . $invoice->client->public_id . ',' . $this->amount;
}
return $rules;
}
}

View File

@ -0,0 +1,26 @@
<?php namespace App\Http\Requests;
class CreateProductRequest extends ProductRequest
{
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return $this->user()->can('create', ENTITY_PRODUCT);
}
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
return [
'product_key' => 'required',
];
}
}

View File

@ -3,7 +3,7 @@
use App\Http\Requests\Request;
use Illuminate\Validation\Factory;
class CreateTaxRateRequest extends Request
class CreateTaxRateRequest extends TaxRateRequest
{
// Expenses
/**
@ -13,7 +13,7 @@ class CreateTaxRateRequest extends Request
*/
public function authorize()
{
return true;
return $this->user()->can('create', ENTITY_TAX_RATE);
}
/**

View File

@ -0,0 +1,6 @@
<?php namespace App\Http\Requests;
class ProductRequest extends EntityRequest {
protected $entityType = ENTITY_PRODUCT;
}

View File

@ -0,0 +1,7 @@
<?php namespace App\Http\Requests;
class TaxRateRequest extends EntityRequest {
protected $entityType = ENTITY_TAX_RATE;
}

View File

@ -0,0 +1,26 @@
<?php namespace App\Http\Requests;
class UpdateProductRequest extends ProductRequest
{
/**
* Determine if the user is authorized to make this request.
*
* @return bool
*/
public function authorize()
{
return $this->user()->can('edit', $this->entity());
}
/**
* Get the validation rules that apply to the request.
*
* @return array
*/
public function rules()
{
return [
'product_key' => 'required',
];
}
}

View File

@ -3,7 +3,7 @@
use App\Http\Requests\Request;
use Illuminate\Validation\Factory;
class UpdateTaxRateRequest extends Request
class UpdateTaxRateRequest extends TaxRateRequest
{
// Expenses
/**
@ -13,7 +13,7 @@ class UpdateTaxRateRequest extends Request
*/
public function authorize()
{
return true;
return $this->user()->can('edit', $this->entity());
}
/**

View File

@ -14,7 +14,7 @@ class UpdateUserRequest extends Request
*/
public function authorize()
{
return true;
return $this->user()->can('edit', $this->entity());
}
/**

View File

@ -246,7 +246,7 @@ Route::group([
// Route groups for API
Route::group(['middleware' => 'api', 'prefix' => 'api/v1'], function()
{
Route::get('ping', 'ClientApiController@ping');
Route::get('ping', 'AccountApiController@ping');
Route::post('login', 'AccountApiController@login');
Route::post('register', 'AccountApiController@register');
Route::get('static', 'AccountApiController@getStaticData');
@ -600,6 +600,8 @@ if (!defined('CONTACT_EMAIL')) {
define('TEST_USERNAME', 'user@example.com');
define('TEST_PASSWORD', 'password');
define('API_SECRET', 'API_SECRET');
define('DEFAULT_API_PAGE_SIZE', 15);
define('MAX_API_PAGE_SIZE', 100);
define('IOS_PRODUCTION_PUSH', env('IOS_PRODUCTION_PUSH', 'ninjaIOS'));
define('IOS_DEV_PUSH', env('IOS_DEV_PUSH', 'devNinjaIOS'));

View File

@ -676,7 +676,7 @@ class Utils
public static function getEntityName($entityType)
{
return ucwords(str_replace('_', ' ', $entityType));
return ucwords(Utils::toCamelCase($entityType));
}
public static function getClientDisplayName($model)

View File

@ -110,7 +110,7 @@ class EntityModel extends Eloquent
{
return 'App\\Ninja\\Transformers\\' . ucwords(Utils::toCamelCase($entityType)) . 'Transformer';
}
public function setNullValues()
{
foreach ($this->fillable as $field) {

View File

@ -8,6 +8,14 @@ class Product extends EntityModel
use SoftDeletes;
protected $dates = ['deleted_at'];
protected $fillable = [
'product_key',
'notes',
'cost',
'qty',
'default_tax_rate_id',
];
public function getEntityType()
{
return ENTITY_PRODUCT;

View File

@ -72,12 +72,13 @@ class ClientRepository extends BaseRepository
if ($client) {
// do nothing
} if (!$publicId || $publicId == '-1') {
} elseif (!$publicId || $publicId == '-1') {
$client = Client::createNew();
} else {
$client = Client::scope($publicId)->with('contacts')->firstOrFail();
\Log::warning('Entity not set in client repo save');
}
// convert currency code to id
if (isset($data['currency_code'])) {
$currencyCode = strtolower($data['currency_code']);

View File

@ -59,12 +59,15 @@ class CreditRepository extends BaseRepository
return $query;
}
public function save($input)
public function save($input, $credit = null)
{
$publicId = isset($data['public_id']) ? $data['public_id'] : false;
if ($publicId) {
if ($credit) {
// do nothing
} elseif ($publicId) {
$credit = Credit::scope($publicId)->firstOrFail();
\Log::warning('Entity not set in credit repo save');
} else {
$credit = Credit::createNew();
}

View File

@ -122,12 +122,15 @@ class ExpenseRepository extends BaseRepository
return $query;
}
public function save($input)
public function save($input, $expense = null)
{
$publicId = isset($input['public_id']) ? $input['public_id'] : false;
if ($publicId) {
if ($expense) {
// do nothing
} elseif ($publicId) {
$expense = Expense::scope($publicId)->firstOrFail();
\Log::warning('Entity not set in expense repo save');
} else {
$expense = Expense::createNew();
}

View File

@ -201,14 +201,16 @@ class InvoiceRepository extends BaseRepository
->make();
}
public function save($data)
public function save($data, $invoice = null)
{
$account = \Auth::user()->account;
$publicId = isset($data['public_id']) ? $data['public_id'] : false;
$isNew = !$publicId || $publicId == '-1';
if ($isNew) {
if ($invoice) {
// do nothing
} elseif ($isNew) {
$entityType = ENTITY_INVOICE;
if (isset($data['is_recurring']) && filter_var($data['is_recurring'], FILTER_VALIDATE_BOOLEAN)) {
$entityType = ENTITY_RECURRING_INVOICE;
@ -224,6 +226,7 @@ class InvoiceRepository extends BaseRepository
}
} else {
$invoice = Invoice::scope($publicId)->firstOrFail();
\Log::warning('Entity not set in invoice repo save');
}
$invoice->fill($data);

View File

@ -123,12 +123,15 @@ class PaymentRepository extends BaseRepository
return $query;
}
public function save($input)
public function save($input, $payment = null)
{
$publicId = isset($input['public_id']) ? $input['public_id'] : false;
if ($publicId) {
if ($payment) {
// do nothing
} elseif ($publicId) {
$payment = Payment::scope($publicId)->firstOrFail();
\Log::warning('Entity not set in payment repo save');
} else {
$payment = Payment::createNew();
}

View File

@ -1,6 +1,7 @@
<?php namespace App\Ninja\Repositories;
use DB;
use App\Models\Product;
use App\Ninja\Repositories\BaseRepository;
class ProductRepository extends BaseRepository
@ -29,4 +30,24 @@ class ProductRepository extends BaseRepository
'products.deleted_at'
);
}
public function save($data, $product = null)
{
$publicId = isset($data['public_id']) ? $data['public_id'] : false;
if ($product) {
// do nothing
} elseif ($publicId) {
$product = Product::scope($publicId)->firstOrFail();
\Log::warning('Entity not set in product repo save');
} else {
$product = Product::createNew();
}
$product->fill($data);
$product->save();
return $product;
}
}

View File

@ -64,10 +64,13 @@ class TaskRepository
return $query;
}
public function save($publicId, $data)
public function save($publicId, $data, $task = null)
{
if ($publicId) {
if ($task) {
// do nothing
} elseif ($publicId) {
$task = Task::scope($publicId)->firstOrFail();
\Log::warning('Entity not set in task repo save');
} else {
$task = Task::createNew();
}

View File

@ -20,14 +20,15 @@ class TaxRateRepository extends BaseRepository
->select('tax_rates.public_id', 'tax_rates.name', 'tax_rates.rate', 'tax_rates.deleted_at');
}
public function save($data, $taxRate = false)
public function save($data, $taxRate = null)
{
if ( ! $taxRate) {
if (isset($data['public_id'])) {
$taxRate = TaxRate::scope($data['public_id'])->firstOrFail();
} else {
$taxRate = TaxRate::createNew();
}
if ($taxRate) {
// do nothing
} elseif (isset($data['public_id'])) {
$taxRate = TaxRate::scope($data['public_id'])->firstOrFail();
\Log::warning('Entity not set in tax rate repo save');
} else {
$taxRate = TaxRate::createNew();
}
$taxRate->fill($data);

View File

@ -62,14 +62,17 @@ class VendorRepository extends BaseRepository
return $query;
}
public function save($data)
public function save($data, $vendor = null)
{
$publicId = isset($data['public_id']) ? $data['public_id'] : false;
if (!$publicId || $publicId == '-1') {
if ($vendor) {
// do nothing
} elseif (!$publicId || $publicId == '-1') {
$vendor = Vendor::createNew();
} else {
$vendor = Vendor::scope($publicId)->with('vendorcontacts')->firstOrFail();
\Log::warning('Entity not set in vendor repo save');
}
$vendor->fill($data);

View File

@ -58,7 +58,7 @@ class ClientTransformer extends EntityTransformer
public function includeInvoices(Client $client)
{
$transformer = new InvoiceTransformer($this->account, $this->serializer);
$transformer = new InvoiceTransformer($this->account, $this->serializer, $client);
return $this->includeCollection($client->invoices, $transformer, ENTITY_INVOICE);
}

View File

@ -37,4 +37,9 @@ class EntityTransformer extends TransformerAbstract
{
return $date ? $date->getTimestamp() : null;
}
public function getDefaultIncludes()
{
return $this->defaultIncludes;
}
}

View File

@ -6,9 +6,15 @@ use League\Fractal;
class ExpenseTransformer extends EntityTransformer
{
public function __construct($account = null, $serializer = null, $client = null)
{
parent::__construct($account, $serializer);
$this->client = $client;
}
public function transform(Expense $expense)
{
return [
'id' => (int) $expense->public_id,
'private_notes' => $expense->private_notes,
@ -25,7 +31,7 @@ class ExpenseTransformer extends EntityTransformer
'exchange_rate' => (float) $expense->exchange_rate,
'invoice_currency_id' => (int) $expense->invoice_currency_id,
'is_deleted' => (bool) $expense->is_deleted,
'client_id' => isset($expense->client->public_id) ? (int) $expense->client->public_id : null,
'client_id' => $this->client ? $this->client->public_id : (isset($expense->client->public_id) ? (int) $expense->client->public_id : null),
'invoice_id' => isset($expense->invoice->public_id) ? (int) $expense->invoice->public_id : null,
'vendor_id' => isset($expense->vendor->public_id) ? (int) $expense->vendor->public_id : null,
];

View File

@ -31,6 +31,13 @@ class InvoiceTransformer extends EntityTransformer
'expenses',
];
public function __construct($account = null, $serializer = null, $client = null)
{
parent::__construct($account, $serializer);
$this->client = $client;
}
public function includeInvoiceItems(Invoice $invoice)
{
$transformer = new InvoiceItemTransformer($this->account, $this->serializer);
@ -45,7 +52,7 @@ class InvoiceTransformer extends EntityTransformer
public function includePayments(Invoice $invoice)
{
$transformer = new PaymentTransformer($this->account, $this->serializer);
$transformer = new PaymentTransformer($this->account, $this->serializer, $invoice);
return $this->includeCollection($invoice->payments, $transformer, ENTITY_PAYMENT);
}
@ -68,7 +75,7 @@ class InvoiceTransformer extends EntityTransformer
'id' => (int) $invoice->public_id,
'amount' => (float) $invoice->amount,
'balance' => (float) $invoice->balance,
'client_id' => (int) $invoice->client->public_id,
'client_id' => (int) ($this->client ? $this->client->public_id : $invoice->client->public_id),
'invoice_status_id' => (int) $invoice->invoice_status_id,
'updated_at' => $this->getTimestamp($invoice->updated_at),
'archived_at' => $this->getTimestamp($invoice->deleted_at),

View File

@ -26,10 +26,11 @@ class PaymentTransformer extends EntityTransformer
];
public function __construct(Account $account)
public function __construct($account = null, $serializer = null, $invoice = null)
{
parent::__construct($account);
parent::__construct($account, $serializer);
$this->invoice = $invoice;
}
public function includeInvoice(Payment $payment)
@ -57,7 +58,7 @@ class PaymentTransformer extends EntityTransformer
'archived_at' => $this->getTimestamp($payment->deleted_at),
'is_deleted' => (bool) $payment->is_deleted,
'payment_type_id' => (int) $payment->payment_type_id,
'invoice_id' => (int) $payment->invoice->public_id,
'invoice_id' => (int) ($this->invoice ? $this->invoice->public_id : $payment->invoice->public_id),
];
}
}

View File

@ -21,6 +21,8 @@ class AuthServiceProvider extends ServiceProvider
\App\Models\Payment::class => \App\Policies\PaymentPolicy::class,
\App\Models\Task::class => \App\Policies\TaskPolicy::class,
\App\Models\Vendor::class => \App\Policies\VendorPolicy::class,
\App\Models\Product::class => \App\Policies\ProductPolicy::class,
\App\Models\TaxRate::class => \App\Policies\TaxRatePolicy::class,
];
/**

View File

@ -28,7 +28,7 @@ class ExpenseService extends BaseService
return $this->expenseRepo;
}
public function save($data)
public function save($data, $expense = null)
{
if (isset($data['client_id']) && $data['client_id']) {
$data['client_id'] = Client::getPrivateId($data['client_id']);
@ -38,7 +38,7 @@ class ExpenseService extends BaseService
$data['vendor_id'] = Vendor::getPrivateId($data['vendor_id']);
}
return $this->expenseRepo->save($data);
return $this->expenseRepo->save($data, $expense);
}
public function getDatatable($search)

View File

@ -30,7 +30,7 @@ class InvoiceService extends BaseService
return $this->invoiceRepo;
}
public function save($data)
public function save($data, $invoice = null)
{
if (isset($data['client'])) {
$canSaveClient = false;
@ -46,7 +46,7 @@ class InvoiceService extends BaseService
}
}
$invoice = $this->invoiceRepo->save($data);
$invoice = $this->invoiceRepo->save($data, $invoice);
$client = $invoice->client;
$client->load('contacts');

View File

@ -26,13 +26,13 @@ class VendorService extends BaseService
return $this->vendorRepo;
}
public function save($data)
public function save($data, $vendor = null)
{
if (Auth::user()->account->isNinjaAccount() && isset($data['plan'])) {
$this->ninjaRepo->updatePlanDetails($data['public_id'], $data);
}
return $this->vendorRepo->save($data);
return $this->vendorRepo->save($data, $vendor);
}
public function getDatatable($search)

View File

@ -1,4 +1,4 @@
<?php //[STAMP] 33bf8261bed0f36cf769e15182e6d905
<?php //[STAMP] a3cf36879dbbec28f15389e7d8d325a2
namespace _generated;
// This class was automatically generated by build task

View File

@ -70,6 +70,18 @@ class APICest
$this->createEntity('tax_rate', $data);
$this->listEntities('tax_rate');
$data = new stdClass;
$data->product_key = $this->faker->word;
$data->notes = $this->faker->realText(100);
$this->createEntity('product', $data);
$this->listEntities('product');
$data = new stdClass;
$data->name = $this->faker->word;
$data->vendorcontacts = [];
$this->createEntity('vendor', $data);
$this->listEntities('vendor');
$this->listEntities('account');
}
@ -79,6 +91,7 @@ class APICest
$response = $this->sendRequest("{$entityType}s", $data);
$entityId = $response->data->id;
PHPUnit_Framework_Assert::assertGreaterThan(0, $entityId);
return $entityId;

View File

@ -48,8 +48,9 @@ class ExpenseCest
// invoice expense
$I->executeJS('submitAction(\'invoice\')');
$I->wait(3);
$I->click('Save');
$I->wait(1);
$I->wait(3);
$I->see($clientEmail);
$I->see($amount);
}