Spryker Core Back Office feature integration
Edit on GitHubThis feature integration guide expects the basic feature to be in place.
The current feature integration guide adds the following functionalities:
-
Translation
-
Security
-
OAuth 2.0/Open ID Connect Support for Zed login
Prerequisites
Ensure that the related features are installed:
NAME | VERSION |
---|---|
Spryker Core | 202108.0 |
1) Install the required modules using Composer
Run the following command(s) to install the required modules:
composer require spryker-feature/spryker-core-back-office:"202108.0" --update-with-dependencies
Ensure that the following modules have been installed:
MODULE | EXPECTED DIRECTORY |
---|---|
Translator | vendor/spryker/translator |
UserLocale | vendor/spryker/user-locale |
UserLocaleGui | vendor/spryker/user-locale-gui |
MessengerExtension | vendor/spryker/messenger-extension |
SecurityGui | vendor/spryker/security-gui |
UserPasswordReset | vendor/spryker/user-password-reset |
UserPasswordResetExtension | vendor/spryker/user-password-reset-extension |
UserPasswordResetMail | vendor/spryker/user-password-reset-mail |
SecurityOauthUser | vendor/sprkyer/security-oauth-user |
Ensure that the following modules have been uninstalled:
MODULE | EXPECTED DIRECTORY |
---|---|
Auth | vendor/spryker/auth |
AuthMailConnector | vendor/spryker/auth-mail-connector |
AuthMailConnectorExtension | vendor/spryker/auth-mail-connector-extension |
if not uninstalled, run the following command:
composer remove spryker/auth spryker/auth-mail-connector spryker/auth-mail-connector-extension
2) Set up transfer objects
Run the following commands to generate transfers:
console transfer:generate
Ensure the following transfers have been created:
TRANSFER | TYPE | EVENT | PATH |
---|---|---|---|
UserTransfer.fkLocale | attribute | created | src/Generated/Shared/Transfer/UserTransfer` |
UserTransfer.localName | attribute | created | src/Generated/Shared/Transfer/UserTransfer` |
UserTransfer.username | attribute | created | src/Generated/Shared/Transfer/UserTransfer` |
UserTransfer.password | attribute | created | src/Generated/Shared/Transfer/UserTransfer` |
UserTransfer.lastLogin | attribute | created | src/Generated/Shared/Transfer/UserTransfer` |
MessageTransfer | class | created | src/Generated/Shared/Transfer/MessageTransfer` |
TranslationTransfer | class | created | src/Generated/Shared/Transfer/TranslationTransfer` |
KeyTranslationTransfer | class | created | src/Generated/Shared/Transfer/KeyTranslationTransfer` |
OauthAuthenticationLinkTransfer | class | created | src/Generated/Shared/Transfer/OauthAuthenticationLinkTransfer |
ResourceOwnerTransfer | class | created | src/Generated/Shared/Transfer/ResourceOwnerTransfer` |
ResourceOwnerRequestTransfer | class | created | src/Generated/Shared/Transfer/ResourceOwnerRequestTransfer |
ResourceOwnerResponseTransfer | class | created | src/Generated/Shared/Transfer/ResourceOwnerResponseTransfer |
3) Set up the configuration
Add the following configuration to your project:
CONFIGURATION | SPECIFICATION | NAMESPACE |
---|---|---|
TranslatorConstants::TRANSLATION_ZED_FALLBACK_LOCALES | Fallback locales that are used if there is no translation for a selected locale. | Spryker\Shared\Translator |
TranslatorConstants::TRANSLATION_ZED_CACHE_DIRECTORY | Absolute path to a translation cache directory. For example, /var/www/data/DE/cache/Zed/translation . |
Spryker\Shared\Translator |
TranslatorConstants::TRANSLATION_ZED_FILE_PATH_PATTERNS | Paths to project level translations. You can use a global pattern that specifies sets of filenames with wildcard characters. | Spryker\Shared\Translator |
AclConstants::ACL_DEFAULT_RULES | Default rules for ACL functionality, where you can open access to some modules or controller out of the box. | Spryker\Shared\Acl |
config/Shared/config_default.php
use Spryker\Shared\Translator\TranslatorConstants;
// ----------- Translator
$config[TranslatorConstants::TRANSLATION_ZED_FALLBACK_LOCALES] = [
'de_DE' => ['en_US'],
];
$config[TranslatorConstants::TRANSLATION_ZED_CACHE_DIRECTORY] = sprintf(
'%s/data/%s/cache/Zed/translation',
APPLICATION_ROOT_DIR,
$CURRENT_STORE
);
$config[TranslatorConstants::TRANSLATION_ZED_FILE_PATH_PATTERNS] = [
APPLICATION_ROOT_DIR . '/data/translation/Zed/*/[a-z][a-z]_[A-Z][A-Z].csv',
];
// >> BACKOFFICE
// ACL: Allow or disallow of URLs for Zed GUI for ALL users
$config[AclConstants::ACL_DEFAULT_RULES] = [
[
'bundle' => 'security-gui',
'controller' => '*',
'action' => '*',
'type' => 'allow',
],
[
'bundle' => 'acl',
'controller' => 'index',
'action' => 'denied',
'type' => 'allow',
],
];
Set up an authentication strategy
Spryker offers two authentication strategies out of the box:
\Spryker\Zed\SecurityOauthUser\SecurityOauthUserConfig::AUTHENTICATION_STRATEGY_CREATE_USER_ON_FIRST_LOGIN
—If a user does not exist, it is created automatically based on the data from an external service.\Spryker\Zed\SecurityOauthUser\SecurityOauthUserConfig::AUTHENTICATION_STRATEGY_ACCEPT_ONLY_EXISTING_USERS
—Accepts only existing users for authentication.
src/Pyz/Zed/SecurityOauthUser/SecurityOauthUserConfig.php
<?php
namespace Pyz\Zed\SecurityOauthUser;
use Spryker\Zed\SecurityOauthUser\SecurityOauthUserConfig as SprykerSecurityOauthUserConfig;
class SecurityOauthUserConfig extends SprykerSecurityOauthUserConfig
{
/**
* Specification:
* - Defines by which strategy Oauth user authentication should be.
*
* @api
*
* @return string
*/
public function getAuthenticationStrategy(): string
{
return static::AUTHENTICATION_STRATEGY_CREATE_USER_ON_FIRST_LOGIN;
}
}
Having finished the entire integration, ensure that:
-
Entries without a translation for a language with a configured fallback are translated into the fallback language.
-
Translation cache is stored under the configured directory.
-
Translations are found based on the configured file path pattern.
4) Set up behavior
Set up the following behaviors.
Set up admin user login to the Back Office
Set up admin user login to the Back Office:
- Activate the following security plugins:
PLUGIN | SPECIFICATION | PREREQUISITES | NAMESPACE |
---|---|---|---|
SecurityApplicationPlugin | Extends the Zed global container with the services required for the Security functionality. | If there is WebProfilerApplicationPlugin in ApplicationDependencyProvider , put SecurityApplicationPlugin before it. |
Spryker\Zed\Security\Communication\Plugin\Application |
UserSessionHandlerSecurityPlugin | Sets an authenticated user to the session. | None | Spryker\Zed\User\Communication\Plugin\Securiy |
UserSecurityPlugin | Sets security firewalls, such as rules and handlers, for the Back Office users. | None | Spryker\Zed\SecurityGui\Communication\Plugin\Security |
UserPasswordResetMailTypePlugin | Adds a new email type, which is used by MailUserPasswordResetRequestHandlerPlugin . |
None | Spryker\Zed\UserPasswordResetMail\Communication\Plugin\Mail |
MailUserPasswordResetRequestHandlerPlugin | Sends a password reset email on a user request. | Mail module must be configured. UserPasswordResetMailTypePlugin is enabled. |
Spryker\Zed\UserPasswordResetMail\Communication\Plugin\UserPasswordReset |
OauthUserSecurityPlugin | Sets security firewalls, such as rules and handlers, for Oauth users. | None | \Spryker\Zed\SecurityOauthUser\Communication\Plugin\Security |
src/Pyz/Zed/Application/ApplicationDependencyProvider.php
<?php
namespace Pyz\Zed\Application;
use Spryker\Zed\Application\ApplicationDependencyProvider as SprykerApplicationDependencyProvider;
use Spryker\Zed\Security\Communication\Plugin\Application\SecurityApplicationPlugin;
class ApplicationDependencyProvider extends SprykerApplicationDependencyProvider
{
/**
* @return \Spryker\Shared\ApplicationExtension\Dependency\Plugin\ApplicationPluginInterface[]
*/
protected function getApplicationPlugins(): array
{
return [
new SecurityApplicationPlugin(),
// web profiler plugin should be after security plugin.
new WebProfilerApplicationPlugin(),
];
}
}
src/Pyz/Zed/Security/SecurityDependencyProvider.php
<?php
namespace Pyz\Zed\Security;
use Spryker\Zed\Security\SecurityDependencyProvider as SprykerSecurityDependencyProvider;
use Spryker\Zed\SecurityOauthUser\Communication\Plugin\Security\OauthUserSecurityPlugin;
class SecurityDependencyProvider extends SprykerSecurityDependencyProvider
{
/**
* @return \Spryker\Shared\SecurityExtension\Dependency\Plugin\SecurityPluginInterface[]
*/
protected function getSecurityPlugins(): array
{
return [
new UserSessionHandlerSecurityPlugin(),
new UserSecurityPlugin(),
new OauthUserSecurityPlugin(),
];
}
}
Ensure that https://mysprykershop.com/security-oauth-user/login
redirects you to the login page with the “Authentication failed!” message displayed.
src/Pyz/Zed/UserPasswordReset/UserPasswordResetDependencyProvider.php
<?php
namespace Pyz\Zed\UserPasswordReset;
use Spryker\Zed\UserPasswordReset\UserPasswordResetDependencyProvider as SprykerUserPasswordResetDependencyProvider;
use Spryker\Zed\UserPasswordResetMail\Communication\Plugin\UserPasswordReset\MailUserPasswordResetRequestHandlerPlugin;
class UserPasswordResetDependencyProvider extends SprykerUserPasswordResetDependencyProvider
{
/**
* @return \Spryker\Zed\UserPasswordResetExtension\Dependency\Plugin\UserPasswordResetRequestHandlerPluginInterface[]
*/
public function getUserPasswordResetRequestHandlerPlugins(): array
{
return [
new MailUserPasswordResetRequestHandlerPlugin(),
];
}
}
src/Pyz/Zed/Mail/MailDependencyProvider.php
<?php
use Spryker\Zed\Mail\MailDependencyProvider as SprykerMailDependencyProvider;
use Spryker\Zed\UserPasswordResetMail\Communication\Plugin\Mail\UserPasswordResetMailTypePlugin;
class MailDependencyProvider extends SprykerMailDependencyProvider
{
/**
* @param \Spryker\Zed\Kernel\Container $container
*
* @return \Spryker\Zed\Kernel\Container
*/
public function provideBusinessLayerDependencies(Container $container)
{
$container = parent::provideBusinessLayerDependencies($container);
$container->extend(static::MAIL_TYPE_COLLECTION, function (MailTypeCollectionAddInterface $mailCollection) {
$mailCollection
->add(new UserPasswordResetMailTypePlugin());
return $mailCollection;
});
return $container;
}
}
- Rebuild Zed router and Twig caches:
console router:cache:warm-up
console twig:cache:warmer
Ensure that:
-
You can open the Back Office login page or any page which requires authentication.
-
On the Back Office login page, the Forgot password? button redirects you to the password reset form.
-
You receive a password reset email to the email address you submitted the password reset form with.
Set up translation across the Back Office
To set up translation:
- Activate the following plugins for translation:
PLUGIN | SPECIFICATION | PREREQUISITES | NAMESPACE |
---|---|---|---|
TranslatorInstallerPlugin | Regenerates new translation caches for all locales of the current store. | None | Spryker\Zed\Translator\Communication\Plugin |
TranslationPlugin | Translates flash messages provided by the Messenger module. | None | Spryker\Zed\Translator\Communication\Plugin\Messenger |
TranslatorTwigPlugin | Extends Twig with Symfony’s translation extension and Spryker’s translator logic. | None | Spryker\Zed\Translator\Communication\Plugin\Twig |
UserLocaleLocalePlugin | Provides locale of the logged-in user as current locale. | Enable \Spryker\Zed\Locale\Communication\Plugin\Application\LocaleApplicationPlugin that sets the locale of the application based on the provided locale plugin. |
Spryker\Zed\UserLocale\Communication\Plugin\Locale |
AssignUserLocalePreSavePlugin | Expands UserTransfer before saving it with a locale ID and name. |
None | Spryker\Zed\UserLocale\Communication\Plugin\User |
UserLocaleTransferExpanderPlugin | Expands UserTransfer with a locale ID and name after reading it from the database. |
None | Spryker\Zed\UserLocale\Communication\Plugin\User |
UserLocaleFormExpanderPlugin | Expands the Edit user profile form with a locale field. | None | Spryker\Zed\UserLocaleGui\Communication\Plugin |
src/Pyz/Zed/Installer/InstallerDependencyProvider.php
<?php
namespace Pyz\Zed\Installer;
use Spryker\Zed\Installer\InstallerDependencyProvider as SprykerInstallerDependencyProvider;
use Spryker\Zed\Translator\Communication\Plugin\TranslatorInstallerPlugin;
class InstallerDependencyProvider extends SprykerInstallerDependencyProvider
{
/**
* @return \Spryker\Zed\Installer\Dependency\Plugin\InstallerPluginInterface[]
*/
public function getInstallerPlugins()
{
return [
new TranslatorInstallerPlugin(),
];
}
}
- Execute the registered installer plugins and install infrastructural data:
console setup:init-db
Ensure that the command:
-
cleaned previous translation cache in the translation folder, which is
data/{YourStore}/cache/Zed/translation
by default. -
generated translation cache files like
catalogue.{your_locale}.{randomString}.php
andcatalogue.{your_locale}.{randomString}.php.meta
in the translation folder, which isdata/{YourStore}/cache/Zed/translation
by default.
src/Pyz/Zed/Messenger/MessengerDependencyProvider.php
<?php
namespace Pyz\Zed\Messenger;
use Spryker\Zed\Messenger\MessengerDependencyProvider as SprykerMessengerDependencyProvider;
use Spryker\Zed\Translator\Communication\Plugin\Messenger\TranslationPlugin;
class MessengerDependencyProvider extends SprykerMessengerDependencyProvider
{
/**
* @return \Spryker\Zed\MessengerExtension\Dependency\Plugin\TranslationPluginInterface[]
*/
protected function getTranslationPlugins(): array
{
return [
/**
* TranslationPlugin needs to be after other translator plugins.
*/
new TranslationPlugin(),
];
}
}
src/Pyz/Zed/Twig/TwigDependencyProvider.php
<?php
namespace Pyz\Zed\Twig;
use Spryker\Zed\Translator\Communication\Plugin\Twig\TranslatorTwigPlugin;
use Spryker\Zed\Twig\TwigDependencyProvider as SprykerTwigDependencyProvider;
class TwigDependencyProvider extends SprykerTwigDependencyProvider
{
/**
* @return \Spryker\Shared\TwigExtension\Dependency\Plugin\TwigPluginInterface[]
*/
protected function getTwigPlugins(): array
{
return [
new TranslatorTwigPlugin(),
];
}
}
Ensure that the trans
and transChoice
Twig filters are working and using translations from the configured translation files.
src/Pyz/Zed/Locale/LocaleDependencyProvider.php
<?php
namespace Pyz\Zed\Locale;
use Spryker\Shared\LocaleExtension\Dependency\Plugin\LocalePluginInterface;
use Spryker\Zed\Locale\LocaleDependencyProvider as SprykerLocaleDependencyProvider;
use Spryker\Zed\UserLocale\Communication\Plugin\Locale\UserLocaleLocalePlugin;
class LocaleDependencyProvider extends SprykerLocaleDependencyProvider
{
/**
* @return \Spryker\Shared\LocaleExtension\Dependency\Plugin\LocalePluginInterface
*/
protected function getLocalePlugin(): LocalePluginInterface
{
return new UserLocaleLocalePlugin();
}
}
Ensure that the locale of the Back Office matches the locale of a logged-in user.
src/Pyz/Zed/User/UserDependencyProvider.php
<?php
namespace Pyz\Zed\User;
use Spryker\Zed\User\UserDependencyProvider as SprykerUserDependencyProvider;
use Spryker\Zed\UserLocale\Communication\Plugin\User\AssignUserLocalePreSavePlugin;
use Spryker\Zed\UserLocale\Communication\Plugin\User\UserLocaleTransferExpanderPlugin;
use Spryker\Zed\UserLocaleGui\Communication\Plugin\UserLocaleFormExpanderPlugin;
class UserDependencyProvider extends SprykerUserDependencyProvider
{
/**
* @return \Spryker\Zed\UserExtension\Dependency\Plugin\UserFormExpanderPluginInterface[]
*/
protected function getUserFormExpanderPlugins(): array
{
return [
new UserLocaleFormExpanderPlugin(),
];
}
/**
* @return \Spryker\Zed\UserExtension\Dependency\Plugin\UserPreSavePluginInterface[]
*/
protected function getUserPreSavePlugins(): array
{
return [
new AssignUserLocalePreSavePlugin(),
];
}
/**
* @return \Spryker\Zed\UserExtension\Dependency\Plugin\UserTransferExpanderPluginInterface[]
*/
protected function getUserTransferExpanderPlugins(): array
{
return [
new UserLocaleTransferExpanderPlugin(),
];
}
}
Ensure that you’ve enabled the plugins:
-
In the Back Office, go to Users > Users.
-
Select +Add New User.
-
On the Create new User page, check that the Interface language* field exists.
Set up console commands for cache
Set up the following console commands:
COMMAND | SPECIFICATION | [PREREQUISITES] | NAMESPACE |
---|---|---|---|
CleanTranslationCacheConsole | Cleans translation cache for Zed. | None | Spryker\Zed\Translator\Communication\Console |
GenerateTranslationCacheConsole | Generates translation cache for Zed. | None | Spryker\Zed\Translator\Communication\Console |
src/Pyz/Zed/Console/ConsoleDependencyProvider.php
<?php
namespace Pyz\Zed\Console;
use Spryker\Zed\Kernel\Container;
use Spryker\Zed\Console\ConsoleDependencyProvider as SprykerConsoleDependencyProvider;
use Spryker\Zed\Translator\Communication\Console\CleanTranslationCacheConsole;
use Spryker\Zed\Translator\Communication\Console\GenerateTranslationCacheConsole;
class ConsoleDependencyProvider extends SprykerConsoleDependencyProvider
{
/**
* @param \Spryker\Zed\Kernel\Container $container
*
* @return \Symfony\Component\Console\Command\Command[]
*/
protected function getConsoleCommands(Container $container)
{
$commands = [
new CleanTranslationCacheConsole(),
new GenerateTranslationCacheConsole(),
];
return $commands;
}
}
Regenerate translation cache:
console translator:clean-cache
console translator:generate-cache
Ensure that the command:
-
cleaned previous translation cache in the translation folder, which is
data/{YourStore}/cache/Zed/translation
by default. -
generated translator cache files like
catalogue.{your_locale}.{randomString}.php
andcatalogue.{your_locale}.{randomString}.php.meta
in the translation folder, which isdata/{YourStore}/cache/Zed/translation
by default.
Thank you!
For submitting the form