Laravel error interface class does not exist - php

I am very new to "Advanced Laravel" so to speak, however I do know most of the basics and I am trying to understand what namespacing, interfaces and repositories is all about, since I came across it not so long ago.
However, I am getting the following error, and I have no idea what I am doing wrong:
Class app\models\Interfaces\CategoriesInterface does not exist
Below is my code:
Routes.php
App::bind('App\Models\Interfaces\BaseInterface', 'App\Models\Repositories\BaseRepository');
CategoriesController.php
<?php
use app\models\Interfaces\CategoriesInterface;
class CategoriesController extends BaseController
{
protected $categories;
public function __construct(CategoriesInterface $categories)
{
$this->categories = $categories;
}
BaseInterface.php
<?php
interface BaseInterface
{
public function all();
}
CategoriesInterface.php
<?php namespace App\Models\Interfaces;
interface CategoriesInterface extends BaseInterface { }
CategoriesRepository.php
<?php namespace app\models\Repositories;
use App\Models\Interfaces\CategoriesInterface;
use Categories;
class CategoriesRepository implements CategoriesInterface
{
public function all()
{
$categories = $this->categories->all();
return $categories;
}
}
EloquentCategoriesRepository.php
<?php namespace app\models\Repositories;
use App\Models\Interfaces\CategoriesInterface;
class EloquentCategoriesRepository implements CategoriesInterface {
public function all()
{
return Categories::all();
}

Try name spacing the classes/interfaces properly. EloquentCategoriesRepository.php and CategoriesRepository are having app instead of App in the namespace. And CategoriesController too needs to use App\.. not app\...

I see you are trying to implement the repository pattern, which at first it might seem a bit 'advanced' but it's actually pretty simple.
So the basic idea is to abstract the data layer of your application with the database to make your transitions from one DBS to another(ex. Mysql to Mongo).
In other words your are trying to make the business logic of your application independent to the data layer (Where you query your collections/instances), so when you reach a point that you might want to change your database you can just implement another repository. The Interfaces are there to provide a contract between your application and the data layer.
Laravel implementation of the repository pattern it's pretty straight forward.
Create your interface
Create your interface's repository (actual implementation)
Bind the repository using a service provider class (Or in your case App::bind)
Instantiate the dependency in to your controller using the repository
Don't forget to auto load your namespaces using psr-04.
In your case I think the problem is you are not autoloading the namespace.
Also CategoriesRepository.php & EloquentCategoriesRepository.php are both Eloquent repositories and will return Eloquent collections. To return an array of stdClass (standar PDO) you will have to use the \DB facade.
If my answer does not cover you please take a look here

Related

What is the proper way to use the Model in Laravel?

Can you help me with this? I am currently studying Laravel on my own and I followed the tutorials in the Laracasts and it is awesome. Before Laravel I am using CodeIgniter and Opencart in my projects and I started to study Laravel because I want to learn a new framework.
In CI and Opencart all your database queries are in the model. But in Laravel you can perform and queries in Controller?. Is it a proper way to the queries in Laravel?
I have this kind of code in the Controller:
<?php namespace App\Http\Controllers;
use App\Http\Requests;
use App\Http\Controllers\Controller;
use App\Article;
use Illuminate\Http\Request;
class ArticlesController extends Controller {
public function index() {
$articles = Article::all();
return view('articles.index')->with('articles', $articles);
}
}
Yes, this is perfectly fine for small applications.
For large-scale apps however, i'd recommend using repositories as they decouple your models from the controller - which makes them more readable and testable.
Your ArticlesController would translate to something like this:
<?php namespace App\Http\Controllers;
use App\Repositories\Articles\ArticleRepositoryInterface;
class ArticlesController extends Controller {
private $articles;
public function __construct(ArticleRepositoryInterface $articles)
{
$this->articles = $articles;
}
public function index()
{
return view('articles.index')
->with('articles', $this->articles->all());
}
}
Have a look at Laravels Service Container to understand the automatic resolution of the ArticleRepositoryInterface. Laracasts has some good videos on repositories.
Repositories is a smart decision to you. But why?
Basically, repositories is a 'gateway' between your application and your storage.
With repositories, you'll find your 'database queries' in a single place.
Let's think about the model Articles.
Instead of use a static instance of Articles all the times that you need to use it (Articles::find(), Articles::all(), etc), just create a repository of Articles.
Inject this repo in your controller (e.g.), and use 'features' storaged in your ArticleRepository.
What do you mean?
Let's consider a repository of Articles. What I'll use many times in my app of Articles model? I need select all, select by id, insert, update, delete. Basically these 'stuffs'. So, if I have all this stuffs in a place?
class ArticleRepository {
public function all(){}
public function getById($id){}
public function insert($data){}
public function update($data){}
public function delete($id){}
}
Inject this ArticleRepository in your controller. To do this, read a about IoC Container here: http://laravel.com/docs/5.0/container
The construct in your controller will be like this:
public function __construct(ArticleRepository $articles)
{
$this->articles = $articles;
}
Once all, when you need get all Articles in your controller, just do:
public function index()
{
$articles = $this->articles->all();
return View::make('articles.index')->with(['articles' => $articles]);
}
With this practice, you have a clean application with testables controllers and a beautiful organization and design. ;)
Look, I tried to be as didactic as possible to you understand the concept. The use of repositories is not only a way to do. So I let the links in the comments. And let other references here as well.
I'm sure you will understand quickly.
Success in learning! :)
https://laracasts.com/search?q=repositories&q-where=lessons
http://ryantablada.com/post/the-repository-pattern-in-action
http://culttt.com/2014/03/17/eloquent-tricks-better-repositories/
http://culttt.com/2013/07/15/how-to-structure-testable-controllers-in-laravel-4/

Are Namespaces necessary everywhere in Laravel?

Im new to Laravel and namespaces, but a colleague told me i have to use the namespaces and place all my models in a folder in the app directory, named after the project.
As far as i know this means that in every single controller that uses one or more models, have have to set "use" for every model my controller needs. Example:
<?php
use Foo\Entities\Entity;
use Foo\Entities\Inheritance;
use Foo\Entities\Type;
class EntitiesController extends BaseController {
public function index()
{
$inheritances = Inheritance::all();
$entities = Entity::all();
return View::make('settings/entities')
->with('entities', $entities)
->with('inheritances', $inheritances);
}
}
If we asume that the associated models above will be used everywhere, would it be completely crazy to put the models in the /app/model/ folder and if a controller need a model which overwrite the standard system, then use namespaces?
First things first: namespaces are NOT a Laravel thing, but a PHP feature created to better organize our code.
So, if you want your code organized, you should use namespaces for everything and, yes, you'll have to add 'use' clauses in the top of most of your PHP files. But in Laravel you also can be free to not use namespaces at all, you just have to add your autoload classes directories to your composer.json file:
"autoload": {
"classmap": [
"models"
],
},
Execute
composer dumpautoload
So Composer read all files in your models folder, to create a class map of them, and then you can just drop all uses clauses:
class EntitiesController extends BaseController {
public function index()
{
$inheritances = Inheritance::all();
$entities = Entity::all();
return View::make('settings/entities')
->with('entities', $entities)
->with('inheritances', $inheritances);
}
}
To not use namespaces in your PHP application, these days, may be considered a code smell. The only 'part' of Laravel where people doesn't usually use namespaces is Controllers, but this is also changing in Laravel 5, where controllers will be namespaced by default, but still, you will have the option to not use them, because this is a Composer/PHP thing, not Laravel.
Taylor Otwell has 3 big things always in mind when creating features and evolving Laravel: Best practices, fast coding and beautiful code.
EDIT
Answering your comment, if all your controllers needs to have access to some service or even model, why not add it to your BaseController?
But you may have to take a read at the repository pattern, because your controllers should not really be aware of your models. Developers are now creating a new layer (repository) between controllers and models, and perform the operations in those layers. You can, also, make use of Laravel Dependency Injection to help you with those use clauses you don't like.
It would be something like this:
Create a repository interface:
interface EntityRepositoryInterface {
}
Create the repository:
use Foo\Entities\Entity;
class EntityRepository {
public function find($id)
{
return Entity::find($id);
}
public function all()
{
return Entity::all();
}
}
Create your controllers using your repository:
class EntitiesController extends BaseController {
public function __construct(EntityRepositoryInterface $entityRepository)
{
$this->entityRepository = $entityRepository;
}
public function index()
{
$entities = $this->entityRepository->all();
return View::make('settings/entities')
->with('entities', $entities);
}
}
And you have to tell Laravel Dependency Injection what to instantiate when it needs a EntityRepositoryInterface:
App::bind('EntityRepositoryInterface', 'Foo\Entities\EntityRepository');
There's nothing wrong with putting your models anywhere you like. In fact, I put all my models that extend directly from Eloquent in app/models. You are free to follow this, or not follow it, in your own project.
However, this does come with a caveat. Very few of my classes actually directly interact with these models (Repositories are pretty much it). Those I do put in separate namespaces which are then injected into my controllers. Consequently, I must either use each repository that a controller needs at the top of each file or specify the fully qualified class name every time I reference it.

Best way to use multiple implementations of interface with Dependeny Injection

I have seen some similar questions but I have yet to find a good solution for this from the interface all the way to the controller.
My Problem:
I have a few different kinds of applications that will require restarts, each has its own logic for restarting the application(SSH,API calls, etc.). I have set up an interface because although different logic, they all will need some similar functions. I have also created 3 classes, one for each app that implements that interface. where I am having issues is understanding the best way to keep the logic as abstracted from the controller as possible.
Some Questions:
Should I also be creating an Abstract class?
Should this be one controller that handles all types and chooses the correct one?
do I simply inject the different classes into the controller?
Code:
RestartInterface.php
<?php namespace Application\Service\Restart;
interface RestartInterface {
public function start();
public function stop();
public function restart();
}
example of implementing class:
<?php namespace Application\Service\Restart\AppOne;
use Application\Service\Restart\RestartInterface;
class AppOneRestart implements RestartInterface {
public function start() {
}
public function stop() {
}
public function restart() {
}
}
How could I use a service provider to keep this as modular as possible?
What is the best practice in this situation, I would like to be able to use many or as little restart implementations as I want.
thanks!
An abstract class is a way to create a base class you don't need your developers instantiating directly because, usually, there is still missing code from it, like, methods were not fully implemented. So you create an abstract which implements the common methods of your concrete restart classes
abstract class Restart {
public function restart() {
}
}
And then you implement one by one of those classes extending your abstract and creating the missing methods:
class AppOneRestart extends Restart implements RestartInterface {
public function start() {
}
public function stop() {
}
}
Option 1
If your whole application can use a single implementation of it and you just need the ability to swap from one to another, because your business somehow changed, a simple binding will do the trick:
App::bind('RestartInterface', 'AppOneRestart');
Option 2
If during a request you might need one or another, you probably will need to implement the Factory pattern: http://en.wikipedia.org/wiki/Factory_method_pattern, so you inject the factory in your controller:
class RestartApiController extends Controller {
public function __construct(RestartFactory $factory)
{
$this->restart = $factory->make('api');
}
}

Laravel 4: How to correctly work with Models in Repositories

Read books From Apprentice To Artisan and Implementing Laravel by Chris Fidao and now i don't know how to correctly work with Models in Repositories.
In Implementing laravel book author is working with models in this way:
Example #1
<?php
use MyApp\Interfaces\UserInterface;
use Illuminate\Database\Eloquent\Model;
class UserRepository implements UserInterface
{
protected $user;
public function __construct(Model $user)
{
$this->user = $user;
}
public function find($userId)
{
return $this->user->find($userId);
}
}
But that can by done in other way, not injecting Model as a dependency, like this:
Example #2
Built example using tutorial http://culttt.com/2013/07/08/creating-flexible-controllers-in-laravel-4-using-repositories/
<?php
use MyApp\Interfaces\UserInterface;
use MyApp\Models\User\User;
class UserRepository implements UserInterface
{
public function find($userId)
{
return User::with('profile')->find($userId);
}
}
Why in first example Model is injected, why not use directly Model like in example two?
Which way is correct and why ?
Also which way will be more testable with integrated to laravel UnitTest package ?
The example 2 is bad because it's coupling your repository to a particular implementation of the User model.
Every time you use your repository it'll need to instantiate Univemba\Models\User\User. The whole idea of Dependency Injection is to inject (send) in to your object whatever dependencies it has. If your object needs a Model to work with you can send it a Laravel Eloquent Model, but any of your co-workers could also need to send to it a Doctrine Model. But if you couple your class to Eloquent, this isn't possible.
So in the first example, there is no instantiation happening on your code and it's not using a concrete class directly as in the second:
return User::with('profile')->find($userId);
It is receiving an implementation in the process of its instantiation:
public function __construct(Model $user)
{
$this->user = $user;
}
There are better ways to do that, because it is still expecting a concrete class while it should be expecting an implementation of an interface
public function __construct(ModelInterface $user)
{
$this->user = $user;
}
In this case you just need to pass to your object something that implements ModelInterface, which could be
Univemba\Models\EloquentModel
Or
Univemba\Models\DoctrineModel
Because both would be implementing
Univemba\Models\ModelInterface
I think if a Repository is intended to be the Eloquent implementation of a RepositoryInterface it isn't a bad idea to use the EloquentModel directly.

Can php have an interface inside a class?

i would like to know if it is possible to have a function in PHP which returns an interface or a class which contains an interface?
i tried something like this, but it fails
<?php
//class for list of controllers for ACL
class Gestionale_Action_Helper_Crud extends Zend_Controller_Action_Helper_Abstract {
interface crud_controller
{
public function indexAction();
public function modificaAction();
public function cancellaAction();
public function creaAction();
}
public function getCrudInterface(){
return $this->crud_controller;
}
}
what i wanted to do, in zend framework, create an interface that crud controllers must implement, or even better if i could create an abstract controller and have them implement that
thank you
I'd suggest that you use Zend_Rest_Controller instead of creating your own interface.
Zend_Rest_Controller is an abstract class that defines five basic methods you need in a CRUD-controller: index, get, post, put, and delete.
Combined with Zend_Rest_Route it lets you create nice and clean RESTful application.
You can get more reading on Zend_Rest_Controller at http://weierophinney.net/matthew/archives/228-Building-RESTful-Services-with-Zend-Framework.html and http://techchorus.net/create-restful-applications-using-zend-framework
Just place the interface outside of any class (preferably in a different file) and let it be implemented by all your crud-controllers.
<?php
class GrudController implements CrudInterface
{
// ...
}
i'm not sure i get what it is you want to do, but i'm fairly certain you're asking the wrong question. if you simply want to make sure an object implements a certain interface, this is quite easy to do. lets say for example you have some helper method in a class which deals with a crud controller, you just specify the type in the argument list:
class crud_helper {
public function help(crud_controller $cc) {
$cc->indexAction();
}
}
now you can pass any object that is an instance of a class that implements crud_controller to the method help. but no other object.

Categories