##### General Information

- Overview
- Features
- Specification
- Getting Started
- Howto Build Turbine
- Changes

##### Documentation

- Services
- Howtos
  - Action Events Howto
  - Annotations Howto
  - Configuration Howto
  - Extend User Howto
  - Hibernate OM Howto
  - Intake Howto
  - JSP Howto
  - Migrating from 2.1 to 2.2
  - Migrating from 2.2 to 2.3
  - Migrating from 2.3 to 4.0
  - Pull Model Howto
  - Python Howto
  - Security Howto
  - Services Howto
  - URL rewriting Howto
  - Velocity Context Howto
  - Velocity Site Howto
  - VelocityOnlyLayout Howto
- Wiki
- JavaDocs

##### Development

- Proposals
- How To Help
- Todo

##### Project Documentation

- Project Information
- Project Reports

##### Apache

- Apache Website
- License
- How the ASF works
- Sponsorship
- Thanks
- Security

## Introduction

This document describes the basic steps needed to migrate an application written for Turbine 2.2 to Turbine 2.3.

You may find that migrating to 2.3 is not all that difficult - it should certainly be less trouble than migrating from 2.1 to 2.2. Most of the pain in figuring out this migration process has been documented in the mailing list archives, but is summarized here for your convenience.

## Deprecated And Removed Services

In 2.3, many services have been deprecated or removed wholly. Below are the changes I made to get my 2.2 app to work under 2.3.

Remove from tr.props ( and any properties that start with services.XXX):

     services.PoolBrokerService.classname=org.apache.turbine.services.db.TurbinePoolBrokerService
     services.MapBrokerService.classname=org.apache.turbine.services.db.TurbineMapBrokerService
     services.ResourceService.classname=org.apache.turbine.services.resources.TurbineResourceService
     services.LoggingService.classname=org.apache.turbine.services.logging.TurbineLoggingService

Note: Removing LoggingService removes all logging stuff from TurbineResources.properties as well! Now you use a Log4j.properties: WEB-INF\conf\Log4j.properties. You need at least an empty file, otherwise log4j complains, but something like this will be better:

    # -------------------------------------------------------------------
    # Log4j.properties
    # -------------------------------------------------------------------

    # This first category is required and the category
    # must be named 'default'. This is used for all logging
    # where an explicit category is not specified.

    log4j.category.default = INFO, default
    log4j.category.org.apache.turbine.services.pull.util.UIManager = DEBUG, default

    log4j.appender.default = org.apache.log4j.RollingFileAppender
    log4j.appender.default.file = logs/turbine.log
    log4j.appender.default.MaxFileSize = 1024KB
    log4j.appender.default.MaxBackupIndex = 5
    log4j.appender.default.append = true
    log4j.appender.default.layout = org.apache.log4j.PatternLayout
    log4j.appender.default.layout.conversionPattern = %d %-5p [%-10t] %c{2} - %m%n

    log4j.appender.email = org.apache.log4j.net.SMTPAppender
    log4j.appender.email.BufferSize = 512
    log4j.appender.email.From = @your-from-address@
    log4j.appender.email.SMTPHost = @your-mail-host@
    log4j.appender.email.Subject = Turbine Error Report
    log4j.appender.email.To = @your-to-address@
    log4j.appender.email.layout = org.apache.log4j.PatternLayout
    log4j.appender.email.layout.conversionPattern = %d %-5p [%-10t] %c{2} - %m%n

    # This category is used in the BasePeer class. All
    # SQL generated will be logged if the category
    # priority is set to DEBUG

    log4j.category.org.apache.torque.util.BasePeer = DEBUG, org.apache.torque.util.BasePeer
    log4j.additivity.org.apache.torque.util.BasePeer = false
    log4j.appender.org.apache.torque.util.BasePeer = org.apache.log4j.RollingFileAppender
    log4j.appender.org.apache.torque.util.BasePeer.file = logs/sql.log
    log4j.appender.org.apache.torque.util.BasePeer.MaxFileSize = 1024KB
    log4j.appender.org.apache.torque.util.BasePeer.MaxBackupIndex = 3
    log4j.appender.org.apache.torque.util.BasePeer.append = true
    log4j.appender.org.apache.torque.util.BasePeer.layout = org.apache.log4j.PatternLayout
    log4j.appender.org.apache.torque.util.BasePeer.layout.conversionPattern = %d %-5p [%-10t] %c{1} - %m%n

    log4j.category.@your-package@.modules.scheduledjobs = DEBUG, scheduledjobs, email
    log4j.additivity.@your-package@.modules.scheduledjobs = false
    log4j.appender.scheduledjobs = org.apache.log4j.RollingFileAppender
    log4j.appender.scheduledjobs.file = logs/batch.log
    log4j.appender.scheduledjobs.MaxFileSize = 256KB
    log4j.appender.scheduledjobs.MaxBackupIndex = 5
    log4j.appender.scheduledjobs.append = true
    log4j.appender.scheduledjobs.layout = org.apache.log4j.PatternLayout
    log4j.appender.scheduledjobs.layout.conversionPattern = %d %-5p [%-10t] %c{1} - %m%n

## Commons-logging Replaces Built-in Logging

In 2.3, the built in logging has been deprecated in favor of using commons-logging. Therefore, where ever you have this import:

    import org.apache.turbine.util.Log;

you will need to remove it and replace it with:

    import org.apache.commons.logging.Log;
    import org.apache.commons.logging.LogFactory;

Also, instead of calling static methods of the old Log object: Log.debug("my message") you will need instead to do this:

     private static Log log = LogFactory.getLog(Audit.class);
     .
     .
     .
     log.debug("My message");

The advantage of this is that now in your logging messages, you will know what class the message is coming from, versus the old way where all you got was the message and you would have to embed the name of the action to know what was emitting the logging message! Also, this makes your underlying logging architecture pluggable. If you use jdk1.4, you can plug in the java logging, or use log4j. See the example Log4j.properties file above to see a few of the possibilities.

## Use VelocityOnly Layout

Change from VelocityECSLayout to VelocityOnly Layout - see: VelocityOnlyLayout Howto.

## New Dependencies

In order to make the Turbine jar smaller, some things have been moved to commons. There are in fact a raft of new dependencies that you should ensure you use as part of your application - see: Dependencies.

## earlyInit Parameter For Selected Services

In order to get some services to work under 2.3, it is necessary to set an earlyInit parameter in TurbineResources.propertiess:

    services.PullService.earlyInit=true
    services.SessionService.earlyInit=true

If your service is not being initialized as you would expect then try setting this flag for it.

## New Optional URI Handling Tools

Under 2.3 there are new URI handling tools with a significant refactoring of how relative and absolute URL's are handled in Turbine. Briefly, the new tools avoid the confusion that arose previoulsy from mixing tools with internal classes, providing uniform access to the various URI types in Turbine. These new tools are backwards-compatible with your old $link and $content tools, so you should not have to change any of your templates if you decide to use the new tools.

To use the new tools, simply redefine the following pull tools in your TurbineResources.properties:

    tool.request.link    = org.apache.turbine.services.pull.tools.TemplateLink
    tool.request.content = org.apache.turbine.services.pull.tools.ContentTool

If you used some of the other tools for creating URL's, then there are analogous new ones as well:

    org.apache.turbine.services.pull.tools.RelativeTemplateLink
    org.apache.turbine.services.pull.tools.TemplateLinkWithSlash

## Ensure you refer to your templates correctly

Places where you might previously have got away with using forward slashes ("/") in your references to template names will need to be corrected (note that this does not apply to the Velocity #parse() and #include() statements which operate at a lower level). See: Template Service.

## Update to the latest DTDs for Intake and Torque

Updating your Intake configuration xml file and your Torque schema files to use the most recent DTDs will ensure that the DTDResolver can be used when validating these files. Deprecation warnings may be produced while these files are being processed - as with your application code you should aim to update these files so that no deprecation warnings are produced before the next Turbine release.

## Extending Turbine User

Refer to Torque Security Service for information on extending TurbineUser in Turbine 2.3 - this is now much easier than it was in previous releases. You may also want to refer to this message from the mail archive - the quoted text from Henning is great and Wei points to a couple of additional messages that may also prove useful.

In the past you may have used a customised MapBuilder (database.maps.builder in TurbineResources.properties) as part of extending your user object - this is no longer required if you use the Torque Security Service. In addidion to this you need to ensure that you replace any references you may have made to the old security related peer classes in any Criteria with the new classes that Torque generates for you as referring to the old ones will result in an inconsistent database map such that your extended user attributes may not consistently be maintained.

## Building Torque OM Classes

You will need to use Maven b9 or above in order to build the Torque Security Service and even then you should install the latest available release of the Torque generator plugin.

## Updates to this document

This document is by no means complete or totally accurate. We welcome suggestions as to how it might be improved, particularly if you have just completed migrating an application by following this howto.