mirror of
https://github.com/silverstripe/silverstripe-framework
synced 2024-10-22 14:05:37 +02:00
Restructured 3.0 changelog
Moved some more important stuff up the page, rewritten upgrading overview to be more task focused, reduced excessive use of paragraphs to make the text more scannable.
This commit is contained in:
parent
2b5214b55a
commit
de73db9ef7
@ -2,43 +2,89 @@
|
||||
|
||||
## Overview ##
|
||||
|
||||
* New template engine
|
||||
* New CMS interface design
|
||||
* Image/Link insertion moved into a modal dialog instead of a sidebar
|
||||
### CMS
|
||||
|
||||
* New CMS interface design more geared towards complex content solutions
|
||||
* List view for pages (sortable and filterable)
|
||||
* More powerful media and link insertion (including auto-embedding of external sources)
|
||||
* Batch actions on site tree moved to an "Edit Tree" view
|
||||
* "Add pages" dropdown now an "Add new" button which goes to a more descriptive page
|
||||
* Renaming of sapphire to SilverStripe framework
|
||||
* FormField classes now have their own HTML templates
|
||||
* Allow usage of SilverStripe framework without the "cms" module
|
||||
* "Add pages" shows a dedicated interface with more info about the page type
|
||||
* CMS JavaScript moved to [jQuery.entwine](https://github.com/hafriedlander/jquery.entwine)
|
||||
* CMS stylesheets are generated by SCSS to provide more flexible and robust styling
|
||||
|
||||
### Framework
|
||||
|
||||
* Renaming of "sapphire" to SilverStripe "framework"
|
||||
* Allow usage of SilverStripe framework without the "cms" module
|
||||
* New template engine with more powerful syntax
|
||||
* New ORM layer with expressive and fluent syntax
|
||||
* New GridField component to replace ComplexTableField
|
||||
* FormField classes now have their own HTML templates
|
||||
* Moved functionality to modules: Widget, RestfulServer, SapphireSoapServer, Translatable, IPRestrictions, PageComment, HomepageForDomain
|
||||
|
||||
## Upgrading ##
|
||||
|
||||
### Overview
|
||||
### Common Upgrade Tasks
|
||||
|
||||
* Folders: `sapphire/` moved to `framework/`, replace with `FRAMEWORK_DIR` (in PHP) or `$ModulePath(framework)` (in templates). Be sure to update `.htaccess` or `web.config` ([more](#sapphire-rename))
|
||||
* Templates: `<% control %>` replaced by `<% loop %>` and `<% with %>` ([more](/reference/templates-upgrading-guide#control))
|
||||
* `DataObjectSet` is replaced by `DataList`; beware that `DataList->remove()` will delete an entry from the database ([more](#deprecated-classes))
|
||||
* `ComplexTableField` is replaced by `GridField`, which is similar to the `DataObjectManager` extension.
|
||||
* `Director::redirect()` and `Director::redirectBack()` deprecated ([more] (#director-static-functions-deprecated-director-redirect-and-director-redirectback-in-particular)
|
||||
* Changes in ORM, DataObject::get() deprecated ([more](#new-orm-datalist))
|
||||
* `DataObjectDecorator::extraStatics` deprecated ([more](#extensions))
|
||||
* Backend tab paths are shortened: `Root.Content.Main` becomes `Root.Main` ([more](#tab-paths))
|
||||
* Rename foder from `sapphire/`to `framework/`, replace own paths with `FRAMEWORK_DIR` (in PHP) or `$ModulePath(framework)` (in templates). Update paths in `.htaccess` or `web.config` ([more](#sapphire-rename))
|
||||
* Replace `<% control %>` in your templates with `<% loop %>` and `<% with %>` ([more](/reference/templates-upgrading-guide#control))
|
||||
* Replace `DataObjectSet` with `DataList` or `ArrayList` ([more](#deprecated-classes))
|
||||
* Rewrite `ComplexTableField` and `DataObjectManager` instances to `GridField`
|
||||
* Rewrite `Director::redirect()` and `Director::redirectBack()` calls ([more] (#director-static-functions-deprecated-director-redirect-and-director-redirectback-in-particular)
|
||||
* Use `<MyModel>::get()` rather than `DataObject::get()` ([more](#new-orm-datalist))
|
||||
* Use new syntax for `DataObjectDecorator::extraStatics` ([more](#extensions))
|
||||
* Change CMS tab paths from `Root.Content.Main` to `Root.Main`, move some field changes to new `SiteTree->getSettingsFields()` method ([more](#tab-paths))
|
||||
* Add new modules if using specific core features like Widget, RestfulServer, PageComment or Translatable
|
||||
|
||||
### sapphire renamed to framework {#sapphire-rename}
|
||||
|
||||
`sapphire` has been renamed to `framework`.
|
||||
|
||||
Please ensure the framework now resides in the new folder when upgrading.
|
||||
|
||||
Here's a list of steps to check:
|
||||
The `sapphire` module has been renamed to `framework`. Please ensure the framework now resides in the new folder when upgrading. Here's a list of steps to check:
|
||||
|
||||
* Remove your existing `sapphire` directory, and replace with `framework` from the new SilverStripe 3.0 package
|
||||
* Rename references of `sapphire` to `framework` in `.htaccess`, `web.config` and `/usr/bin/sake` (the last is only necessary if you use `sake`)
|
||||
* Find and replace any references to `sapphire` in your custom code to `framework`. In your PHP code, you can use the constant `FRAMEWORK_DIR`,
|
||||
which points to the framework directory, and in the templates you can use `$ModulePath(framework)`
|
||||
|
||||
### GridField: Replacement for TableListField and ComplexTableField [gridfield]###
|
||||
|
||||
We have a new component for managing lists of objects: The `[GridField](/topics/grid-field)`.
|
||||
It's a substantial rewrite of the features previously captured by `TableListField`,
|
||||
`ComplexTableField`, `HasManyComplexTableField` and `ManyManyComplexTableField`.
|
||||
|
||||
The legacy fields remain operational for now, although a switch to `GridField` is strongly encouraged,
|
||||
for stability, interface and performance reasons. The `HasManyComplexTableField` and `ManyManyComplexTableField`
|
||||
are no longer maintained, for those you do have to make the switch.
|
||||
The `TableField` class will be deprecated soon, but we don't have an adequate replacement for it yet.
|
||||
|
||||
Upgrade example: Record listing
|
||||
|
||||
:::php
|
||||
// before
|
||||
$field = new TableListField('Companies', 'Company');
|
||||
$field->setPageSize(20);
|
||||
// after
|
||||
$field = new GridField('Companies', null, Company::get());
|
||||
$field->getConfig()->getComponentByType('GridFieldPaginator')->setItemsPerPage(20);
|
||||
|
||||
Upgrade example: Record listing with view/edit interface
|
||||
|
||||
:::php
|
||||
// before
|
||||
$field = new ComplexTableField($myController, 'Companies', 'Company');
|
||||
// after
|
||||
$field = new GridField('Companies', null, Company::get(), GridFieldConfig_RecordEditor::create());
|
||||
|
||||
|
||||
Upgrade example: Relationship editing
|
||||
|
||||
:::php
|
||||
// before
|
||||
$field = new HasManyComplexTableField($myController, 'MyRelation', 'MyRelationObject');
|
||||
// after
|
||||
$field = new GridField('MyRelation', null, $myRecord->MyRelation(), GridFieldConfig_RelationEditor::create());
|
||||
|
||||
More information is available in the [GridField documentation](/topics/grid-field).
|
||||
|
||||
### Object static functions replaced with new Config class {#new-config}
|
||||
Static functions for getting a static variable on the `Object` class have been deprecated,
|
||||
in favour of using the new `Config` class instead.
|
||||
@ -63,21 +109,17 @@ Note the different options for the third parameter of `get()`:
|
||||
If you don't set an option, it will get all the values for the static, including inherited ones.
|
||||
This was previously known as `Object::combined_static()`.
|
||||
|
||||
### Director static functions deprecated, Director::redirect() and Director::redirectBack() in particular
|
||||
### Director static functions deprecated (e.g. redirect() and redirectBack())
|
||||
|
||||
`Director::redirect()` and `Director::redirectBack()` are now marked as deprecated.
|
||||
`Director::redirect()` and `Director::redirectBack()` are now marked as deprecated. If you have a `Controller` instance and need to redirect, call `redirect()` or `redirectBack()` on the instance
|
||||
instead, e.g. `$controller->redirect()` or `$controller->redirectBack()`. Most of the time, form action handler methods on a controller need only call `$this->redirect()` or `$this->redirectBack()`.
|
||||
|
||||
If you have a `Controller` instance and need to redirect, call `redirect()` or `redirectBack()` on the instance
|
||||
instead, e.g. `$controller->redirect()` or `$controller->redirectBack()`. Most of the time, form action handler
|
||||
methods on a controller need only call `$this->redirect()` or `$this->redirectBack()`.
|
||||
|
||||
Use `Controller::curr()->redirect()` and `Controller::curr()->redirectBack()` if you need to redirect in contexts
|
||||
where a controller might not be immediately available.
|
||||
Use `Controller::curr()->redirect()` and `Controller::curr()->redirectBack()` if you need to redirect in contexts where a controller might not be immediately available.
|
||||
|
||||
### DataExtension and deprecated extraStatics on extension classes {#extensions}
|
||||
|
||||
`DataObjectDecorator` has been renamed to `DataExtension`. Any classes that extend `DataObjectDecorator`
|
||||
should now extend `DataExtension` instead.
|
||||
`DataObjectDecorator` has been renamed to `DataExtension`. Please extend this class in case you
|
||||
have written your own extensions.
|
||||
|
||||
`extraStatics()` on extensions is now deprecated.
|
||||
|
||||
@ -86,10 +128,10 @@ Instead of using `extraStatics()`, you can simply define static variables on you
|
||||
If you need custom logic, e.g. checking for a class before applying the statics on the extension,
|
||||
you can use `add_to_class()` as a replacement to `extraStatics()`.
|
||||
|
||||
Given the original `extraStatics` function:
|
||||
:::php
|
||||
class MyExtension extends Extension {
|
||||
|
||||
<?php
|
||||
//...
|
||||
// before
|
||||
function extraStatics($class, $extensionClass) {
|
||||
if($class == 'MyClass') {
|
||||
return array(
|
||||
@ -100,11 +142,12 @@ Given the original `extraStatics` function:
|
||||
}
|
||||
}
|
||||
|
||||
This would now become a static function `add_to_class`, and calls `update()` with an array
|
||||
instead of returning it. It also needs to call `parent::add_to_class()`:
|
||||
// after
|
||||
static $db = array(
|
||||
'Title' => 'Varchar'
|
||||
);
|
||||
|
||||
<?php
|
||||
//...
|
||||
// advanced syntax
|
||||
static function add_to_class($class, $extensionClass, $args = null) {
|
||||
if($class == 'MyClass') {
|
||||
Config::inst()->update($class, 'db', array(
|
||||
@ -113,14 +156,8 @@ instead of returning it. It also needs to call `parent::add_to_class()`:
|
||||
}
|
||||
parent::add_to_class($class, $extensionClass, $args);
|
||||
}
|
||||
}
|
||||
|
||||
Alternatively, you can define statics on the extension directly, like this:
|
||||
|
||||
<?php
|
||||
//...
|
||||
static $db = array(
|
||||
'Title' => 'Varchar'
|
||||
);
|
||||
|
||||
### New ORM: More flexible and expressive querying via `DataList` {#new-orm-datalist}
|
||||
|
||||
@ -163,6 +200,7 @@ for the presence of records, please call the count() method on the `DataList`:
|
||||
// after
|
||||
if(!DataObject::get('SiteTree', '"ParentID" = 5')->count()) echo "Page 5 has no children";
|
||||
|
||||
Beware that `DataList->remove()` will delete an entry from the database.
|
||||
See the ["datamodel" documentation](../../topics/datamodel) for more details.
|
||||
|
||||
### New ORM: Changes to manipulation of SQL queries {#new-orm-sql-queries}
|
||||
@ -204,23 +242,10 @@ The abstract `RelationList` class and its implementations `ManyManyList` and `Ha
|
||||
are replacing the `ComponentSet` API, which is only relevant if you have instanciated these manually.
|
||||
Relations are retrieved through the same way (e.g. `$myMember->Groups()`).
|
||||
|
||||
### Aggregate changes for partial caching in templates ###
|
||||
|
||||
`DataObject::Aggregate()` and `DataObject::RelationshipAggregate()` are now deprecated. To replace your deprecated aggregate calls
|
||||
in PHP code, you should query with something like `Member::get()->max('LastEdited')`, that is, calling the aggregate on the `DataList` directly.
|
||||
The same concept applies for replacing `RelationshipAggregate()`, just call the aggregate method on the relationship instead,
|
||||
so something like `Member::get()->Groups()->max('LastEdited')`.
|
||||
|
||||
For partial caching in templates, the syntax `<% cached Aggregate(Page).Max(LastEdited) %>` has been deprecated. The new syntax is similar,
|
||||
except you use `List()` instead of `Aggregate()`, and the aggregate call `Max()` is now lowercase, as in `max()`.
|
||||
An example of the new syntax is `<% cached List(Page).max(LastEdited) %>`. Check `DataList` class for more aggregate methods to use.
|
||||
|
||||
### `SQLQuery` changes ###
|
||||
|
||||
`SQLQuery` has been changed so direct access to internal properties `$from`, `$select`, `$orderby` is
|
||||
now deprecated.
|
||||
|
||||
Instead, there are now methods you can call which allow you to get and set SQL clauses instead.
|
||||
now deprecated. Instead, there are now methods you can call which allow you to get and set SQL clauses instead.
|
||||
|
||||
* `$from` getter is `getFrom()` and setters `setFrom()` and `addFrom()`
|
||||
* `$select` getter is `getSelect()` and setters `setSelect()` and `addSelect()`
|
||||
@ -232,23 +257,19 @@ Instead, there are now methods you can call which allow you to get and set SQL c
|
||||
* `$distinct` getter is `getDistinct()` and setter `setDistinct()`
|
||||
* `$delete` getter is `getDelete()` and setter `setDelete()`
|
||||
* `$connective` getter is `getConnective()` and settter `setConnective()`
|
||||
|
||||
* `innerJoin()` has been renamed to `addInnerJoin()`
|
||||
* `leftJoin()` has been renamed to `addLeftJoin()`
|
||||
|
||||
### TinyMCE upgraded to 3.5 ###
|
||||
### Aggregate changes for partial caching in templates ###
|
||||
|
||||
TinyMCE has been upgraded to version 3.5.
|
||||
`DataObject::Aggregate()` and `DataObject::RelationshipAggregate()` are now deprecated. To replace your deprecated aggregate calls
|
||||
in PHP code, you should query with something like `Member::get()->max('LastEdited')`, that is, calling the aggregate on the `DataList` directly.
|
||||
The same concept applies for replacing `RelationshipAggregate()`, just call the aggregate method on the relationship instead,
|
||||
so something like `Member::get()->Groups()->max('LastEdited')`.
|
||||
|
||||
This change should be transparent to most people upgrading, but if you're using custom plugins for TinyMCE,
|
||||
please ensure they are still working correctly with the new version.
|
||||
|
||||
If you're upgrading from an SS 3.0 beta, TinyMCE HTML source editor and other popups might be blank.
|
||||
This is caused by the TinyMCE compressor leaving stale cache files in the system temp folder from an earlier
|
||||
version.
|
||||
|
||||
To resolve this problem, simply delete the `{hash}.gz` files within your temp location (defined by `sys_get_temp_dir()` in PHP.)
|
||||
These cache files will be regenerated next time the CMS is opened.
|
||||
For partial caching in templates, the syntax `<% cached Aggregate(Page).Max(LastEdited) %>` has been deprecated. The new syntax is similar,
|
||||
except you use `List()` instead of `Aggregate()`, and the aggregate call `Max()` is now lowercase, as in `max()`.
|
||||
An example of the new syntax is `<% cached List(Page).max(LastEdited) %>`. Check `DataList` class for more aggregate methods to use.
|
||||
|
||||
### InnoDB driver for existing and new tables on MySQL (instead of MyISAM) [innodb]###
|
||||
|
||||
@ -270,12 +291,9 @@ Note: MySQL has made InnoDB the default engine in its [5.5 release](http://dev.m
|
||||
|
||||
### Convert::json2array() changes [raw2json]###
|
||||
|
||||
Convert JSON functions have been changed to use built-in json PHP functions `json_decode()` and `json_encode()`
|
||||
|
||||
Convert JSON functions have been changed to use built-in json PHP functions `json_decode()` and `json_encode()`.
|
||||
Because `json_decode()` will convert nested JSON structures to arrays as well, this has changed the way it worked,
|
||||
as before nested structures would be converted to an object instead.
|
||||
|
||||
So, given the following JSON input to `Convert::json2array()`:
|
||||
as before nested structures would be converted to an object instead. So, given the following JSON input to `Convert::json2array()`:
|
||||
|
||||
{"Joe":"Bloggs","Tom":"Jones","My":{"Complicated":"Structure"}}
|
||||
|
||||
@ -299,47 +317,6 @@ Now in SilverStripe 3.x, nested structures are arrays:
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
### GridField: Replacement for TableListField and ComplexTableField [gridfield]###
|
||||
|
||||
We have a new component for managing lists of objects: The `[GridField](/topics/grid-field)`.
|
||||
It's a substantial rewrite of the features previously captured by `TableListField`,
|
||||
`ComplexTableField`, `HasManyComplexTableField` and `ManyManyComplexTableField`.
|
||||
|
||||
The legacy fields remain operational for now, although a switch to `GridField` is strongly encouraged,
|
||||
for stability, interface and performance reasons. The `HasManyComplexTableField` and `ManyManyComplexTableField`
|
||||
are no longer maintained, for those you do have to make the switch.
|
||||
The `TableField` class will be deprecated soon, but we don't have an adequate replacement for it yet.
|
||||
|
||||
Upgrade example: Record listing
|
||||
|
||||
:::php
|
||||
// before
|
||||
$field = new TableListField('Companies', 'Company');
|
||||
$field->setPageSize(20);
|
||||
// after
|
||||
$field = new GridField('Companies', null, Company::get());
|
||||
$field->getConfig()->getComponentByType('GridFieldPaginator')->setItemsPerPage(20);
|
||||
|
||||
Upgrade example: Record listing with view/edit interface
|
||||
|
||||
:::php
|
||||
// before
|
||||
$field = new ComplexTableField($myController, 'Companies', 'Company');
|
||||
// after
|
||||
$field = new GridField('Companies', null, Company::get(), GridFieldConfig_RecordEditor::create());
|
||||
|
||||
|
||||
Upgrade example: Relationship editing
|
||||
|
||||
:::php
|
||||
// before
|
||||
$field = new HasManyComplexTableField($myController, 'MyRelation', 'MyRelationObject');
|
||||
// after
|
||||
$field = new GridField('MyRelation', null, $myRecord->MyRelation(), GridFieldConfig_RelationEditor::create());
|
||||
|
||||
More information is available in the [GridField documentation](/topics/grid-field).
|
||||
|
||||
### New template engine [templates]###
|
||||
|
||||
The template engine has been completely rewritten, and although it is generally backward compatible, there are new features
|
||||
@ -373,6 +350,18 @@ The page tree moved from a bespoke tree library to [JSTree](http://jstree.com),
|
||||
which required changes to markup of the tree and its JavaScript architecture.
|
||||
This includes changes to `TreeDropdownField` and `TreeMultiSelectField`.
|
||||
|
||||
### TinyMCE upgraded to 3.5 ###
|
||||
|
||||
TinyMCE has been upgraded to version 3.5.
|
||||
|
||||
This change should be transparent to most people upgrading, but if you're using custom plugins for TinyMCE,
|
||||
please ensure they are still working correctly with the new version.
|
||||
|
||||
If you're upgrading from an SS 3.0 beta, TinyMCE HTML source editor and other popups might be blank.
|
||||
This is caused by the TinyMCE compressor leaving stale cache files in the system temp folder from an earlier
|
||||
version. To resolve this problem, simply delete the `{hash}.gz` files within your temp location (defined by `sys_get_temp_dir()` in PHP.)
|
||||
These cache files will be regenerated next time the CMS is opened.
|
||||
|
||||
### Settings-related fields move from SiteTree->getCMSFields() to new SiteTree->getSettingsFields() [getcmsfields]###
|
||||
|
||||
The fields and tabs are now split into two separate forms, which required a structural
|
||||
@ -491,10 +480,9 @@ Please use the appropriate setters on the form field instance instead.
|
||||
### EmailField now uses type "email" instead of type "text" {#email-form-field}
|
||||
|
||||
EmailField now uses "email" for the `type` attribute, which integrates better with HTML5 features like
|
||||
form validation in the browser.
|
||||
|
||||
If you want to change this back to "text", use `setAttribute()` when constructing the field:
|
||||
form validation in the browser. If you want to change this back to "text", use `setAttribute()` when constructing the field:
|
||||
|
||||
:::php
|
||||
$field = new EmailField('Email');
|
||||
$field->setAttribute('type', 'text');
|
||||
|
||||
@ -502,7 +490,6 @@ If you want to change this back to "text", use `setAttribute()` when constructin
|
||||
|
||||
In order to make the SilverStripe framework useable without the `cms` module,
|
||||
we've moved some files around.
|
||||
|
||||
CMS base functionality which is not directly related to content pages (`SiteTree`)
|
||||
has been moved from the `cms` module into a new "sub-module" located in `framework/admin`.
|
||||
This includes generic management interfaces like "Files & Images" (`AssetAdmin`),
|
||||
|
Loading…
Reference in New Issue
Block a user