Non-static method Cartalyst\Sentinel\Sentinel::getUser() should not be called statically - laravel

Hi I am using laravel Sentinel as my Auth, also I am trying to use laravel auditing I am getting "Non-static method Cartalyst\Sentinel\Sentinel::getUser() should not be called statically".
In my user model I have added a static function resolveId() for adding user_id in Laravel Auditing 'audits' table
public static function resolveId(){
return Sentinel::getUser()->getUserId();
//return auth()->check() ? auth()->user()->getAuthIdentifier() : null;
}
When I try to use \Sentinel::getUser() I am getting the error below.
Non-static method Cartalyst\Sentinel\Sentinel::getUser() should not be called statically

From the docs:
After installing the package, open your Laravel config file located at config/app.php and add the following lines.
In the $aliases array add the following facades for this package.
'Sentinel' => Cartalyst\Sentinel\Laravel\Facades\Sentinel::class,
Then just add this to the top of the class:
use Sentinel;

Put this use on top of the file in question:
use Cartalyst\Sentinel\Laravel\Facades\Sentinel;

I'm aware that the package version #manikandan k was asking help for is 4.x or 5.x, and while the documentation does mention the use case for Sentinel, it doesn't provide an actual example.
Since version 6.x, the Audit Resolvers documentation has this very use case, where Sentinel is used instead.
I suggest updating the resolver logic to the following:
return Sentinel::check() ? Sentinel::getUser()->getUserId() : null;
This will prevent calling getUserId() on null, when a user isn't logged.

Related

Proper way to create a service provider in Laravel

I am having trouble creating a service for my Laravel application. I wish to use this service to easily communicate with an API to perform IO operations. To be specific, my Laravel application needs to communicate with InvoiceNinja. There is an invoiceninja/sdk-php which I am using to facilitate this communication. According to their docs, it is used like this:
require __DIR__ . '/vendor/autoload.php';
use InvoiceNinja\Config as NinjaConfig;
use InvoiceNinja\Models\Client; // Model can be Invoice, Payment, etc
NinjaConfig::setURL('https://ninja.dev/api/v1');
NinjaConfig::setToken('Your Token');
$clients = Client::all();
The code snippet above is an example of using the API to fetch a list of clients. Now, since I am using Laravel, I did not see the need of setting the API URL and Token every time I needed to send a request to the API. And so I decided to use a Service Provider. Below is my code in InvoiceNinjaServiceProvider.php register method:
$this->app->singleton(NinjaConfig::class, function ($app) {
NinjaConfig::setURL(config('invoice-ninja.API_URL')); // I created a config/invoice-ninja.php which has these variables set
NinjaConfig::setToken(config('invoice-ninja.API_TOKEN'));
});
I then registered this provider in config/app.php. I thought that would be enough to use the API in my controllers like this:
use InvoiceNinja\Models\Client;
public function index(InvoiceNinjaServiceProvider $invoiceNinja)
{
$clients = Client::all();
dd($clients); // To test that I actually receive data
}
But I get an error Unresolvable dependency resolving [Parameter #0 [ <required> $app ]] in class Illuminate\Support\ServiceProvider. I am not very well versed with Service Providers and I am hoping someone out there can point me in the right direction to get this to work.
Thank you. Thank you!
You should return the resolved instance when you bind your singleton, the instance will be injected as a parameter in yout index method.
From the doc:
$this->app->singleton('HelpSpot\API', function ($app) {
return new \HelpSpot\API($app->make('HttpClient'));
});
note the return

security with method not working

I'm trying to set up security on my entities in API Platform and found that I can call a method instead of the property example used in the docs (found this in some example somewhere on the web):
* attributes={"access_control"="is_granted('ROLE_USER') and object.belongsTo(user)"},
This is necessary in my case as I keep the user account data seperate from the user profile data and the entity in question is linked to the profile, not the user entity.
This works like charm on an individual getter (/api/data/{id}) but fails with a server 500 error on the list (/api/data):
"hydra:description": "Unable to call method \"belongsTo\" of object
\"ApiPlatform\Core\Bridge\Doctrine\Orm\Paginator\".",
Wondering what is going wrong and how to fix it.
the "belongsTo()" method is fairly simple:
public function belongsTo(User $user) {
return $user == $this->owner->user;
}
Try this way
Create custom extension

Laravel Gate method not being called

In my Laravel 5.4 application users can create Projects and then Posts inside those projects.
I'm trying to prevent users from creating or editing posts inside a project they don't have access to.
To do this I implemented a Gate as explained here: https://laravel.com/docs/5.4/authorization#gates
The gate checks if a user is the owner of the project.
Gate::define('create-post', function ($user, $project) {
Log::info($project) // !!! Never gets called
return $project->owner_id == $user->id;
});
On the PostController I call Gate::denies passing the project as an argument
if (Gate::denies('create-post', $project)) {
abort(403);
}
The problem is the code I defined for the gate never gets called. Instead it always returns false and goes to the 403 error.
However, the code does get called if I don't pass the project as an argument but that makes it useless.
I also want to add that in this case I cannot use a Policy because the create method only takes one argument ($user) and if I try to pass the $project it fails the same way it does with the Gate.
Is this a bug? Is there another, better way to implement this funcionality? Thanks.
I have the same issue. It seems something wrong happens when the second parameter in Gate::allows() is an eloquent model.
If you pass in denies() any other variable (even object, but not eloquent model), your Log::info() will work.
I wasted the whole day with it and switched to $user->can()
I was able to fix it by using a policy. I created the following method in ProjectPolicy:
public function createOrEditPosts(User $user, Project $project)
{
return $project->owner_id == $user->id;
}
Then from PostController I call:
$this->authorize('createOrEditPosts', $project));
I still don't know why the gate approach doesn't work.
I had the same issue.
I replaced Gate::denies() with Gate::allows().
I'm not sure why but this worked for me. The policy framework is a little bit tricky to be honest
first, check to log in to your project then gate work because of the gate when work that you log in to your project.

what does it mean in blade #extends('some::thing')

Today I have installed jeroennoten/laravel-adminlte and after following all the installation command I created a view and just wrote the line
#extends('adminlte::page')
and it works fine but I do not understand how it works? specially this :: symbol? I checked the laravel documentation but could not find anything.
Please help me by explaining it or give some article/tutorial link from where I can learn more.
adminlte is the name of the package, which is used for views and configs in Laravel as a namespace in order to avoid conflicts with other other packages.
It is defined in the ServiceProvider class on line 51.
By calling this in your blade files:
#extends('adminlte::page')
you are telling to Laravel, that you want to extend the page.blade.php file.
If you call #extends('page'), without adminlte::, it will look for the page.blade.php in your resources/views directory.
You won't see information in Laravel's Blade documentation section about this, because it's specific for Laravel Packages. And you can learn more from here.
::
symbol is a call of static function or static property in a class, for example if you define a class like this:
class Foo{
public static $a = 1;
public static function test(){};
}
you can use Foo::$a to get the value of $a, and use Foo::test() to call the function test().

How can I render a twig template in a custom controller in Silex?

I'm playing with Silex microframework to build a very simple app.
The Silex documentation briefly illustrates how to keep your code organised using controller as class and I've also found this useful article talking about the same practice:
https://igor.io/2012/11/09/scaling-silex.html
but still can't solve my problem
The issue:
in my app.php I'm using
$app->get('/{artist}', 'MyNamespace\\MyController::getAlbum');
This is working. MyController is a class correctly loaded through composer using psr-4.
At the moment the return method of getAlbum($artist) is return $player;
What I'd like to do instead, is returning a twig view from getAlbum, something like:
return $app['twig']->render('player.twig', $player);
To do so, what I've tried to do in my custom class/controller is:
use Silex\Application;
use Symfony\Component\HttpFoundation\Request;
[...]
public function getAlbum(Request $request, Application $app, $artist)
but this is generating the following error when I try to access the routed pages:
ReflectionException in ControllerResolver.php line 43:
Class MyNamespace\Request does not exist
Whic made me think that there's a namespace conflict between myNamespace and the Silex namespaces?!
What am I doing wrong?
Is this the right way to make $app visible in my custom controller in order to use return $app['twig']... ?
Thank you in advance!
EDIT
After several other tries still didn't get to the point (replies still welcome!) but I've found a workaround solution that could be useful to anyone will incur in a similar issue. Directly in my app.php I added this
$app->get('/{artist}', function (Silex\Application $app, $artist) use ($app)
{
$object = new MyNamespace\MyController();
$player = $object->getAlbum($artist);
return $app['twig']->render('player.twig',
array(
//passing my custom method return to twig
'player' => $player,));
});
then in my player.twig I added:
{{player | raw}}
And this basically means that I still need an anonymous function to get use of my custom method which is a working solution I'm not really happy with because:
I'm using 2 functions for 1 purpose.
The return value of getAlbum is dependent from the use of "raw" in twig.
SOLVED
The workflow described works fine. It was a distraction error: I've placed the namespace of my custom class after use Symfony\Component\HttpFoundation\Request;
namespace declaration in PHP needs always to be at the top of the file, Silex wasn't able to injects $app and $request for this reason.

Resources