mirror of
https://github.com/silverstripe/silverstripe-framework
synced 2024-10-22 14:05:37 +02:00
Merge pull request #7169 from open-sausages/pulls/4.0/upgrade-docs-need-an-upgrade
Upgrade the upgrading docs
This commit is contained in:
commit
2bd24e0f98
@ -10,6 +10,7 @@ guide developers in preparing existing 3.x code for compatibility with 4.0
|
||||
* [Upgrading Guide](#upgrading)
|
||||
* [Standard Upgrade](#upgrading-primary)
|
||||
* [API Specific Upgrades](#upgrading-specifics)
|
||||
* [User code style upgrades](#usercode-style-upgrades)
|
||||
* [API Changes](#api-changes)
|
||||
* [General and Core API](#overview-general)
|
||||
* [ORM API](#overview-orm)
|
||||
@ -18,7 +19,7 @@ guide developers in preparing existing 3.x code for compatibility with 4.0
|
||||
* [i18n](#overview-i18n)
|
||||
* [Email and Mailer](#overview-mailer)
|
||||
* [SapphireTest](#overview-testing)
|
||||
* [Commit History](#commit-history)
|
||||
* [Security](#overview-security)
|
||||
|
||||
## <a name="overview"></a>Highlights of major changes
|
||||
|
||||
@ -26,10 +27,12 @@ guide developers in preparing existing 3.x code for compatibility with 4.0
|
||||
is required.
|
||||
* All code earlier marked as deprecated for 4.0 has now been removed. See
|
||||
[deprecation documentation](/contributing/release_process) for information on code deprecation.
|
||||
* All SilverStripe classes are now namespaced, and some have been renamed. This has major implications for
|
||||
* All code has been migrated to follow the PSR-2 coding standard. Most significantly, all SilverStripe
|
||||
classes are now namespaced, and some have been renamed. This has major implications for
|
||||
arrangement of templates, as well as other references to classes via string literals or configuration.
|
||||
Automatic upgrading tools have been developed to cope with the bulk of these changes (see
|
||||
[upgrading notes](#upgrading)).
|
||||
[upgrading notes](#upgrading)). Some classes have been rearranged so that each file contains only one class definition. It is recommended that user code follow the same convention.
|
||||
For example, page types and their controllers should longer be collated in a single file.
|
||||
* Object class has been removed.
|
||||
* Asset storage has been abstracted, and a new concept of `DBFile` references via database column references
|
||||
now exists in addition to references via the existing `File` dataobject. File security and protected files
|
||||
@ -74,7 +77,14 @@ as a standard first point of upgrade.
|
||||
#### Upgrade references to renamed and namespaced classes
|
||||
|
||||
Nearly all core PHP classes have been namespaced. For example, `DataObject` is now called `SilverStripe\ORM\DataObject`.
|
||||
We have developed an [upgrader tool](https://github.com/silverstripe/silverstripe-upgrader/) to (semi-)automatically update your 3.x code to the new naming. Here's an example how to upgrade your `mysite` folder:
|
||||
The below tasks describe how to upgrade an existing site to remain compatible with the newly upgraded classes.
|
||||
|
||||
##### Using the upgrader tool to automatically upgrade
|
||||
|
||||
This task should be run on every upgraded project.
|
||||
|
||||
We have developed an [upgrader tool](https://github.com/silverstripe/silverstripe-upgrader/) to (semi-)automatically
|
||||
update your 3.x code to the new naming. Here's an example how to upgrade your `mysite` folder:
|
||||
|
||||
```
|
||||
composer global require silverstripe/upgrader
|
||||
@ -92,6 +102,83 @@ For a full list of renamed classes, check the `.upgrade.yml` definitions in each
|
||||
|
||||
The rename won't affect class-based permission codes or database table names.
|
||||
|
||||
##### Upgrade references to literal or class table names
|
||||
|
||||
In 3.x the class name of any DataObject matched the table name, but in 4.x all classes are namespaced, and it is
|
||||
necessary to map between table and class for querying the database.
|
||||
|
||||
In order to ensure you are using the correct table for any class a new
|
||||
[DataObjectSchema](api:SilverStripe\ORM\DataObjectSchema) service is available to manage these mappings
|
||||
(see [versioned documentation](/developer_guides/model/data_model_and_orm)).
|
||||
|
||||
For example, the below shows how you would update a query with a hard-coded table name:
|
||||
|
||||
```diff
|
||||
public function countDuplicates($model, $fieldToCheck)
|
||||
{
|
||||
$query = new SilverStripe\ORM\Queries\SQLSelect();
|
||||
+ $table = SilverStripe\ORM\DataObject::getSchema()->tableForField($model, $field);
|
||||
- $query->setFrom("\"{$model}\"");
|
||||
+ $query->setFrom("\"{$table}\"");
|
||||
- $query->setWhere(["\"{$model}\".\"{$field}\"" => $model->$fieldToCheck]);
|
||||
+ $query->setWhere(["\"{$table}\".\"{$field}\"" => $model->$fieldToCheck]);
|
||||
return $query->count();
|
||||
}
|
||||
```
|
||||
|
||||
##### Replacing literal strings with fully qualified class name, or ::class constant
|
||||
|
||||
You'll need to update any strings that represent class names and make sure they're fully
|
||||
qualified. In particular, relationship definitions such as `has_one` and `has_many` will need
|
||||
to be updated to refer to fully qualified class names.
|
||||
|
||||
In configs and with literal PHP strings it is recommended to use the php `::class` constant,
|
||||
as demonstrated below.
|
||||
|
||||
```diff
|
||||
<?php
|
||||
+ use SilverStripe\ORM\DataObject;
|
||||
+ use SilverStripe\Security\Member;
|
||||
class MyClass extends DataObject
|
||||
{
|
||||
private static $has_one = [
|
||||
- 'Author' => 'Member',
|
||||
+ 'Author' => Member::class,
|
||||
];
|
||||
}
|
||||
```
|
||||
|
||||
In the context of YAML, the magic constant `::class` does not apply. Fully qualified class names must be hard coded.
|
||||
|
||||
```diff
|
||||
-MyObject:
|
||||
+My\Project\MyObject:
|
||||
property: value
|
||||
```
|
||||
|
||||
##### Update references to literal classes to use Injector
|
||||
|
||||
In many places, classes namespaced in SilverStripe 4.x will still have a non-namespaced service
|
||||
name that can be accessed via Injector. You should upgrade direct object constructors with
|
||||
the Injector API.
|
||||
|
||||
E.g.
|
||||
|
||||
```diff
|
||||
- $field = new Varchar();
|
||||
+ $field = Injector::inst()->create('Varchar');
|
||||
```
|
||||
|
||||
#### Migrate your controllers to their own files
|
||||
|
||||
The convention for naming controllers is now `[MyPageType]Controller`, where it used to be `[MyPageType]_Controller`. This change was made to be more compatible with the PSR-2 standards.
|
||||
|
||||
You can still use, for example, `Page_Controller`, but you will get a deprecation notice. It is
|
||||
best to change it to `PageController` during your upgrade process. Keep in mind any modules or
|
||||
other thirdparty code that extend `PageController` are likely to assume that class exists.
|
||||
|
||||
By default, a controller for a page type *must* reside in the same namespace as its page. To use different logic, override `SiteTree::getControllerName()`.
|
||||
|
||||
#### Upgrade template locations and references
|
||||
|
||||
Templates are now much more strict about their locations. You can no longer put a template in an arbitrary
|
||||
@ -109,6 +196,28 @@ Core template locations have moved - if you're including or overriding these
|
||||
no longer exists, and instead template locations will be placed in paths that match
|
||||
the `SilverStripe\Forms` namespace.
|
||||
|
||||
#### Upgrade static config settings to `private static`
|
||||
|
||||
If you have some class configuration statics defined and they aren't private,
|
||||
you may find that they don't register anymore. For example, this code, taken from
|
||||
the `silverstripe/tagfield` module will no longer work in SilverStripe 4.0.
|
||||
|
||||
```php
|
||||
public static $allowed_actions = [
|
||||
'suggest'
|
||||
];
|
||||
```
|
||||
|
||||
Changing the visibility to `private` (as per `RequestHandler::$allowed_actions`
|
||||
visibility) will make it 4.0 compatible.
|
||||
|
||||
```diff
|
||||
-public static $allowed_actions = [
|
||||
+private static $allowed_actions = [
|
||||
'suggest'
|
||||
];
|
||||
```
|
||||
|
||||
#### Upgrade module paths in file references
|
||||
|
||||
You should no longer rely on modules being placed in a deterministic folder (e.g. `/framework`),
|
||||
@ -172,15 +281,89 @@ To ensure consistency, we've also deprecated support for path constants:
|
||||
The below sections deal with upgrades to specific parts of various API. Projects which rely on certain
|
||||
API should be upgraded as appropriate using any of the relevant processes documented below.
|
||||
|
||||
#### Upgrade references of SS_Log to use PSR-3 logging
|
||||
|
||||
One of the great changes that comes with SilverStripe 4 is the introduction of
|
||||
[PSR-3](http://www.php-fig.org/psr/psr-3/) compatible logger interfaces. This
|
||||
means we can use thirdparty services like Monolog. `SS_Log` has been replaced
|
||||
with a logger which can be accessed using the LoggerInterface::class service.
|
||||
|
||||
For instance, code which logs errors should be upgraded as below:
|
||||
|
||||
```diff
|
||||
-SS_Log::log('My error message', SS_Log::ERR);
|
||||
+use Psr\Log\LoggerInterface;
|
||||
+Injector::inst()->get(LoggerInterface::class)->error('My error message');
|
||||
```
|
||||
|
||||
##### How to customise the default PSR-3 logger
|
||||
|
||||
If necessary, you may need to customise either the default logging handler, or
|
||||
one of the error formatters. For example, if running unit tests you may want to
|
||||
suppress errors. You can temporarily disable logging by setting a `NullHandler`
|
||||
|
||||
```yml
|
||||
---
|
||||
Name: custom-dev-logging
|
||||
After: dev-logging
|
||||
Only:
|
||||
environment: dev
|
||||
---
|
||||
# Replace default handler with null
|
||||
SilverStripe\Core\Injector\Injector:
|
||||
Monolog\Handler\HandlerInterface: Monolog\Handler\NullHandler
|
||||
```
|
||||
|
||||
Alternatively you can customise one or both of the below services:
|
||||
- `Monolog\Formatter\FormatterInterface.detailed` service, which is used for displaying
|
||||
detailed error messages useful for developers.
|
||||
- `Monolog\Formatter\FormatterInterface.friendly` service, which is used to display "error"
|
||||
page content to visitors of the site who encounter errors.
|
||||
|
||||
For example, a custom error page generator could be added as below:
|
||||
|
||||
```yml
|
||||
---
|
||||
Name: custom-errorpage
|
||||
After:
|
||||
- '#loggingformatters'
|
||||
---
|
||||
SilverStripe\Core\Injector\Injector:
|
||||
Monolog\Formatter\FormatterInterface.friendly:
|
||||
class: WebDesignGroup\ShopSite\Logging\ErrorPageFormatter
|
||||
```
|
||||
|
||||
`WebDesignGroup\ShopSite\Logging\ErrorPageFormatter` should be a class that
|
||||
implements the `Monolog\Formatter\FormatterInterface` interface.
|
||||
|
||||
#### Upgrade `mysite/_config.php`
|
||||
|
||||
The globals `$database` and `$databaseConfig` are deprecated. You should upgrade your
|
||||
site _config.php files to use the `.env` configuration (below).
|
||||
|
||||
If you need to configure database details in PHP, use the new `DB::setConfig()` api instead.
|
||||
`conf/ConfigureFromEnv.php` is also no longer used, and references to this file should be deleted.
|
||||
|
||||
You should remove any references to `ConfigureFromEnv.php` in your project, as this file
|
||||
is no longer necessary.
|
||||
If you need to configure database details in PHP you should configure these details via `.env` file,
|
||||
or alternatively (but less recommended) use the new `DB::setConfig()` api.
|
||||
|
||||
The global `$project` is deprecated in favour of the configuration setting
|
||||
`SilverStripe\Core\Manifest\ModuleManifest.project`.
|
||||
|
||||
Changes to `mysite/_config.php`:
|
||||
|
||||
```diff
|
||||
<?php
|
||||
-global $project;
|
||||
-$project = 'mysite';
|
||||
-include 'conf/ConfigureFromEnv.php';
|
||||
```
|
||||
|
||||
And also add to `mysite/_config/mysite.yml`:
|
||||
|
||||
```yml
|
||||
SilverStripe\Core\Manifest\ModuleManifest:
|
||||
project: mysite
|
||||
```
|
||||
|
||||
#### Upgrade of `_ss_environment.php` to `.env` configuration
|
||||
|
||||
@ -204,7 +387,7 @@ $_FILE_TO_URL_MAPPING[__DIR__] = 'http://localhost';
|
||||
// Database
|
||||
define('SS_DATABASE_CHOOSE_NAME', true);
|
||||
define('SS_DATABASE_CLASS', 'MySQLDatabase');
|
||||
define('SS_DATABASE_USERNAME', 'root')
|
||||
define('SS_DATABASE_USERNAME', 'root');
|
||||
define('SS_DATABASE_PASSWORD', '');
|
||||
define('SS_DATABASE_SERVER', '127.0.0.1');
|
||||
```
|
||||
@ -548,7 +731,7 @@ In YML format this will be expressed as the below:
|
||||
`mymodule/lang/en.yml`:
|
||||
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
en:
|
||||
MyObject:
|
||||
SINGULAR_NAME: 'object'
|
||||
@ -561,7 +744,7 @@ en:
|
||||
`extendedmodule/lang/en.yml`:
|
||||
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
en:
|
||||
AnotherSection:
|
||||
DESCRIPTION: 'This is the description for this section'
|
||||
@ -612,7 +795,7 @@ In order to retain existing file paths in line with framework version 3 you shou
|
||||
Note that this will not allow you to utilise certain file versioning features in 4.0.
|
||||
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
SilverStripe\Filesystem\Flysystem\FlysystemAssetStore:
|
||||
legacy_paths: true
|
||||
```
|
||||
@ -629,7 +812,7 @@ this task is run manually during an explicit migration process, as this process
|
||||
large amounts of memory and run for an extended time.
|
||||
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
File:
|
||||
migrate_legacy_file: true
|
||||
```
|
||||
@ -850,14 +1033,14 @@ use SilverStripe\ORM\FieldType\DBComposite;
|
||||
|
||||
class MyAddressField extends DBComposite
|
||||
{
|
||||
private static $composite_db = ]
|
||||
private static $composite_db = [
|
||||
'Street' => 'Varchar(200)',
|
||||
'Suburb' => 'Varchar(100)',
|
||||
'City' => 'Varchar(100)',
|
||||
'Country' => 'Varchar(100)'
|
||||
];
|
||||
|
||||
public function scaffoldFormField($title = null)
|
||||
public function scaffoldFormField($title = null, $params = null)
|
||||
{
|
||||
new SilverStripe\Forms\TextField($this->getName(), $title);
|
||||
}
|
||||
@ -891,39 +1074,6 @@ these references should be replaced with `SQLSelect`. Legacy code which generate
|
||||
`SQLQuery` can still communicate with new code that expects `SQLSelect` as it is a
|
||||
subclass of `SQLSelect`, but the inverse is not true.
|
||||
|
||||
#### Upgrade code that references table names
|
||||
|
||||
A major change in 4.0.0 is that now tables and class names can differ from model to model. In order to
|
||||
fix a table name, to prevent it being changed (for instance, when applying a namespace to a model)
|
||||
the `table_name` config can be applied to any DataObject class.
|
||||
|
||||
|
||||
```php
|
||||
namespace SilverStripe\BannerManager;
|
||||
|
||||
use SilverStripe\ORM\DataObject;
|
||||
|
||||
class BannerImage extends DataObject
|
||||
{
|
||||
private static $table_name = 'BannerImage';
|
||||
}
|
||||
```
|
||||
|
||||
In order to ensure you are using the correct table for any class a new [DataObjectSchema](api:SilverStripe\ORM\DataObjectSchema) service
|
||||
is available to manage these mappings (see [versioned documentation](/developer_guides/model/data_model_and_orm)).
|
||||
|
||||
|
||||
```php
|
||||
public function countDuplicates($model, $fieldToCheck)
|
||||
{
|
||||
$table = SilverStripe\ORM\DataObject::getSchema()->tableForField($model, $field);
|
||||
$query = new SilverStripe\ORM\Queries\SQLSelect();
|
||||
$query->setFrom("\"{$table}\"");
|
||||
$query->setWhere(["\"{$table}\".\"{$field}\"" => $model->$fieldToCheck]);
|
||||
return $query->count();
|
||||
}
|
||||
```
|
||||
|
||||
#### Upgrade BuildTask classes
|
||||
|
||||
Similarly to the `$table_name` configuration property for DataObjects, you should define a `private static $segment` for `BuildTask`
|
||||
@ -1105,10 +1255,43 @@ These methods are deprecated:
|
||||
#### Implementation of ownership API
|
||||
|
||||
In order to support the recursive publishing of dataobjects, a new API has been developed to allow
|
||||
developers to declare dependencies between objects. See the
|
||||
[versioned documentation](/developer_guides/model/versioning) for more information.
|
||||
developers to declare dependencies between objects. This is done to ensure that the published state
|
||||
of linked components are consistent with their "owner." Without the concept of ownership, these linked
|
||||
components could be implicitly exposed on the frontend, which may not align with the intent of the
|
||||
content author.
|
||||
|
||||
By default all versioned dataobjects will automatically publish objects that they own.
|
||||
For instance, on a products page which has a list of products, the products should not be published unless the products page is, too. The ownership API solves this by allowing you to declare
|
||||
a two-way relationship between objects, typically, but not necessarily, linked by a database relationship
|
||||
(`has_many`, `many_many`, etc.).
|
||||
|
||||
```php
|
||||
class ProductPage extends Page
|
||||
{
|
||||
private static $has_many = [
|
||||
'Products' => Product::class
|
||||
];
|
||||
|
||||
private static $owns = [
|
||||
'Products'
|
||||
];
|
||||
}
|
||||
|
||||
class Product extends DataObject
|
||||
{
|
||||
private static $extensions = [
|
||||
Versioned::class
|
||||
];
|
||||
|
||||
private static $has_one = [
|
||||
'Parent' => ProductPage::class
|
||||
];
|
||||
}
|
||||
```
|
||||
If your objects are linked by something other than a database relationship, for instance, a custom
|
||||
getter that is computed at runtime, the same rules can be applied, as long as you provide an `$owned_by`
|
||||
setting on the child object.
|
||||
|
||||
For more information, see the [DataObject ownership](https://docs.silverstripe.org/en/4/developer_guides/model/versioning/#dataobject-ownership) documentation and the [versioning](/developer_guides/model/versioning) documentation
|
||||
|
||||
#### ChangeSet batch publishing
|
||||
|
||||
@ -1210,7 +1393,7 @@ specific functions.
|
||||
|
||||
The methods `register` and `unregister` on `Authenticator` are deprecated in favor of the `Config` system. This means that any custom Authenticator needs to be registered through the yml config:
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
SilverStripe\Security\Authenticator;
|
||||
authenticators:
|
||||
- MyVendor\MyModule\MyAuthenticator
|
||||
@ -1218,7 +1401,7 @@ SilverStripe\Security\Authenticator;
|
||||
|
||||
If there is no authenticator registered, `Authenticator` will try to fall back on the `default_authenticator`, which can be changed using the following config, replacing the MemberAuthenticator with your authenticator:
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
SilverStripe\Security\Authenticator:
|
||||
default_authenticator: SilverStripe\Security\MemberAuthenticator
|
||||
```
|
||||
@ -1254,7 +1437,6 @@ This also allowed us to remove SilverStripe's `Cache` API and use dependency inj
|
||||
Caches should be retrieved through `Injector` instead of `Cache::factory()`,
|
||||
and have a slightly different API (e.g. `set()` instead of `save()`).
|
||||
|
||||
|
||||
```diff
|
||||
-$cache = Cache::factory('myCache');
|
||||
+use Psr\SimpleCache\CacheInterface;
|
||||
@ -1281,10 +1463,9 @@ and have a slightly different API (e.g. `set()` instead of `save()`).
|
||||
+$cache->delete('myCacheKey');
|
||||
```
|
||||
|
||||
With the necessary minimal config in `_config/mycache.yml`
|
||||
With the necessary minimal config in _config/mycache.yml
|
||||
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
---
|
||||
Name: mycache
|
||||
---
|
||||
@ -1295,13 +1476,12 @@ SilverStripe\Core\Injector\Injector:
|
||||
namespace: 'mycache'
|
||||
```
|
||||
|
||||
|
||||
##### Configuration Changes
|
||||
|
||||
Caches are now configured through dependency injection services instead of PHP.
|
||||
See our ["Caching" docs](/developer-guides/performance/caching) for more details.
|
||||
|
||||
Before (`mysite/_config.php`):
|
||||
Before (mysite/_config.php):
|
||||
|
||||
```php
|
||||
Cache::add_backend(
|
||||
@ -1317,9 +1497,9 @@ Cache::add_backend(
|
||||
Cache::pick_backend('primary_memcached', 'any', 10);
|
||||
```
|
||||
|
||||
After (`mysite/_config/config.yml`):
|
||||
After (mysite/_config/config.yml):
|
||||
|
||||
```yaml
|
||||
```yml
|
||||
---
|
||||
After:
|
||||
- '#corecache'
|
||||
@ -1335,6 +1515,158 @@ SilverStripe\Core\Injector\Injector:
|
||||
client: '%$MemcachedClient
|
||||
```
|
||||
|
||||
### <a name="usercode-style-upgrades"></a>User-code style upgrades
|
||||
|
||||
Although it is not mandatory to upgrade project code to follow SilverStripe and
|
||||
PSR-2 standard it is highly recommended to ensure that code is consistent. The below sections
|
||||
will assist you with bringing yourself up to speed.
|
||||
|
||||
Please note that before upgrading user code style it is necessary to run the standard upgrade path
|
||||
to fix references and usages of framework API.
|
||||
|
||||
#### Upgrading user-code to use namespaces
|
||||
|
||||
Upgrading code to use namespaces is quite a complex process, and as such we have provided
|
||||
several development tools and processes to help make the upgrade user friendly and as
|
||||
automated as possible.
|
||||
|
||||
##### Using the upgrader tool to automatically apply namespaces
|
||||
|
||||
The [upgrader tool](https://github.com/silverstripe/silverstripe-upgrader/) provides a feature
|
||||
to not only automatically namespace code, but will provide automatic upgrade of other code
|
||||
references to those classes.
|
||||
|
||||
Use the below to setup upgrader, and apply a namespace to a given code folder.
|
||||
|
||||
```
|
||||
composer global require silverstripe/upgrader
|
||||
cd ~/Project/Root
|
||||
~/.composer/vendor/bin/upgrade-code add-namespace "WebDesignGroup\ShopSite" ./mysite/code --recursive --write
|
||||
```
|
||||
|
||||
If you want to do a dry-run, omit the `--write` option to see a preview of a diff of
|
||||
all changed project files.
|
||||
|
||||
This task will do the following:
|
||||
|
||||
- Add the given namespace to all files in the code class, and subdirectories.
|
||||
- Sub-namespaces will be applied based on directory structure
|
||||
- All references to classes in any namespaced files will be safely retained with additional `use` directives
|
||||
added as necessary.
|
||||
- Register all namespaced classese in a mysite/.upgrade.yml file for migration of other code
|
||||
|
||||
This task will not do the following, and must be done manually:
|
||||
|
||||
- Adding `table_name` to any namespaced classes
|
||||
- Upgrade other references to namespaced classes outside of this folder
|
||||
- Migrate any database table records
|
||||
|
||||
Please see the following steps for more information.
|
||||
|
||||
##### Using the upgrader tool to update references to namespaced user classes
|
||||
|
||||
Once a project has been namespaced all newly renamed classes will have a mapping included in the `mysite/.upgrade.yml`
|
||||
file. If you have any user-code that references these, you may need to run the upgrader again (as you did did
|
||||
to upgrade your project to namespaced framework classe).
|
||||
|
||||
```
|
||||
composer global require silverstripe/upgrader
|
||||
cd ~/Project/Root
|
||||
~/.composer/vendor/bin/upgrade-code upgrade ./othercode --write
|
||||
```
|
||||
|
||||
##### Updating custom dataobjects to use existing table names
|
||||
|
||||
Once you have namespaced your user code it will be necessary to customise the `table_name` config
|
||||
for your dataobjects, in order to ensure the correct table is used after upgrade. It is recommended
|
||||
to point this to the base name of the class, excluding namespace, as in 3.x.
|
||||
|
||||
```diff
|
||||
namespace WebDesignGroup\ShopSite;
|
||||
use SilverStripe\ORM\DataObject;
|
||||
use Page;
|
||||
class GalleryPage extends Page
|
||||
{
|
||||
+ private static $table_name = 'GalleryPage';
|
||||
}
|
||||
```
|
||||
|
||||
##### Class name remapping
|
||||
|
||||
If you've namespaced one of your custom page types, you may notice a message in the CMS
|
||||
telling you it's obsolete. This is likely because the `ClassName`
|
||||
field in the `SiteTree` table still contains the singular model name, e.g. `GalleryPage`
|
||||
and that when you change it to `WebDesignGroup\ShopSite\GalleryPage` then everything
|
||||
works again.
|
||||
|
||||
The `dev/build` task is configured to look for a legacy class name mapping
|
||||
configuration setting and will update this for you automatically. You can use
|
||||
this to add DB upgrading rules for your own classes.
|
||||
|
||||
For example, you could upgrade references to the newly namespaced Banner class by adding
|
||||
this to your `mysite/_config/upgrade.yml` file:
|
||||
|
||||
```yml
|
||||
SilverStripe\ORM\DatabaseAdmin:
|
||||
classname_value_remapping:
|
||||
GalleryPage: WebDesignGroup\ShopSite\GalleryPage
|
||||
```
|
||||
|
||||
The next time you run a dev/build the class name for all `GalleryPage` pages will
|
||||
be automatically updated to the new `WebDesignGroup\ShopSite\GalleryPage`
|
||||
|
||||
#### Using php code checker to automatically update to PSR-2
|
||||
|
||||
You can use the [php codesniffer](https://github.com/squizlabs/PHP_CodeSniffer) tool
|
||||
to not only detect and lint PSR-2 coding errors, but also do some minimal automatic
|
||||
code style migration.
|
||||
|
||||
- Install the necessary library:
|
||||
`composer require squizlabs/php_codesniffer`
|
||||
- Copy silverstripe standards config file from framework/phpcs.xml to your project root:
|
||||
`cp ./framework/phpcs.xml ./phpcs.xml`
|
||||
- Run the automatic upgrade tool on your code folder
|
||||
`vendor/bin/phpcbf ./mysite/code`
|
||||
- Run the automatic linting tool to detect and manually fix other errors:
|
||||
`vendor/bin/phpcs ./mysite/code`
|
||||
|
||||
Repeat the final step and manually repair suggested changes, as necessary,
|
||||
until you no longer have any linting issues.
|
||||
|
||||
#### Upgrade user-code to use PSR-4 autoloading
|
||||
|
||||
While not critical to an upgrade, SilverStripe 4.0 has adopted the [PS-4 autoloading](http://www.php-fig.org/psr/psr-4/)
|
||||
standard for the core modules, so it's probably a good idea to be consistent.
|
||||
|
||||
You can implement this in your composer configuration like so:
|
||||
|
||||
```json
|
||||
{
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"WebDesignGroup\\ShopSite\\": "mysite/src/"
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
Now you just need to ensure that each class site in the correct folder location
|
||||
(including case sensitivity) to match its namespace. For example,
|
||||
`WebDesignGroup\ShopSite\Model\GalleryItem.php` should live at `mysite/src/Model/GalleryItem.php`.
|
||||
|
||||
Note that you don’t have to use `src/` as the root folder name. You can continue
|
||||
to use `code/` if you want to. SilverStripe has adopted the PSR-4 approach and
|
||||
have also started to use `src/` as a default folder location instead of
|
||||
`code/`. If you’re going to change, it's probably a good time to do it while you're
|
||||
upgrading.
|
||||
|
||||
For examples, take a look at the file/folder structure and to the
|
||||
`composer.json` configuration in either the `framework` or `cms` modules.
|
||||
|
||||
Please note that there are changes to template structure which in some cases
|
||||
require templates to be in a folder location that matches the namespace of the class
|
||||
that it belongs to, e.g. `themes/mytheme/templates/MyVendor/Foobar/Model/MyModel.ss`.
|
||||
|
||||
## <a name="api-changes"></a>API Changes
|
||||
|
||||
### <a name="overview-general"></a>General and Core API
|
||||
@ -2056,10 +2388,8 @@ New `TimeField` methods replace `getConfig()` / `setConfig()`
|
||||
* `i18n::get_language_code()` removed.
|
||||
* `i18n::get_common_locales()` removed.
|
||||
* `i18n.common_locales` config removed
|
||||
|
||||
### <a name="overview-mailer"></a>Email and Mailer
|
||||
|
||||
#### <a name="overview-mailer-api"></a>Email Additions / Changes
|
||||
#### <a name="overview-mailer"></a>Email Additions / Changes
|
||||
|
||||
* `Mailer` converted to an interface
|
||||
* `SwfitMailer` added as new default mailer
|
||||
@ -2080,7 +2410,7 @@ New `TimeField` methods replace `getConfig()` / `setConfig()`
|
||||
* `SapphireTest::$extraDataObjects` renamed to `SapphireTest::$extra_dataobjects` and made static
|
||||
* `SapphireTest::$extraControllers` renamed to `SapphireTest::$extra_controllers` and made static
|
||||
|
||||
### <a name="overview-testing"></a>Security
|
||||
### <a name="overview-security"></a>Security
|
||||
|
||||
* `LoginForm` now has an abstract method `getAuthenticatorName()`. If you have made subclasses of this,
|
||||
you will need to define this method and return a short name describing the login method.
|
||||
|
Loading…
Reference in New Issue
Block a user