/*
* This program is free software; you can redistribute it and/or modify it under the
* terms of the GNU General Public License, version 2 as published by the Free Software
* Foundation.
*
* You should have received a copy of the GNU General Public License along with this
* program; if not, you can obtain a copy at http://www.gnu.org/licenses/gpl-2.0.html
* or from the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU General Public License for more details.
*
*
* Copyright 2006 - 2013 Pentaho Corporation. All rights reserved.
*/
package org.pentaho.platform.engine.core.solution;
import org.apache.commons.lang.StringUtils;
import org.pentaho.platform.api.repository2.unified.RepositoryFile;
import org.pentaho.platform.api.util.PentahoCheckedChainedException;
public class ActionInfo {
/**
* TODO the method PentahoSystem.parseActionString() should be converted into a ctor for this class, and then
* removed. Callers should be adjusted. ActionResource.getLocationInSolution should be refactored into a method
* in this class, and callers adjusted. In general, the solutionName, path and actionName should likely be
* abstracted into an opaque class that can be passed around, instead of passing around 3 strings, and manually
* combining and parsing them in many places.
*
* @author Steven Barkdull
*
*/
private String solutionName;
private String path;
private String actionName;
public ActionInfo( final String solutionName, final String path, final String actionName ) {
this.solutionName = solutionName;
this.path = path;
this.actionName = actionName;
}
public String getActionName() {
return actionName;
}
public String getPath() {
return path;
}
public String getSolutionName() {
return solutionName;
}
public static ActionInfo parseActionString( final String actionString ) {
return ActionInfo.parseActionString( actionString, true );
}
// TODO sbarkdull, instead of returning null on parse error, should throw ActionInfoParseException
/**
* Break an action string into it's 3 components: the solution Id, the path to action file, and the action name
*
* @param actionString
* @return
*/
public static ActionInfo parseActionString( String actionString, boolean mustBeComplete ) {
// parse a string in this format samples/reporting/JFR/report.xml into
// the solution, path, and document name
if ( StringUtils.isEmpty( actionString ) ) {
return null;
}
// first normalize the path separators
actionString = actionString.replace( '\\', RepositoryFile.SEPARATOR.charAt( 0 ) );
// remove a leading '/'
if ( actionString.charAt( 0 ) == RepositoryFile.SEPARATOR.charAt( 0 ) ) {
actionString = actionString.substring( 1 );
}
String solution;
String path = ""; //$NON-NLS-1$
String name;
int idx1 = actionString.indexOf( RepositoryFile.SEPARATOR.charAt( 0 ) );
int idx2 = actionString.lastIndexOf( RepositoryFile.SEPARATOR.charAt( 0 ) );
if ( idx1 == -1 ) {
if ( mustBeComplete ) {
// this is not a valid action String
return null;
} else {
return new ActionInfo( actionString, null, null );
}
}
solution = actionString.substring( 0, idx1 );
name = actionString.substring( idx2 + 1 );
if ( idx2 > idx1 ) {
path = actionString.substring( idx1 + 1, idx2 );
}
// see if the name has an extension
if ( !mustBeComplete && ( name.indexOf( '.' ) == -1 ) ) {
// not really a filename
if ( StringUtils.isEmpty( path ) ) {
path = name;
} else {
path = path + RepositoryFile.SEPARATOR + name;
}
name = null;
}
return new ActionInfo( solution, path, name );
}
public String toString() {
return ActionInfo.buildSolutionPath( this.solutionName, this.path, this.actionName );
}
public static String buildSolutionPath( final String solution, String path, String filename ) {
StringBuffer buf = new StringBuffer();
// if the solutionName is the same as the fileName and the path is empty, then we are
// probably trying to load the solution root itself
if ( solution != null && solution.equals( filename ) && "".equals( path ) ) { //$NON-NLS-1$
filename = ""; //$NON-NLS-1$
}
if ( path != null && path.equalsIgnoreCase( "/" ) ) { //$NON-NLS-1$
path = ""; //$NON-NLS-1$
}
if ( StringUtils.isEmpty( path ) ) {
if ( !StringUtils.isEmpty( filename ) && filename.charAt( 0 ) == RepositoryFile.SEPARATOR.charAt( 0 ) ) {
return buf.append( solution ).append( filename ).toString();
} else {
return buf.append( solution ).append( RepositoryFile.SEPARATOR.charAt( 0 ) ).append( filename ).toString();
}
} else if ( path.charAt( 0 ) == RepositoryFile.SEPARATOR.charAt( 0 ) ) {
if ( !StringUtils.isEmpty( filename ) && filename.charAt( 0 ) == RepositoryFile.SEPARATOR.charAt( 0 ) ) {
return buf.append( solution ).append( path ).append( filename ).toString();
} else {
return buf.append( solution ).append( path ).append( RepositoryFile.SEPARATOR.charAt( 0 ) ).append( filename )
.toString();
}
} else {
if ( !StringUtils.isEmpty( filename ) && filename.charAt( 0 ) == RepositoryFile.SEPARATOR.charAt( 0 ) ) {
return buf.append( solution ).append( RepositoryFile.SEPARATOR.charAt( 0 ) ).append( path ).append( filename )
.toString();
} else {
return buf.append( solution ).append( RepositoryFile.SEPARATOR.charAt( 0 ) ).append( path ).append(
RepositoryFile.SEPARATOR.charAt( 0 ) ).append( filename ).toString();
}
}
}
public static class ActionInfoParseException extends PentahoCheckedChainedException {
private static final long serialVersionUID = 420;
public ActionInfoParseException( final String message, final Throwable reas ) {
super( message, reas );
}
public ActionInfoParseException( final String message ) {
super( message );
}
public ActionInfoParseException( final Throwable reas ) {
super( reas );
}
public ActionInfoParseException() {
super();
}
}
}