Prestashop Repository not found - php

Good morning.
i have a problem using the new Symfony architecture.
i created a modern controller where routing is working perfect.
now i want to search products with ProductRepository.
MyModule/src/Repository/ProductRepository
namespace PrestaShop\Module\MyModule\Repository;
use Doctrine\DBAL\Connection;
class ProductRepository
{
/**
* #var Connection the Database connection.
*/
private $connection;
/**
* #var string the Database prefix.
*/
private $databasePrefix;
/**
* #param int $langId the lang id
* #return array the list of products
*/
public function findAllbyLangId(int $langId)
{
$prefix = $this->databasePrefix;
$productTable = "${prefix}product";
$productLangTable = "${prefix}product_lang";
$query = "SELECT p.* FROM ${productTable} p LEFT JOIN ${productLangTable} pl ON (p.`id_product` = pl.`id_product`) WHERE pl.`id_lang` = :langId";
$statement = $this->connection->prepare($query);
$statement->bindValue('langId', $langId);
$statement->execute();
return $statement->fetchAll();
}
}
MyModule/config/services.yml
services:
product_repository:
class: PrestaShop\Module\MyModule\Repository\ProductRepository
arguments: ['#doctrine.dbal.default_connection', '%database_prefix%']
MyController
$products = $this->get('product_repository')->findAllByLangId(1);
dump($products);
Now i get the following error:
"Attempted to load class "ProductRepository" from namespace "PrestaShop\Module\MyModule\Repository".
Did you forget a "use" statement for another namespace?"
What im missing there?
Thx for your time and help.
update - Stacktrace:
**ClassNotFoundException**
Symfony\Component\Debug\Exception\ClassNotFoundException:
Attempted to load class "ProductRepository" from namespace
"PrestaShop\Module\EasyUpload\Repository".
Did you forget a "use" statement for another namespace?
at var\cache\dev\ContainerZiol6qc\getProductRepositoryService.php:8
at require()
(var\cache\dev\ContainerZiol6qc\appDevDebugProjectContainer.php:1713)
at ContainerZiol6qc\appDevDebugProjectContainer->load('getProductRepositoryService.php')(vendor\symfony\symfony\src\Symfony\Component\DependencyInjection\Container.php:304)
at Symfony\Component\DependencyInjection\Container->get('product_repository')
(vendor\symfony\symfony\src\Symfony\Bundle\FrameworkBundle\Controller\ControllerTrait.php:67)
at Symfony\Bundle\FrameworkBundle\Controller\Controller->get('product_repository')
(modules\easyupload\src\Controller\DemoController.php:111)
at EasyUpload\Controller\DemoController->search()
(modules\easyupload\src\Controller\DemoController.php:76)
at EasyUpload\Controller\DemoController->indexAction(object(Request), null)(vendor\symfony\symfony\src\Symfony\Component\HttpKernel\HttpKernel.php:151)
at Symfony\Component\HttpKernel\HttpKernel->handleRaw(object(Request), 1)
(vendor\symfony\symfony\src\Symfony\Component\HttpKernel\HttpKernel.php:68)
at Symfony\Component\HttpKernel\HttpKernel->handle(object(Request), 1, false)
(vendor\symfony\symfony\src\Symfony\Component\HttpKernel\Kernel.php:200)
at Symfony\Component\HttpKernel\Kernel->handle(object(Request), 1, false)
(admin108ptrz6g\index.php:86)`

It's look like you didn't create composer.json file with predefined namespaces.
Here example:
{
"name": "YourName/YourModuleName",
"description": "Awesome description",
"autoload": {
"psr-4": {
"YourName\\YourModuleName\\": "/",
"YourName\\YourModuleName\\Repository": "src/Repository/",
}
},
"config": {
"prepend-autoloader": false
},
"type": "prestashop-module"
}
OR if you want with Prestashop right way
{
"name": "YourName/YourModuleName",
"description": "Awesome description",
"autoload": {
"psr-4": {
"Prestashop\\Module\\YourModuleName": "src/",
"Prestashop\\Module\\YourModuleName\\Repository": "src/Repository/",
}
},
"config": {
"prepend-autoloader": false
},
"type": "prestashop-module"
}
Then run composer install and add to your YourModuleName.php file require_once.
$autoloadPath = __DIR__ . '/vendor/autoload.php';
if (file_exists($autoloadPath)) {
require_once $autoloadPath;
}

I was also searching for hours and find out I needed this exact structure to register the mycompany.mymodule.myservice. This has to be exactly like this in Prestashop 1.7.6:
// mycompany\mymodule\config
config
admin
services.yml
front
services.yml
common.yml
Also make sure your namespace is setup correctly.

Related

Laravel 8 package development - Route Target class does not exist

I know the title topic sounds similar to other questions, but I've searched many topics on stackoverflow and none resolve my issue.
I am currently developing a package under Laravel ^8.12, below the content of the function that register my routes:
protected function registerRoutes(): void
{
Route::prefix('workflowmakr')
->namespace('AlvariumDigital\WorkflowMakr\Http\Controllers')
->as('workflowmakr.')
->middleware(config('workflowmakr.routes_middleware'))
->group(__DIR__ . '/../routes/api.php');
}
And below is the content of the routes/api.php file:
<?php
use Illuminate\Support\Facades\Route;
Route::resource('actions', 'ActionController')->except(['created', 'edit']);
Route::resource('scenarios', 'ScenarioController')->except(['created', 'edit']);
Route::resource('statuses', 'StatusController')->except(['created', 'edit']);
Route::resource('transitions', 'TransitionController')->except(['created', 'edit']);
For a better view of the project architecture, below is a screenshot of the packages folder containing the package under development:
And finally, below is the composer.json declaring my package:
...
"extra": {
"laravel": {
"providers": [
"AlvariumDigital\\WorkflowMakr\\WorkflowMakrServiceProvider"
]
}
},
"autoload": {
"psr-4": {
"App\\": "app/",
"Database\\Factories\\": "database/factories/",
"Database\\Seeders\\": "database/seeders/",
"AlvariumDigital\\WorkflowMakr\\": "packages/AlvariumDigital/WorkflowMakr/src/"
}
},
...
When I execute the command php artisan route:list to view all my routes I got this error :
$> php artisan route:list
Illuminate\Contracts\Container\BindingResolutionException
Target class [AlvariumDigital\WorkflowMakr\Http\Controllers\ActionController] does not exist.
at D:\Films\R_D\Laravel packages\workflow-makr\vendor\laravel\framework\src\Illuminate\Container\Container.php:832
828▕
829▕ try {
830▕ $reflector = new ReflectionClass($concrete);
831▕ } catch (ReflectionException $e) {
➜ 832▕ throw new BindingResolutionException("Target class [$concrete] does not exist.", 0, $e);
833▕ }
834▕
835▕ // If the type is not instantiable, the developer is attempting to resolve
836▕ // an abstract type such as an Interface or Abstract Class and there is
1 [internal]:0
Illuminate\Foundation\Console\RouteListCommand::Illuminate\Foundation\Console\{closure}(Object(Illuminate\Routing\Route))
2 D:\Films\R_D\Laravel packages\workflow-makr\vendor\laravel\framework\src\Illuminate\Container\Container.php:830
ReflectionException::("Class AlvariumDigital\WorkflowMakr\Http\Controllers\ActionController does not exist")
EDIT
Below is the content of the ActionController file:
<?php
namespace AlvariumDigital\WorkflowMakr\Http\Controllers;
use AlvariumDigital\Models\Action;
use AlvariumDigital\WorkflowMakr\Helpers\Constants;
use Illuminate\Routing\Controller;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Validator;
class ActionController extends Controller
{
/**
* Display a listing of the resource.
*
* #return \Illuminate\Http\JsonResponse
*/
public function index()
{
$query = Action::query();
if (config('workflowmakr.pagination_size') == -1) {
return response()->json($query->get(), 200);
}
return response()->json($query->paginate(config('workflowmakr.pagination_size')), 200);
}
// ...
}
EDIT 2
The content of the package composer.json file:
{
"name": "AlvariumDigital/WorkflowMakr",
"description": "Generalize the management of your workflows",
"type": "library",
"license": "MIT",
"authors": [
{
"name": "Alvarium Digital",
"email": "contact#alvariumdigital.com",
"homepage": "http://www.alvariumdigital.com",
"role": "Corporate"
},
{
"name": "EL OUFIR Hatim",
"email": "heloufir#alvariumdigital.com",
"homepage": "https://www.linkedin.com/in/eloufirhatim/",
"role": "Developer"
}
],
"support": {
"email": "heloufir#alvariumdigital.com"
},
"minimum-stability": "dev",
"require": {}
}
Did I do something wrong or incomplete?
You can ask for more details if needed.
Thanks
You have structured this directory incorrectly. You have the PSR4 autoloading loading the src directory as the namespace. Your controllers are not in the src folder, only the Service Provider is in there. So to composer there are no files for it to find and autoload based on your PSR4 autoloading.

Composer autoloader seems to be not included correctly

I'm trying to implement simple library without web server. That means I actually don't have any entry point where I can include autoload.php.
I trying to add bunch of classes, but PhpStorm cannot recognise namespacing and and my classes cannot being auto-imported.
E.g.
I'm trying to import file App/Engines/Contracts/BaseEngine.php which is placed in src/Engines/Contracts/BaseEngine.php via
use App\Engines\Contracts\BaseEngine;
The PhpStorm says Undefined Class
All PhpStorm configuration seems to be correct: I've specified composer.json and checked auto-import in namespace scope.
So, basically the question is: How to deal with composer autoloader in such a library?
Attaching my composer.json code.
{
"name": "mom/task",
"description": "Todo",
"authors": [
{
"name": "Foo Bar",
"email": "foo.mail.com"
}
],
"require": {
"php": "^7.4"
},
"require-dev": {
"phpunit/phpunit": "^8",
"squizlabs/php_codesniffer": "3.*"
},
"autoload": {
"psr-4": {
"App\\": "src/"
}
},
"autoload-dev": {
"psr-4": {
"Tests\\": "tests/"
}
}
}
UPD: attaching BaseEngine code.
<?php
namespace App\Engines\Contracts;
interface BaseEngine
{
/**
* #param int $variable
* #param int $multiplier
* #return mixed
*/
public function compute(int $variable, int $multiplier): int;
}

package:discovery does not find my ServiceProvider

I have created a custom Laravel package. Its hosted on a private repository.
When I try to install the package in a Laravel application like this:
composer require memberportal/congress-models
I get this error:
In ProviderRepository.php line 208:
Class 'Memberportal\CongressesModels\CMServiceProvider' not found
Script #php artisan package:discover --ansi handling the post-autoload-dump event returned with error code 1
Installation failed, reverting ./composer.json to its original content.
I have double checked everything a hundred times, but I am clueless why he doesn't find the class CMServiceProvider.php.
Do I need to specify the provider anywhere else then in the composer.json?
This is the content of composer.json from my package:
{
"name": "memberportal/congress-models",
"description": "Takes care of the models between API and client",
"type": "metapackage",
"authors": [
{
"name": "My name",
"email": "my#email.com"
}
],
"version" : "1.0",
"minimum-stability": "stable",
"require": {
"laracasts/presenter": "^0.2.2"
},
"require-dev": {
"orchestra/testbench": "^4.0"
},
"autoload": {
"psr-4": {
"Memberportal\\CongressesModels\\": "src"
}
},
"autoload-dev": {
"psr-4": {
"Memberportal\\CongressesModels\\Tests\\": "tests"
}
},
"extra": {
"laravel": {
"providers": [
"Memberportal\\CongressesModels\\CMServiceProvider"
]
}
}
}
This is the folder structure:
This is the content of CMServiceProvider.php:
<?php
namespace Memberportal\CongressesModels;
use Illuminate\Support\ServiceProvider;
class CMServiceProvider extends ServiceProvider
{
/**
* Register services.
*
* #return void
*/
public function register()
{
}
/**
* Bootstrap services.
*
* #return void
*/
public function boot()
{
$this->loadMigrationsFrom(__DIR__ . '/../database/migrations');
}
}
Since you want to install a Laravel package your package type should be package. A metapackage is a package that does not contain actual software, it simply depends on other packages to be installed.
In short, change
"type": "metapackage",
to
"type": "package",
and Laravel will find the service provider with auto-discovery when the package is required by composer.

Can't load class on Slim 3

I'm trying to load my custom classes for the model on Slim 3 (using the skeleton) so I made this:
In app/composer.json:
"autoload": {
"psr-4": {
"App\\Classes\\": "/src/classes"
}
},
In routes.php I have this setting:
<?php
use Slim\Http\Request;
use Slim\Http\Response;
use Slim\Container;
// Routes
$app->get('/sugiere', function (Request $request, Response $response, array $args) {
// Sample log message
$this->logger->info("Slim-Skeleton '/' route");
$cat_mapper = new \App\Classes\CategoryMapper($this->db);
$comuna_mapper = new \App\Classes\ComunaMapper($this->db);
$lang_mapper = new \App\Classes\LanguageMapper($this->db);
$netw_mapper = new \App\Classes\NetworkMapper($this->db);
$com_list = $com_mapper->getComunaList();
$cat_list = $cat_mapper->getCategoryList();
$lang_list = $lang_mapper->getLangList();
$netw_list = $netw_mapper->getNetworkList();
By the way I added to all classes a namespace App\Classes on top.
Your path /src/classes looks incorrect. It's unlikely your src directory is in the filesystem root.
Change your composer.json file to
"autoload": {
"psr-4": {
"App\\Classes\\": "src/classes/"
}
}
and run
composer dump-autoload
to re-generate the autoload.php file.
See https://getcomposer.org/doc/01-basic-usage.md#autoloading

Class not found, plugin working good

I made new plugin with informations find at this post: https://luketowers.ca/blog/how-to-use-laravel-packages-in-october-cms-plugins/
I update composer.php and in vendor folder i got created files I see plugin phpclasses/evalmath in backend.
When on page i try do math operation:
function onStart() {
// instantiate a new EvalMath
$m = new EvalMath;
$m->suppress_errors = true;
// set the value of x
$m->evaluate('x = 3');
var_dump($m->evaluate('y = (x > 5)'));
}
I got error that Class 'EvalMath' not found Class is defined in file /plugins/phpclasses/evalmath/vendor/phpclasses/evalmath/evalmath.class.php What i am doing wrong?
in file /plugins/phpclasses/evalmath/composer.json
{
"require": {
"phpclasses/evalmath": ">=1.0.0"
},
"repositories": [
{
"type": "composer",
"url": "https:\/\/www.phpclasses.org\/"
},
{
"packagist": false
}
]
}
in file /plugins/phpclasses/evalmath/Plugin.php
<?php namespace phpclasses\evalmath;
use App;
use Config;
use System\Classes\PluginBase;
use Illuminate\Foundation\AliasLoader;
/**
*
* Class Plugin */
class Plugin extends PluginBase
{
/**
*
* Returns information about this plugin.
* #return array
*/
public function pluginDetails()
{
return ['name' => 'phpclasses/evalmath',
'description' => 'OctoberCMS plugin for demonstrating the use of Laravel Packages within October plugins',
'author' => 'hhh',
'icon' => 'icon-leaf'
];
}
/**
*
* Runs right before the request route */
public function boot()
{
// Setup required packages $this->bootPackages(); }
/**
*
* Boots (configures and registers) any packages found within this plugin's packages.load configuration value
* #see https://luketowers.ca/blog/how-to-use-laravel-packages-in-october-plugins
* #author Luke Towers octobercms#luketowers.ca
*/
public
function bootPackages()
{ // Get the namespace of the current plugin to use in accessing the Config of the plugin $pluginNamespace = str_replace('\', '.', strtolower(NAMESPACE));
// Instantiate the AliasLoader for any aliases that will be loaded
$aliasLoader = AliasLoader::getInstance();
// Get the packages to boot
$packages = Config::get($pluginNamespace . '::packages');
// Boot each package
foreach ($packages as $name => $options) {
// Setup the configuration for the package, pulling from this plugin's config
if (!empty($options['config']) && !empty($options['config_namespace'])) {
Config::set($options['config_namespace'], $options['config']);
}
// Register any Service Providers for the package
if (!empty($options['providers'])) {
foreach ($options['providers'] as $provider) {
App::register($provider);
}
}
// Register any Aliases for the package
if (!empty($options['aliases'])) {
foreach ($options['aliases'] as $alias => $path) {
$aliasLoader->alias($alias, $path);
}
}
}
}
}
}
in file /plugins/phpclasses/evalmath/classes/config.php
<?php
return [
// This contains the Laravel Packages that you want this plugin to utilize listed under their package identifiers
'packages' => [
'phpclasses/evalmath' => [
],
],
];
the most of the code in file /plugins/phpclasses/evalmath/Plugin.php(bootPackages()) is not nessesary if you dont have configs or additional providers or aliases
if its a laravel package you can use \App::register('\Your\LaravelPackage\ServiceProvider'); in the boot function
to register the package with the laravel Provider
and ad an alias for your package
$alias = \Illuminate\Foundation\AliasLoader::getInstance()->alias('YourAlias', '\Your\LaravelPackage\Facade');
if its not a laravel package try use the full namespace i think its \EvalMath if you use this package https://www.phpclasses.org/browse/file/11680.html

Categories