mirror of
https://github.com/invoiceninja/invoiceninja.git
synced 2025-07-09 03:14:30 -04:00
Working on the API
This commit is contained in:
parent
c130e67e54
commit
6130626422
@ -7,7 +7,7 @@ use Input;
|
||||
use App\Models\Client;
|
||||
use App\Models\Account;
|
||||
use App\Ninja\Repositories\AccountRepository;
|
||||
|
||||
use Illuminate\Http\Request;
|
||||
use League\Fractal;
|
||||
use League\Fractal\Resource\Item;
|
||||
use League\Fractal\Manager;
|
||||
@ -23,6 +23,19 @@ class AccountApiController extends Controller
|
||||
$this->accountRepo = $accountRepo;
|
||||
}
|
||||
|
||||
public function login(Request $request)
|
||||
{
|
||||
if ( ! env(API_SECRET) || $request->api_secret !== env(API_SECRET)) {
|
||||
return 'Invalid secret';
|
||||
}
|
||||
|
||||
if (Auth::attempt(['email' => $request->email, 'password' => $request->password])) {
|
||||
return $this->accountRepo->createToken($request->token_name);
|
||||
} else {
|
||||
return 'Invalid credentials';
|
||||
}
|
||||
}
|
||||
|
||||
public function index()
|
||||
{
|
||||
$manager = new Manager();
|
||||
|
@ -98,13 +98,6 @@ class AuthController extends Controller {
|
||||
$users = $this->accountRepo->loadAccounts(Auth::user()->id);
|
||||
}
|
||||
Session::put(SESSION_USER_ACCOUNTS, $users);
|
||||
|
||||
if ($request->create_token) {
|
||||
if ( ! env(API_SECRET) || $request->api_secret !== env(API_SECRET)) {
|
||||
return 'Invalid secret';
|
||||
}
|
||||
return $this->accountRepo->createToken($request->token_name);
|
||||
}
|
||||
} elseif ($user) {
|
||||
$user->failed_logins = $user->failed_logins + 1;
|
||||
$user->save();
|
||||
|
@ -109,6 +109,7 @@ class DashboardController extends BaseController
|
||||
->leftJoin('contacts', 'contacts.client_id', '=', 'clients.id')
|
||||
->leftJoin('invoices', 'invoices.id', '=', 'payments.invoice_id')
|
||||
->where('payments.account_id', '=', Auth::user()->account_id)
|
||||
->where('payments.deleted_at', '=', null)
|
||||
->where('clients.deleted_at', '=', null)
|
||||
->where('contacts.deleted_at', '=', null)
|
||||
->where('contacts.is_primary', '=', true)
|
||||
|
@ -528,7 +528,7 @@ class PaymentController extends BaseController
|
||||
if (method_exists($gateway, 'completePurchase') && !$accountGateway->isGateway(GATEWAY_TWO_CHECKOUT)) {
|
||||
$details = $this->paymentService->getPaymentDetails($invitation, $accountGateway);
|
||||
$response = $gateway->completePurchase($details)->send();
|
||||
$ref = $response->getTransactionReference();
|
||||
$ref = $response->getTransactionReference() ?: $token;
|
||||
|
||||
if ($response->isSuccessful()) {
|
||||
$payment = $this->paymentService->createPayment($invitation, $ref, $payerId);
|
||||
|
@ -21,33 +21,38 @@ class ApiCheck {
|
||||
*/
|
||||
public function handle($request, Closure $next)
|
||||
{
|
||||
$loggingIn = $request->is('api/v1/login');
|
||||
$headers = Utils::getApiHeaders();
|
||||
|
||||
// check for a valid token
|
||||
$token = AccountToken::where('token', '=', Request::header('X-Ninja-Token'))->first(['id', 'user_id']);
|
||||
|
||||
if ($token) {
|
||||
Auth::loginUsingId($token->user_id);
|
||||
Session::set('token_id', $token->id);
|
||||
if ($loggingIn) {
|
||||
// do nothing
|
||||
} else {
|
||||
sleep(3);
|
||||
return Response::make('Invalid token', 403, $headers);
|
||||
// check for a valid token
|
||||
$token = AccountToken::where('token', '=', Request::header('X-Ninja-Token'))->first(['id', 'user_id']);
|
||||
|
||||
if ($token) {
|
||||
Auth::loginUsingId($token->user_id);
|
||||
Session::set('token_id', $token->id);
|
||||
} else {
|
||||
sleep(3);
|
||||
return Response::make('Invalid token', 403, $headers);
|
||||
}
|
||||
}
|
||||
|
||||
if (!Utils::isNinja()) {
|
||||
if (!Utils::isNinja() && !$loggingIn) {
|
||||
return $next($request);
|
||||
}
|
||||
|
||||
if (!Utils::isPro()) {
|
||||
if (!Utils::isPro() && !$loggingIn) {
|
||||
return Response::make('API requires pro plan', 403, $headers);
|
||||
} else {
|
||||
$accountId = Auth::user()->account->id;
|
||||
$key = Auth::check() ? Auth::user()->account->id : $request->getClientIp();
|
||||
|
||||
// http://stackoverflow.com/questions/1375501/how-do-i-throttle-my-sites-api-users
|
||||
$hour = 60 * 60;
|
||||
$hour_limit = 100; # users are limited to 100 requests/hour
|
||||
$hour_throttle = Cache::get("hour_throttle:{$accountId}", null);
|
||||
$last_api_request = Cache::get("last_api_request:{$accountId}", 0);
|
||||
$hour_throttle = Cache::get("hour_throttle:{$key}", null);
|
||||
$last_api_request = Cache::get("last_api_request:{$key}", 0);
|
||||
$last_api_diff = time() - $last_api_request;
|
||||
|
||||
if (is_null($hour_throttle)) {
|
||||
@ -66,11 +71,10 @@ class ApiCheck {
|
||||
return Response::make("Please wait {$wait} second(s)", 403, $headers);
|
||||
}
|
||||
|
||||
Cache::put("hour_throttle:{$accountId}", $new_hour_throttle, 10);
|
||||
Cache::put("last_api_request:{$accountId}", time(), 10);
|
||||
Cache::put("hour_throttle:{$key}", $new_hour_throttle, 10);
|
||||
Cache::put("last_api_request:{$key}", time(), 10);
|
||||
}
|
||||
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
|
||||
|
@ -7,6 +7,7 @@ class VerifyCsrfToken extends BaseVerifier {
|
||||
|
||||
private $openRoutes = [
|
||||
'signup/register',
|
||||
'api/v1/login',
|
||||
'api/v1/clients',
|
||||
'api/v1/invoices',
|
||||
'api/v1/quotes',
|
||||
@ -34,12 +35,6 @@ class VerifyCsrfToken extends BaseVerifier {
|
||||
}
|
||||
}
|
||||
|
||||
if ($request->is('login')) {
|
||||
if (env(API_SECRET) && $request->api_secret === env(API_SECRET)) {
|
||||
return $next($request);
|
||||
}
|
||||
}
|
||||
|
||||
return parent::handle($request, $next);
|
||||
}
|
||||
|
||||
|
@ -186,10 +186,11 @@ Route::group(['middleware' => 'auth'], function() {
|
||||
get('/resend_confirmation', 'AccountController@resendConfirmation');
|
||||
});
|
||||
|
||||
// Route group for API
|
||||
// Route groups for API
|
||||
Route::group(['middleware' => 'api', 'prefix' => 'api/v1'], function()
|
||||
{
|
||||
Route::resource('ping', 'ClientApiController@ping');
|
||||
Route::post('login', 'AccountApiController@login');
|
||||
Route::get('accounts', 'AccountApiController@index');
|
||||
Route::resource('clients', 'ClientApiController');
|
||||
Route::get('quotes/{client_id?}', 'QuoteApiController@index');
|
||||
|
@ -459,8 +459,14 @@ class AccountRepository
|
||||
|
||||
public function createToken($name)
|
||||
{
|
||||
$name = trim($name) ?: 'TOKEN';
|
||||
|
||||
if ($token = AccountToken::scope()->whereName($name)->first()) {
|
||||
return $token->token;
|
||||
}
|
||||
|
||||
$token = AccountToken::createNew();
|
||||
$token->name = trim($name) ?: 'TOKEN';
|
||||
$token->name = $name;
|
||||
$token->token = str_random(RANDOM_KEY_LENGTH);
|
||||
$token->save();
|
||||
|
||||
|
@ -39,15 +39,15 @@ If you'd like to use our code to sell your own invoicing app email us for detail
|
||||
* [Support Forum](https://www.invoiceninja.com/forums/forum/support/)
|
||||
* [Feature Roadmap](https://trello.com/b/63BbiVVe/)
|
||||
|
||||
### Recommended Providers
|
||||
* [Stripe](https://stripe.com/)
|
||||
* [Postmark](https://postmarkapp.com/)
|
||||
|
||||
### Contributors
|
||||
* [Troels Liebe Bentsen](https://github.com/tlbdk)
|
||||
* [Jeramy Simpson](https://github.com/JeramyMywork) - [MyWork](https://www.mywork.com.au)
|
||||
* [Sigitas Limontas](https://lt.linkedin.com/in/sigitaslimontas)
|
||||
|
||||
### Recommended Providers
|
||||
* [Stripe](https://stripe.com/)
|
||||
* [Postmark](https://postmarkapp.com/)
|
||||
|
||||
### Frameworks/Libraries
|
||||
* [laravel/laravel](https://github.com/laravel/laravel) - A PHP Framework For Web Artisans
|
||||
* [twbs/bootstrap](https://github.com/twbs/bootstrap) - Sleek, intuitive, and powerful front-end framework for faster and easier web development.
|
||||
|
Loading…
x
Reference in New Issue
Block a user