export cleanups and mobile style
This commit is contained in:
parent
93819cda0c
commit
1f3ab6a419
20 changed files with 518 additions and 318 deletions
|
|
@ -1,4 +1,9 @@
|
|||
7.7.6
|
||||
- Added mobile style template. If enabled in settings, will serve alternate style templates
|
||||
and page layout templates to matching user agents. Also adds the 'mobileExportPath' config
|
||||
variable where the mobile version of the site will be exported in addition to the normal
|
||||
export process.
|
||||
- Clean up the Asset export API to allow for easier re-use.
|
||||
- New features in the UKplayer slidehow: you can hide the textblock, volume
|
||||
slider and mute button, resize the textblock and thumbnails. A new demo
|
||||
config is added. See: /extras/ukplayer/slideshow.html (Rogier Voogt, Arjan
|
||||
|
|
|
|||
|
|
@ -14,6 +14,8 @@ save you many hours of grief.
|
|||
|
||||
* WebGUI now requires Crypt::SSLeay 0.57 or greater.
|
||||
|
||||
* WebGUI now requires Scope::Guard 0.03 or greater.
|
||||
|
||||
7.7.5
|
||||
--------------------------------------------------------------------
|
||||
* Due to a long standing bug in the Profile system, if the type of a
|
||||
|
|
|
|||
|
|
@ -32,6 +32,7 @@ my $session = start();
|
|||
|
||||
# upgrade functions go here
|
||||
addTemplateAttachmentsTable($session);
|
||||
addMobileStyleTemplate( $session );
|
||||
revertUsePacked( $session );
|
||||
fixDefaultPostReceived($session);
|
||||
addEuVatDbColumns( $session );
|
||||
|
|
@ -71,6 +72,50 @@ sub sendWebguiStats {
|
|||
print "DONE!\n" unless $quiet;
|
||||
}
|
||||
|
||||
#----------------------------------------------------------------------------
|
||||
sub addMobileStyleTemplate {
|
||||
my $session = shift;
|
||||
print "\tAdding mobile style template field... " unless $quiet;
|
||||
$session->db->write(q{
|
||||
ALTER TABLE wobject ADD COLUMN mobileStyleTemplateId CHAR(22) BINARY DEFAULT 'PBtmpl0000000000000060'
|
||||
});
|
||||
$session->db->write(q{
|
||||
UPDATE wobject SET mobileStyleTemplateId = styleTemplateId
|
||||
});
|
||||
$session->db->write(q{
|
||||
ALTER TABLE Layout ADD COLUMN mobileTemplateId CHAR(22) BINARY DEFAULT 'PBtmpl0000000000000054'
|
||||
});
|
||||
$session->setting->add('useMobileStyle', 0);
|
||||
$session->config->set('mobileUserAgents', [
|
||||
'AvantGo',
|
||||
'DoCoMo',
|
||||
'Vodafone',
|
||||
'EudoraWeb',
|
||||
'Minimo',
|
||||
'UP\.Browser',
|
||||
'PLink',
|
||||
'Plucker',
|
||||
'NetFront',
|
||||
'^WM5 PIE$',
|
||||
'Xiino',
|
||||
'iPhone',
|
||||
'Opera Mobi',
|
||||
'BlackBerry',
|
||||
'Opera Mini',
|
||||
'HP iPAQ',
|
||||
'IEMobile',
|
||||
'Profile/MIDP',
|
||||
'Smartphone',
|
||||
'Symbian ?OS',
|
||||
'J2ME/MIDP',
|
||||
'PalmSource',
|
||||
'PalmOS',
|
||||
'Windows CE',
|
||||
'Opera Mini',
|
||||
]);
|
||||
print "Done.\n" unless $quiet;
|
||||
}
|
||||
|
||||
#----------------------------------------------------------------------------
|
||||
sub addListingsCacheTimeoutToMatrix{
|
||||
my $session = shift;
|
||||
|
|
@ -80,21 +125,22 @@ sub addListingsCacheTimeoutToMatrix{
|
|||
}
|
||||
|
||||
#----------------------------------------------------------------------------
|
||||
|
||||
sub addTemplateAttachmentsTable {
|
||||
my $session = shift;
|
||||
print "\tAdding template attachments table... " unless $quiet;
|
||||
my $create = q{
|
||||
create table template_attachments (
|
||||
templateId varchar(22),
|
||||
CREATE TABLE template_attachments (
|
||||
templateId CHAR(22) BINARY,
|
||||
revisionDate bigint(20),
|
||||
url varchar(256),
|
||||
type varchar(20),
|
||||
sequence int(11),
|
||||
|
||||
primary key (templateId, revisionDate, url)
|
||||
PRIMARY KEY (templateId, revisionDate, url)
|
||||
)
|
||||
};
|
||||
$session->db->write($create);
|
||||
print "Done.\n" unless $quiet;
|
||||
}
|
||||
|
||||
#----------------------------------------------------------------------------
|
||||
|
|
@ -116,6 +162,7 @@ sub revertUsePacked {
|
|||
# Describe what our function does
|
||||
sub fixDefaultPostReceived {
|
||||
my $session = shift;
|
||||
print "\tFixing post received template setting... " unless $quiet;
|
||||
$session->db->write(<<EOSQL);
|
||||
UPDATE Collaboration SET postReceivedTemplateId='default_post_received1' WHERE postReceivedTemplateId='default-post-received'
|
||||
EOSQL
|
||||
|
|
|
|||
|
|
@ -2469,7 +2469,7 @@ ENDJS
|
|||
|
||||
### Show the processed template
|
||||
$session->http->sendHeader;
|
||||
my $style = $session->style->process($self->getSeparator,$self->getParent->get("styleTemplateId"));
|
||||
my $style = $self->getParent->processStyle($self->getSeparator);
|
||||
my ($head, $foot) = split($self->getSeparator,$style);
|
||||
$self->session->output->print($head, 1);
|
||||
$self->session->output->print($self->processTemplate($var, undef, $template));
|
||||
|
|
|
|||
|
|
@ -99,7 +99,16 @@ sub definition {
|
|||
hoverHelp=>$i18n->get('1079 description'),
|
||||
filter=>'fixId',
|
||||
namespace=>'style'
|
||||
}
|
||||
},
|
||||
mobileStyleTemplateId => {
|
||||
fieldType => ( $session->setting->get('useMobileStyle') ? 'template' : 'hidden' ),
|
||||
defaultValue => 'PBtmpl0000000000000060',
|
||||
tab => 'display',
|
||||
label => $i18n->get('mobileStyleTemplateId label'),
|
||||
hoverHelp => $i18n->get('mobileStyleTemplateId description'),
|
||||
filter => 'fixId',
|
||||
namespace => 'style',
|
||||
},
|
||||
);
|
||||
push(@{$definition}, {
|
||||
tableName=>'wobject',
|
||||
|
|
@ -390,7 +399,10 @@ sub processStyle {
|
|||
content => $self->get('synopsis'),
|
||||
});
|
||||
}
|
||||
return $style->process($output,$self->get("styleTemplateId"));
|
||||
if ($style->useMobileStyle) {
|
||||
return $style->process($output,$self->get("mobileStyleTemplateId"));
|
||||
}
|
||||
return $style->process($output,$self->get("styleTemplateId"));
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -72,6 +72,11 @@ sub definition {
|
|||
namespace => "Layout",
|
||||
defaultValue =>'PBtmpl0000000000000054',
|
||||
},
|
||||
mobileTemplateId => {
|
||||
fieldType => ( $session->style->useMobileStyle ? 'template' : 'hidden' ),
|
||||
namespace => 'Layout',
|
||||
defaultValue => 'PBtmpl0000000000000054',
|
||||
},
|
||||
contentPositions => {
|
||||
noFormPost =>1,
|
||||
defaultValue =>undef,
|
||||
|
|
@ -117,6 +122,22 @@ sub getEditForm {
|
|||
-namespace=>"Layout"
|
||||
);
|
||||
|
||||
if ( $self->session->setting->get('useMobileStyle') ) {
|
||||
$tabform->getTab("display")->template(
|
||||
name => 'mobileTemplateId',
|
||||
value => $self->getValue('mobileTemplateId'),
|
||||
label => $i18n->get('mobileTemplateId label'),
|
||||
hoverHelp => $i18n->get('mobileTemplateId description'),
|
||||
namespace => 'Layout',
|
||||
);
|
||||
}
|
||||
else {
|
||||
$tabform->getTab("display")->hidden(
|
||||
name => 'mobileTemplateId',
|
||||
value => $self->getValue('mobileTemplateId'),
|
||||
);
|
||||
}
|
||||
|
||||
tie my %assetOrder, "Tie::IxHash";
|
||||
%assetOrder = (
|
||||
"asc" =>$i18n->get("asset order asc"),
|
||||
|
|
@ -163,7 +184,16 @@ sub prepareView {
|
|||
my $self = shift;
|
||||
$self->SUPER::prepareView;
|
||||
my $session = $self->session;
|
||||
my $template = WebGUI::Asset->new($session,$self->get("templateId"),"WebGUI::Asset::Template");
|
||||
my $templateId;
|
||||
|
||||
if ($session->style->useMobileStyle) {
|
||||
$templateId = $self->get('templateId');
|
||||
}
|
||||
else {
|
||||
$templateId = $self->get('mobileTemplateId');
|
||||
}
|
||||
|
||||
my $template = WebGUI::Asset->new($session,$templateId,"WebGUI::Asset::Template");
|
||||
$template->prepare( $self->getMetaDataAsTemplateVariables );
|
||||
$self->{_viewTemplate} = $template;
|
||||
|
||||
|
|
@ -325,30 +355,34 @@ sub getContentLastModified {
|
|||
#-------------------------------------------------------------------
|
||||
sub www_view {
|
||||
my $self = shift;
|
||||
my $session = $self->session;
|
||||
# slashdot / burst protection hack
|
||||
if ($self->session->var->get("userId") eq "1" && $self->session->form->param() == 0) {
|
||||
if ($session->var->get("userId") eq "1"
|
||||
&& $session->form->param() == 0
|
||||
&& !$session->scratch->get('isExporting')
|
||||
) {
|
||||
my $check = $self->checkView;
|
||||
return $check if (defined $check);
|
||||
my $cache = WebGUI::Cache->new($self->session, "view_".$self->getId);
|
||||
my $cache = WebGUI::Cache->new($session, "view_".$self->getId);
|
||||
my $out = $cache->get if defined $cache;
|
||||
unless ($out) {
|
||||
$self->prepareView;
|
||||
$self->session->stow->set("cacheFixOverride", 1);
|
||||
$session->stow->set("cacheFixOverride", 1);
|
||||
$out = $self->processStyle($self->view);
|
||||
$cache->set($out, 60);
|
||||
$self->session->stow->delete("cacheFixOverride");
|
||||
$session->stow->delete("cacheFixOverride");
|
||||
}
|
||||
# keep those ads rotating
|
||||
while ($out =~ /(\[AD\:([^\]]+)\])/gs) {
|
||||
my $code = $1;
|
||||
my $adSpace = WebGUI::AdSpace->newByName($self->session, $2);
|
||||
my $adSpace = WebGUI::AdSpace->newByName($session, $2);
|
||||
my $ad = $adSpace->displayImpression if (defined $adSpace);
|
||||
$out =~ s/\Q$code/$ad/ges;
|
||||
}
|
||||
$self->session->http->setLastModified($self->getContentLastModified);
|
||||
$self->session->http->sendHeader;
|
||||
$self->session->output->print($out, 1);
|
||||
return "chunked";
|
||||
$session->http->setLastModified($self->getContentLastModified);
|
||||
$session->http->sendHeader;
|
||||
$session->output->print($out, 1);
|
||||
return "chunked";
|
||||
}
|
||||
$self->{_viewPrintOverride} = 1; # we do this to make it output each asset as it goes, rather than waiting until the end
|
||||
return $self->SUPER::www_view;
|
||||
|
|
|
|||
|
|
@ -2011,7 +2011,7 @@ sub www_viewProject {
|
|||
$var->{'task.back.label'} = $i18n->get("task back label");
|
||||
$var->{'task.back.url'} = $self->getUrl;
|
||||
|
||||
return $style->process($self->processTemplate($var,$self->getValue("projectDisplayTemplateId")),$self->getValue("styleTemplateId"));
|
||||
return $style->processStyle($self->processTemplate($var,$self->getValue("projectDisplayTemplateId")));
|
||||
}
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -1408,7 +1408,7 @@ sub www_takeSurvey {
|
|||
my $self = shift;
|
||||
|
||||
my $out = $self->processTemplate( {}, $self->get('surveyTakeTemplateId') );
|
||||
return $self->session->style->process( $out, $self->get('styleTemplateId') );
|
||||
return $self->processStyle($out);
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
|
@ -2071,7 +2071,7 @@ sub www_viewGradeBook {
|
|||
$paginator->appendTemplateVars($var);
|
||||
|
||||
my $out = $self->processTemplate( $var, $self->get('gradebookTemplateId') );
|
||||
return $self->session->style->process( $out, $self->get('styleTemplateId') );
|
||||
return $self->processStyle($out);
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
|
@ -2161,7 +2161,7 @@ sub www_viewStatisticalOverview {
|
|||
$paginator->appendTemplateVars($var);
|
||||
|
||||
my $out = $self->processTemplate( $var, $self->get('overviewTemplateId') );
|
||||
return $self->session->style->process( $out, $self->get('styleTemplateId') );
|
||||
return $self->processStyle($out);
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
|
|
|||
|
|
@ -3468,8 +3468,9 @@ sub www_viewThingData {
|
|||
|
||||
$self->getViewThingVars($thingId,$thingDataId,$var);
|
||||
$self->appendThingsVars($var, $thingId);
|
||||
return $self->session->style->process($self->processTemplate($var,$thingProperties->{viewTemplateId}),$self->get("styleTemplateId"));
|
||||
|
||||
return $self->processStyle(
|
||||
$self->processTemplate($var,$thingProperties->{viewTemplateId})
|
||||
);
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
|
|
|||
|
|
@ -146,7 +146,6 @@ sub www_editBranch {
|
|||
-value=>$self->getValue("styleTemplateId"),
|
||||
-hoverHelp=>$i18n2->get('1073 description'),
|
||||
-namespace=>'style',
|
||||
-afterEdit=>'op=editPage;npp='.$self->session->form->process("npp"),
|
||||
-subtext=>'<br />'.$i18n->get("change").' '.WebGUI::Form::yesNo($self->session,{name=>"change_styleTemplateId"})
|
||||
);
|
||||
$tabform->getTab("display")->template(
|
||||
|
|
@ -155,9 +154,19 @@ sub www_editBranch {
|
|||
-hoverHelp=>$i18n2->get('1079 description'),
|
||||
-value=>$self->getValue("printableStyleTemplateId"),
|
||||
-namespace=>'style',
|
||||
-afterEdit=>'op=editPage;npp='.$self->session->form->process("npp"),
|
||||
-subtext=>'<br />'.$i18n->get("change").' '.WebGUI::Form::yesNo($self->session,{name=>"change_printableStyleTemplateId"})
|
||||
);
|
||||
if ( $self->session->setting->get('useMobileStyle') ) {
|
||||
$tabform->getTab("display")->template(
|
||||
name => 'mobileStyleTemplateId',
|
||||
label => $i18n2->get('mobileStyleTemplateId label'),
|
||||
hoverHelp => $i18n2->get('mobileStyleTemplateId description'),
|
||||
value => $self->getValue('mobileStyleTemplateId'),
|
||||
namespace => 'style',
|
||||
subtext => '<br />' . $i18n->get('change') . q{ }
|
||||
. WebGUI::Form::yesNo($self->session,{name=>"change_mobileStyleTemplateId"}),
|
||||
);
|
||||
}
|
||||
$tabform->addTab("security",$i18n->get(107),6);
|
||||
if ($self->session->config->get("sslEnabled")) {
|
||||
$tabform->getTab("security")->yesNo(
|
||||
|
|
@ -254,6 +263,8 @@ sub www_editBranchSave {
|
|||
if ($self->session->form->yesNo("change_styleTemplateId"));
|
||||
$wobjectData{printableStyleTemplateId} = $self->session->form->template("printableStyleTemplateId")
|
||||
if ($self->session->form->yesNo("change_printableStyleTemplateId"));
|
||||
$wobjectData{mobileStyleTemplateId} = $self->session->form->template("mobileStyleTemplateId")
|
||||
if ($self->session->form->yesNo("change_mobileStyleTemplateId"));
|
||||
my ($urlBaseBy, $urlBase, $endOfUrl);
|
||||
my $changeUrl = $self->session->form->yesNo("change_url");
|
||||
if ($changeUrl) {
|
||||
|
|
|
|||
|
|
@ -15,14 +15,15 @@ package WebGUI::Asset;
|
|||
=cut
|
||||
|
||||
use strict;
|
||||
use File::Basename ();
|
||||
use File::Path ();
|
||||
use Path::Class;
|
||||
use Scalar::Util 'looks_like_number';
|
||||
use Path::Class ();
|
||||
use Scalar::Util qw(looks_like_number);
|
||||
use WebGUI::International;
|
||||
use WebGUI::Exception;
|
||||
use WebGUI::Utility ();
|
||||
use WebGUI::Session;
|
||||
use URI::URL;
|
||||
use Scope::Guard;
|
||||
|
||||
=head1 NAME
|
||||
|
||||
|
|
@ -46,18 +47,19 @@ These methods are available from this class:
|
|||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
=head2 exportCheckPath ( session )
|
||||
=head2 exportCheckPath ( [session] )
|
||||
|
||||
Class method. Tries very hard to ensure that exportPath is defined in the
|
||||
Class or object method. Tries very hard to ensure that exportPath is defined in the
|
||||
configuration file, that it exists on the filesystem (creating any directories
|
||||
necessary), and that the OS user running WebGUI can write to it. Throws an
|
||||
appropriate exception on failure and returns a true value on success.
|
||||
appropriate exception on failure and returns a the export path as a L<Path::Class::Dir>
|
||||
object on success.
|
||||
|
||||
Takes the following parameters:
|
||||
|
||||
=head3 session
|
||||
|
||||
A reference to a L<WebGUI::Session> object.
|
||||
A reference to a L<WebGUI::Session> object. Should only be specified if called as a class method.
|
||||
|
||||
Throws the following exceptions:
|
||||
|
||||
|
|
@ -73,25 +75,31 @@ Encountered filesystem permission problems with the defined exportPath
|
|||
|
||||
sub exportCheckPath {
|
||||
my $class = shift;
|
||||
my $session = shift;
|
||||
|
||||
# make sure we were given the right parameters
|
||||
if(ref $session ne 'WebGUI::Session') {
|
||||
WebGUI::Error::InvalidObject->throw(error => "first param to exportCheckPath must be a WebGUI::Session");
|
||||
my $session;
|
||||
if (ref $class && $class->can('session')) {
|
||||
$session = $class->session;
|
||||
}
|
||||
|
||||
my $exportPath = $session->config->get('exportPath');
|
||||
else {
|
||||
$session = shift;
|
||||
# make sure we were given the right parameters
|
||||
if((!ref $session) || !$session->isa('WebGUI::Session')) {
|
||||
WebGUI::Error::InvalidObject->throw(error => "first param to exportCheckPath as a class method must be a WebGUI::Session");
|
||||
}
|
||||
}
|
||||
my $exportPath = $session->style->useMobileStyle ? $session->config->get('mobileExportPath')
|
||||
: $session->config->get('exportPath');
|
||||
|
||||
# first check that the path is defined in the config file and that it's not
|
||||
# an empty string
|
||||
if(!defined $exportPath || !$exportPath) {
|
||||
if (!defined $exportPath || !$exportPath) {
|
||||
WebGUI::Error::InvalidObject->throw(error => 'exportPath must be defined and not ""');
|
||||
}
|
||||
$exportPath = Path::Class::Dir->new($exportPath);
|
||||
|
||||
# now that we know that it's defined and not an empty string, test if it exists.
|
||||
if(!-e $exportPath) {
|
||||
if (!-e $exportPath) {
|
||||
# it doesn't exist; let's try making it
|
||||
eval { File::Path::mkpath( [$exportPath] ) };
|
||||
eval { $exportPath->mkpath };
|
||||
if($@) {
|
||||
WebGUI::Error->throw(error => "can't create exportPath $exportPath");
|
||||
}
|
||||
|
|
@ -99,11 +107,11 @@ sub exportCheckPath {
|
|||
# the path didn't exist, and we succeeded creating it. Therefore we
|
||||
# know we can write to it and that it's an actual directory. Nothing
|
||||
# more left to do. indicate success to our caller.
|
||||
return 1;
|
||||
return $exportPath;
|
||||
}
|
||||
|
||||
# the path exists. make sure it's actually a directory.
|
||||
if(!-d $exportPath) {
|
||||
if (!-d $exportPath) {
|
||||
WebGUI::Error->throw(error => "$exportPath isn't a directory");
|
||||
}
|
||||
|
||||
|
|
@ -113,12 +121,12 @@ sub exportCheckPath {
|
|||
# directories beneath it, and we need to be able to 'execute' the directory
|
||||
# to list files in it. and of course we need to be able to read it too.
|
||||
# check for all of these.
|
||||
if(! (-w $exportPath) || ! (-x _) || ! (-r _) ) {
|
||||
if (! (-w $exportPath && -x _ && -r _) ) {
|
||||
WebGUI::Error->throw(error => "can't access $exportPath");
|
||||
}
|
||||
|
||||
# everything checks out, return 1
|
||||
return 1;
|
||||
# everything checks out, return path
|
||||
return $exportPath;
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
|
@ -189,9 +197,8 @@ false will do nothing.
|
|||
|
||||
sub exportAsHtml {
|
||||
my $self = shift;
|
||||
my $args = shift;
|
||||
my $session = $self->session;
|
||||
# set a scratch variable for Assets to know we're exporting
|
||||
my ($returnCode, $message);
|
||||
|
||||
# get the i18n object
|
||||
my $i18n = WebGUI::International->new($self->session, 'Asset');
|
||||
|
|
@ -199,23 +206,10 @@ sub exportAsHtml {
|
|||
# take down when we started to tell the user how long the process took.
|
||||
my $startTime = $session->datetime->time;
|
||||
|
||||
# before even looking at the parameters, make sure the exportPath is valid.
|
||||
eval { WebGUI::Asset->exportCheckPath($session) };
|
||||
|
||||
# something went wrong. we don't really care what at this point. we did
|
||||
# everything we could to try to make exporting possible and we failed. give
|
||||
# up.
|
||||
if($@) {
|
||||
$returnCode = 0;
|
||||
$message = $@;
|
||||
return ($returnCode, $message);
|
||||
}
|
||||
|
||||
# if we're still here, then the exportPath is valid.
|
||||
my $exportPath = $session->config->get('exportPath');
|
||||
# get the export path and ensure it is valid.
|
||||
my $exportPath = $self->exportCheckPath;
|
||||
|
||||
# get parameters
|
||||
my $args = shift;
|
||||
my $quiet = $args->{quiet};
|
||||
my $userId = $args->{userId};
|
||||
my $depth = $args->{depth};
|
||||
|
|
@ -224,186 +218,180 @@ sub exportAsHtml {
|
|||
my $rootUrlAction = $args->{rootUrlAction};
|
||||
my $exportUrl = $args->{exportUrl};
|
||||
|
||||
# if we're doing symlinking of the root URL, then the current default asset
|
||||
# is the root of the tree. take down that asset ID so we can pass it to
|
||||
# exportSymlinkRoot later.
|
||||
my $defaultAssetId = $self->session->setting->get('defaultPage');
|
||||
my $defaultAsset = WebGUI::Asset->newByDynamicClass($session, $defaultAssetId);
|
||||
|
||||
my @extraUploadActions = qw/ symlink none /;
|
||||
my @rootUrlActions = qw/ symlink none /;
|
||||
|
||||
# verify them
|
||||
if(!defined $userId) {
|
||||
$returnCode = 0;
|
||||
$message = $i18n->get('need a userId parameter');
|
||||
return ($returnCode, $message);
|
||||
if (!defined $userId) {
|
||||
WebGUI::Error->throw(error => $i18n->get('need a userId parameter'));
|
||||
}
|
||||
|
||||
# we take either a numeric userId or a WebGUI::User object
|
||||
if( ref $userId ne 'WebGUI::User' && ! (looks_like_number($userId) || $session->id->valid($userId))) {
|
||||
$returnCode = 0;
|
||||
$message = "'$userId' ".$i18n->get('is not a valid userId');
|
||||
return ($returnCode, $message);
|
||||
my $user;
|
||||
if ( ref $userId && $userId->isa('WebGUI::User') ) {
|
||||
$user = $userId;
|
||||
}
|
||||
elsif ( looks_like_number($userId) || $session->id->valid($userId) ) {
|
||||
$user = WebGUI::User->new($session, $userId);
|
||||
}
|
||||
if (! defined $user) {
|
||||
WebGUI::Error->throw(error => "'$userId' ".$i18n->get('is not a valid userId'));
|
||||
}
|
||||
$userId = $user->userId;
|
||||
|
||||
# depth is required.
|
||||
if(!defined $depth) {
|
||||
$returnCode = 0;
|
||||
$message = $i18n->get('need a depth');
|
||||
return ($returnCode, $message);
|
||||
if(! defined $depth) {
|
||||
WebGUI::Error->throw(error => $i18n->get('need a depth'));
|
||||
}
|
||||
# and it must be a number.
|
||||
if( !looks_like_number($depth) ) {
|
||||
$returnCode = 0;
|
||||
$message = sprintf $i18n->get('%s is not a valid depth'), $depth;
|
||||
return ($returnCode, $message);
|
||||
WebGUI::Error->throw(error => sprintf $i18n->get('%s is not a valid depth'), $depth);
|
||||
}
|
||||
|
||||
# extrasUploadAction and rootUrlAction must have values matching something
|
||||
# in the arrays defined above
|
||||
if( defined $extrasUploadAction && !isIn($extrasUploadAction, @extraUploadActions) ) {
|
||||
$returnCode = 0;
|
||||
$message = "'$extrasUploadAction' is not a valid extrasUploadAction";
|
||||
return ($returnCode, $message);
|
||||
if( defined $extrasUploadAction && !WebGUI::Utility::isIn($extrasUploadAction, @extraUploadActions) ) {
|
||||
WebGUI::Error->throw(error => "'$extrasUploadAction' is not a valid extrasUploadAction");
|
||||
}
|
||||
|
||||
if( defined $rootUrlAction && !isIn($rootUrlAction, @rootUrlActions) ) {
|
||||
$returnCode = 0;
|
||||
$message = "'$rootUrlAction' is not a valid rootUrlAction";
|
||||
return ($returnCode, $message);
|
||||
if( defined $rootUrlAction && !WebGUI::Utility::isIn($rootUrlAction, @rootUrlActions) ) {
|
||||
WebGUI::Error->throw(error => "'$rootUrlAction' is not a valid rootUrlAction");
|
||||
}
|
||||
|
||||
# the export path is valid. the params are good. let's get started. first,
|
||||
# we need to get the assets that we'll be exporting. exportGetDescendants
|
||||
# takes a WebGUI::User object, so give it one.
|
||||
my $user;
|
||||
if(ref $userId ne 'WebGUI::User') {
|
||||
$user = WebGUI::User->new($session, $userId);
|
||||
}
|
||||
else {
|
||||
$user = $userId;
|
||||
}
|
||||
|
||||
my $assetIds = $self->exportGetDescendants($user, $depth);
|
||||
|
||||
# make sure this user can view the top level asset we're exporting. if not,
|
||||
# don't do anything.
|
||||
unless ( $self->canView($userId) ) {
|
||||
$returnCode = 0;
|
||||
$message = "can't view asset at URL " . $self->getUrl;
|
||||
return ($returnCode, $message);
|
||||
WebGUI::Error->throw(error => "can't view asset at URL " . $self->getUrl);
|
||||
}
|
||||
|
||||
# now, create a new session as the user doing the exports. this is so that
|
||||
# the exported assets are taken from that user's perspective.
|
||||
my $exportSession = WebGUI::Session->open(
|
||||
$session->config->getWebguiRoot,
|
||||
$session->config->getFilename,
|
||||
);
|
||||
my $esGuard = Scope::Guard->new(sub {
|
||||
$exportSession->var->end;
|
||||
$exportSession->close;
|
||||
});
|
||||
|
||||
$exportSession->user( { userId => $userId } );
|
||||
|
||||
# set a scratch variable for Assets and widgets to know we're exporting
|
||||
$exportSession->scratch->set('isExporting', 1);
|
||||
$exportSession->scratch->set('exportUrl', $exportUrl);
|
||||
$exportSession->style->setMobileStyle(0);
|
||||
|
||||
my $asset = WebGUI::Asset->new(
|
||||
$exportSession,
|
||||
$self->getId,
|
||||
$self->get('className'),
|
||||
$self->get('revisionDate'),
|
||||
);
|
||||
|
||||
# pass in reporting session unless we're in quiet mode
|
||||
my $exportedCount = $asset->exportBranch( $args, $quiet ? () : $session );
|
||||
|
||||
if ($session->config->get('mobileExportPath')) {
|
||||
$exportSession->style->setMobileStyle(1);
|
||||
|
||||
# pass in reporting session unless we're in quiet mode
|
||||
$exportedCount += $asset->exportBranch( $args, $quiet ? () : $session );
|
||||
}
|
||||
|
||||
# we're done. give the user a status report.
|
||||
my $timeRequired = $session->datetime->time - $startTime;
|
||||
my $message = sprintf $i18n->get('export information'), $exportedCount, $timeRequired;
|
||||
return $message;
|
||||
}
|
||||
|
||||
sub exportBranch {
|
||||
my $self = shift;
|
||||
my $options = shift;
|
||||
my $reportSession = shift;
|
||||
|
||||
my $depth = $options->{depth};
|
||||
my $indexFileName = $options->{indexFileName};
|
||||
my $extrasUploadAction = $options->{extrasUploadAction};
|
||||
my $rootUrlAction = $options->{rootUrlAction};
|
||||
|
||||
my $i18n;
|
||||
if ( $reportSession ) {
|
||||
$i18n = WebGUI::International->new($self->session, 'Asset');
|
||||
}
|
||||
|
||||
my $exportedCount = 0;
|
||||
my $assetIds = $self->exportGetDescendants(undef, $depth);
|
||||
foreach my $assetId ( @{$assetIds} ) {
|
||||
# now, create a new session as the user doing the exports. this is so that
|
||||
# the exported assets are taken from that user's perspective.
|
||||
# Must be created once for each asset, since session is supposed to only handle
|
||||
# one main asset
|
||||
my $exportSession = WebGUI::Session->open($self->session->config->getWebguiRoot, $self->session->config->getFilename);
|
||||
$exportSession->user( { userId => $userId } );
|
||||
my $outputSession = $self->session->duplicate;
|
||||
my $osGuard = Scope::Guard->new(sub {
|
||||
$outputSession->close;
|
||||
});
|
||||
|
||||
# set a scratch variable for Assets and widgets to know we're exporting
|
||||
$exportSession->scratch->set('isExporting', 1);
|
||||
$exportSession->scratch->set('exportUrl', $exportUrl);
|
||||
|
||||
my $asset = WebGUI::Asset->newByDynamicClass($exportSession, $assetId);
|
||||
my $fullPath = $asset->exportGetUrlAsPath;
|
||||
my $asset = WebGUI::Asset->new($outputSession, $assetId);
|
||||
my $fullPath = $asset->exportGetUrlAsPath;
|
||||
|
||||
# skip this asset if we can't view it as this user.
|
||||
unless( $asset->canView($userId) ) {
|
||||
if( !$quiet ) {
|
||||
unless( $asset->canView ) {
|
||||
if( $reportSession ) {
|
||||
my $message = sprintf( $i18n->get('bad user privileges') . "\n") . $asset->getUrl;
|
||||
$self->session->output->print($message);
|
||||
$reportSession->output->print($message);
|
||||
}
|
||||
$exportSession->var->end;
|
||||
$exportSession->close;
|
||||
next;
|
||||
}
|
||||
|
||||
# skip this asset if it's not exportable.
|
||||
unless ( $asset->exportCheckExportable ) {
|
||||
if( !$quiet ) {
|
||||
$self->session->output->print("$fullPath skipped, not exportable<br />");
|
||||
if ( $reportSession ) {
|
||||
$reportSession->output->print("$fullPath skipped, not exportable<br />");
|
||||
}
|
||||
$exportSession->var->end;
|
||||
$exportSession->close;
|
||||
next;
|
||||
}
|
||||
|
||||
# tell the user which asset we're exporting.
|
||||
unless ($quiet) {
|
||||
if ( $reportSession ) {
|
||||
my $message = sprintf $i18n->get('exporting page'), $fullPath;
|
||||
$self->session->output->print($message);
|
||||
$reportSession->output->print($message);
|
||||
}
|
||||
|
||||
# try to write the file
|
||||
eval { $asset->exportWriteFile };
|
||||
if($@) {
|
||||
$returnCode = 0;
|
||||
$message = $@;
|
||||
$self->session->output->print("could not export asset with URL " . $asset->getUrl . ": $@");
|
||||
$exportSession->var->end;
|
||||
$exportSession->close;
|
||||
return ($returnCode, $message);
|
||||
if( $@ ) {
|
||||
WebGUI::Error->throw(error => "could not export asset with URL " . $asset->getUrl . ": $@");
|
||||
}
|
||||
|
||||
# next, tell the asset that we're exporting, so that it can export any
|
||||
# of its collateral or other extra data.
|
||||
eval { $asset->exportAssetCollateral($asset->exportGetUrlAsPath, $args, $session) };
|
||||
eval { $asset->exportAssetCollateral($asset->exportGetUrlAsPath, $options, $reportSession) };
|
||||
if($@) {
|
||||
$returnCode = 0;
|
||||
$message = $@;
|
||||
$self->session->output->print("failed to export asset collateral for URL " . $asset->getUrl . ": $@");
|
||||
$exportSession->var->end;
|
||||
$exportSession->close;
|
||||
return ($returnCode, $message);
|
||||
WebGUI::Error->throw(error => "failed to export asset collateral for URL " . $asset->getUrl . ": $@");
|
||||
}
|
||||
|
||||
# we exported this one successfully, so count it
|
||||
$exportedCount++;
|
||||
|
||||
# track when this asset was last exported for external caching and the like
|
||||
$session->db->write( "UPDATE asset SET lastExportedAs = ? WHERE assetId = ?",
|
||||
$self->session->db->write( "UPDATE asset SET lastExportedAs = ? WHERE assetId = ?",
|
||||
[ $fullPath, $asset->getId ] );
|
||||
|
||||
$self->updateHistory("exported");
|
||||
|
||||
# tell the user we did this asset correctly
|
||||
unless( $quiet ) {
|
||||
$session->output->print($i18n->get('done'));
|
||||
if ( $reportSession ) {
|
||||
$reportSession->output->print($i18n->get('done'));
|
||||
}
|
||||
|
||||
$exportSession->var->end;
|
||||
$exportSession->close;
|
||||
}
|
||||
|
||||
|
||||
# handle symlinking
|
||||
if($extrasUploadAction eq 'symlink') {
|
||||
eval { WebGUI::Asset->exportSymlinkExtrasUploads($session) };
|
||||
if ($@) {
|
||||
$returnCode = 0;
|
||||
$message = $@;
|
||||
return ($returnCode, $message);
|
||||
}
|
||||
if ($extrasUploadAction eq 'symlink') {
|
||||
$self->exportSymlinkExtrasUploads;
|
||||
}
|
||||
|
||||
if($rootUrlAction eq 'symlink') {
|
||||
eval { WebGUI::Asset->exportSymlinkRoot($session, $defaultAsset, $indexFileName, $quiet) };
|
||||
if ($@) {
|
||||
$returnCode = 0;
|
||||
$message = $@;
|
||||
return ($returnCode, $message);
|
||||
}
|
||||
if ($rootUrlAction eq 'symlink') {
|
||||
my $defaultAsset = WebGUI::Asset->getDefault($self->session);
|
||||
$self->exportSymlinkRoot($defaultAsset, $indexFileName, $reportSession);
|
||||
}
|
||||
|
||||
# we're done. give the user a status report.
|
||||
$returnCode = 1;
|
||||
my $timeRequired = $session->datetime->time - $startTime;
|
||||
$message = sprintf $i18n->get('export information'), $exportedCount, $timeRequired;
|
||||
return ($returnCode, $message);
|
||||
return $exportedCount;
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
|
@ -472,9 +460,9 @@ sub exportCheckExportable {
|
|||
Gets the descendants of this asset for exporting, walking the lineage as the
|
||||
user specified. Takes the following parameters:
|
||||
|
||||
=head3 userId
|
||||
=head3 user
|
||||
|
||||
The WebGUI user ID as which to do the export.
|
||||
The WebGUI user object as which to do the export. If not specified, uses the current user.
|
||||
|
||||
=head3 depth
|
||||
|
||||
|
|
@ -497,36 +485,52 @@ sub exportGetDescendants {
|
|||
my $user = shift;
|
||||
my $depth = shift;
|
||||
|
||||
# check for parameter validity
|
||||
if( (!defined $user) or (ref $user ne 'WebGUI::User') ) {
|
||||
WebGUI::Error::InvalidObject->throw(
|
||||
expected => 'WebGUI::User',
|
||||
got => ref $user,
|
||||
error => 'Need a WebGUI::User object',
|
||||
param => $user
|
||||
);
|
||||
}
|
||||
# use current session by default
|
||||
my $session = $self->session;
|
||||
my $asset = $self;
|
||||
my $sGuard;
|
||||
|
||||
# check for parameter validity
|
||||
if( (!defined $depth) or (!looks_like_number($depth)) ) {
|
||||
WebGUI::Error::InvalidParam->throw(error => 'Need a depth', param => $depth);
|
||||
}
|
||||
|
||||
# open a temporary session as the user doing the exporting so we don't get
|
||||
# assets that they can't see
|
||||
my $tempSession = WebGUI::Session->open($self->session->config->getWebguiRoot,$self->session->config->getFilename);
|
||||
$tempSession->user( { userId => $user->userId } );
|
||||
if ( defined $user ) {
|
||||
# open a temporary session as the user doing the exporting so we don't get
|
||||
# assets that they can't see
|
||||
if ( ref $user && $user->isa('WebGUI::User') ) {
|
||||
$session = WebGUI::Session->open(
|
||||
$session->config->getWebguiRoot,
|
||||
$session->config->getFilename,
|
||||
);
|
||||
$session->user( { userId => $user->userId } );
|
||||
$sGuard = Scope::Guard->new(sub {
|
||||
$session->var->end;
|
||||
$session->close;
|
||||
});
|
||||
# clone self in the new session
|
||||
$asset = WebGUI::Asset->new(
|
||||
$session,
|
||||
$self->getId,
|
||||
$self->get('className'),
|
||||
$self->get('revisionDate'),
|
||||
);
|
||||
}
|
||||
else {
|
||||
WebGUI::Error::InvalidObject->throw(
|
||||
expected => 'WebGUI::User',
|
||||
got => ref $user,
|
||||
error => 'Need a WebGUI::User object',
|
||||
param => $user,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
# clone self in the new session and get its lineage as the new user
|
||||
my $cloneOfSelf = WebGUI::Asset->new($tempSession, $self->getId, $self->get('className'), $self->get('revisionDate'));
|
||||
my $assetIds = $cloneOfSelf->getLineage( [ "self", "descendants" ], {
|
||||
endingLineageLength => $cloneOfSelf->getLineageLength + $depth,
|
||||
orderByClause => 'assetData.url DESC',
|
||||
my $assetIds = $asset->getLineage( [ "self", "descendants" ], {
|
||||
endingLineageLength => $asset->getLineageLength + $depth,
|
||||
orderByClause => 'assetData.url DESC',
|
||||
} );
|
||||
|
||||
# properly close the temp session
|
||||
$tempSession->var->end;
|
||||
$tempSession->close;
|
||||
|
||||
return $assetIds;
|
||||
}
|
||||
|
||||
|
|
@ -553,55 +557,58 @@ index filename passed from L</exportAsHtml>
|
|||
sub exportGetUrlAsPath {
|
||||
my $self = shift;
|
||||
my $index = shift || 'index.html';
|
||||
my $options = shift || {};
|
||||
|
||||
my $config = $self->session->config;
|
||||
|
||||
# make sure that the export path is valid
|
||||
WebGUI::Asset->exportCheckPath($self->session);
|
||||
my $exportPath = $self->exportCheckPath;
|
||||
|
||||
# if we're still here, it's valid. get it.
|
||||
my $exportPath = $config->get('exportPath');
|
||||
|
||||
# get a list of file types to pass through as-is
|
||||
my $fileTypes = $config->get('exportBinaryExtensions');
|
||||
|
||||
# get the asset's URL as a URI::URL object for easy parsing of components
|
||||
my $url = URI::URL->new($self->session->url->getSiteURL . $self->getUrl);
|
||||
my $url = $self->get('url');
|
||||
|
||||
# for either a sub page or extension, remove the existing extension
|
||||
if ($options->{subPage} || $options->{extension}) {
|
||||
$url =~ s/\.[^.]+$//;
|
||||
}
|
||||
if ($options->{extension}) {
|
||||
my $ext = $options->{extension};
|
||||
$ext =~ s/^\.//;
|
||||
$url .= ".$ext";
|
||||
}
|
||||
if ($options->{subPage}) {
|
||||
my $subPage = $options->{subPage};
|
||||
$subPage =~ s{^/}{};
|
||||
$url .= "/$subPage";
|
||||
}
|
||||
$url = URI::URL->new($self->session->url->gateway($url));
|
||||
my @pathComponents = $url->path_components;
|
||||
shift @pathComponents; # first item is the empty string
|
||||
my $filename = pop @pathComponents;
|
||||
|
||||
# if there's no . (i.e., no file with an extension) in $filename, this is
|
||||
# simple. Slap on a directory separator, $index, and return it.
|
||||
if(!index $filename, '.') { # no need to regex match for a single character
|
||||
return Path::Class::File->new($exportPath, @pathComponents, $filename, $index);
|
||||
my ($extension) = $filename =~ /\.([^.]+)$/;
|
||||
if ($extension && WebGUI::Utility::isIn($extension, @{ $fileTypes }) ) {
|
||||
return Path::Class::File->new($exportPath, @pathComponents, $filename);
|
||||
}
|
||||
else { # got a dot
|
||||
my $extension = (File::Basename::fileparse($filename, qr/[^.]*$/))[2]; # get just the extension
|
||||
|
||||
# check if the file type is recognised by apache. if it is, return it
|
||||
# as-is. if not, slap on the directory separator, $index, and return
|
||||
# it.
|
||||
if( isIn($extension, @{ $fileTypes } ) ) {
|
||||
return Path::Class::File->new($exportPath, @pathComponents, $filename);
|
||||
}
|
||||
else { # don't know what it is
|
||||
return Path::Class::File->new($exportPath, @pathComponents, $filename, $index);
|
||||
}
|
||||
else {
|
||||
return Path::Class::File->new($exportPath, @pathComponents, $filename, $index);
|
||||
}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
=head2 exportSymlinkExtrasUploads ( session )
|
||||
=head2 exportSymlinkExtrasUploads ( [ session ] )
|
||||
|
||||
Class method. Sets up the extras and uploads symlinks.
|
||||
Class or object method. Sets up the extras and uploads symlinks.
|
||||
|
||||
Takes the following parameters:
|
||||
|
||||
=head3 session
|
||||
|
||||
A reference to a L<WebGUI::Session> object.
|
||||
A reference to a L<WebGUI::Session> object. Should only be specified if caled as a class method.
|
||||
|
||||
Throws the following exceptions:
|
||||
|
||||
|
|
@ -617,11 +624,16 @@ The first parameter is not a L<WebGUI::Session>.
|
|||
|
||||
sub exportSymlinkExtrasUploads {
|
||||
my $class = shift;
|
||||
my $session = shift;
|
||||
|
||||
# check that session is a valid WebGUI::Session object
|
||||
if(!defined $session || ref $session ne 'WebGUI::Session') {
|
||||
WebGUI::Error::InvalidObject->throw(error => "first param to exportSymlinkExtrasUploads must be a WebGUI::Session");
|
||||
my $session;
|
||||
if (ref $class && $class->can('session')) {
|
||||
$session = $class->session;
|
||||
}
|
||||
else {
|
||||
$session = shift;
|
||||
# make sure we were given the right parameters
|
||||
if((!ref $session) || !$session->isa('WebGUI::Session')) {
|
||||
WebGUI::Error::InvalidObject->throw(error => "first param to exportSymlinkExtrasUploads as a class method must be a WebGUI::Session");
|
||||
}
|
||||
}
|
||||
|
||||
my $config = $session->config;
|
||||
|
|
@ -631,14 +643,11 @@ sub exportSymlinkExtrasUploads {
|
|||
my $uploadsUrl = $config->get('uploadsURL');
|
||||
|
||||
# we have no assurance whether the exportPath is valid or not, so check it.
|
||||
WebGUI::Asset->exportCheckPath($session);
|
||||
|
||||
# if we're still here, it's valid
|
||||
my $exportPath = $config->get('exportPath');
|
||||
my $exportPath = WebGUI::Asset->exportCheckPath($session);
|
||||
|
||||
# chop off leading / so we don't accidentally get absolute paths
|
||||
for my $url ($extrasUrl, $uploadsUrl) {
|
||||
s#^/*##;
|
||||
$url =~ s{^/*}{};
|
||||
}
|
||||
|
||||
# construct the destination paths
|
||||
|
|
@ -667,7 +676,7 @@ sub exportSymlinkExtrasUploads {
|
|||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
=head2 exportSymlinkRoot ( session, defaultAsset, [indexFile], [quiet] )
|
||||
=head2 exportSymlinkRoot ( [session,] defaultAsset, [indexFile], [reportSession] )
|
||||
|
||||
Class method. Places a symlink in the exportPath linking to the index file of
|
||||
the default asset.
|
||||
|
|
@ -676,7 +685,7 @@ Takes the following parameters:
|
|||
|
||||
=head3 session
|
||||
|
||||
A reference to a L<WebGUI::Session> object.
|
||||
A reference to a L<WebGUI::Session> object. Should only be specified if called as a class method.
|
||||
|
||||
Throws the following exceptions:
|
||||
|
||||
|
|
@ -689,9 +698,9 @@ symlink for the root URL.
|
|||
|
||||
Optional. Specifies a file name for the index URL. Defaults to C<index.html>.
|
||||
|
||||
=head3 quiet
|
||||
=head3 reportSession
|
||||
|
||||
Optional. Whether to be quiet with our output.
|
||||
Optional. If included, status information will be printed to this session.
|
||||
|
||||
=head3 WebGUI::Error
|
||||
|
||||
|
|
@ -705,16 +714,21 @@ The first parameter is not a L<WebGUI::Session>.
|
|||
|
||||
sub exportSymlinkRoot {
|
||||
my $class = shift;
|
||||
my $session;
|
||||
if (ref $class && $class->can('session')) {
|
||||
$session = $class->session;
|
||||
}
|
||||
else {
|
||||
$session = shift;
|
||||
# make sure we were given the right parameters
|
||||
if((!ref $session) || !$session->isa('WebGUI::Session')) {
|
||||
WebGUI::Error::InvalidObject->throw(error => "first param to exportSymlinkRoot as a class method must be a WebGUI::Session");
|
||||
}
|
||||
}
|
||||
|
||||
my $session = shift;
|
||||
my $defaultAsset = shift;
|
||||
my $index = shift || 'index.html';
|
||||
my $quiet = shift;
|
||||
|
||||
# check that $session is valid
|
||||
if(!defined $session || ref $session ne 'WebGUI::Session') {
|
||||
WebGUI::Error::InvalidObject->throw(error => 'first param to exportSymlinkRoot must be a WebGUI::Session');
|
||||
}
|
||||
my $reportSession = shift;
|
||||
|
||||
# check that $defaultAsset is valid
|
||||
if( !defined $defaultAsset || !$defaultAsset->isa('WebGUI::Asset') ) {
|
||||
|
|
@ -722,10 +736,7 @@ sub exportSymlinkRoot {
|
|||
}
|
||||
|
||||
# can't be sure if the export path exists, so check it.
|
||||
WebGUI::Asset->exportCheckPath($session);
|
||||
|
||||
# if we're still here, it's valid, so get it
|
||||
my $exportPath = $session->config->get('exportPath');
|
||||
my $exportPath = WebGUI::Asset->exportCheckPath($session);
|
||||
|
||||
# get the source and the destination
|
||||
my $source = $defaultAsset->exportGetUrlAsPath->absolute->stringify;
|
||||
|
|
@ -734,9 +745,9 @@ sub exportSymlinkRoot {
|
|||
my $i18n = WebGUI::International->new($session, 'Asset');
|
||||
|
||||
# tell the user what's happening
|
||||
if( !$quiet ) {
|
||||
if ( $reportSession ) {
|
||||
my $message = $i18n->get('rootUrl symlinking default') . "\n";
|
||||
$session->output->print($message);
|
||||
$reportSession->output->print($message);
|
||||
}
|
||||
|
||||
# if the link exists, check if it's set up properly. if it's not, remove it.
|
||||
|
|
@ -767,7 +778,7 @@ sub exportWriteFile {
|
|||
my $self = shift;
|
||||
|
||||
# we have no assurance whether the exportPath is valid or not, so check it.
|
||||
WebGUI::Asset->exportCheckPath($self->session);
|
||||
$self->exportCheckPath;
|
||||
|
||||
# if we're still here, everything is well with the export path. let's make
|
||||
# sure that this user can view the asset that we want to export.
|
||||
|
|
@ -775,14 +786,12 @@ sub exportWriteFile {
|
|||
WebGUI::Error->throw(error => "user can't view asset at " . $self->getUrl . " to export it");
|
||||
}
|
||||
|
||||
|
||||
# if we're still here, everything is well with the export path. let's get
|
||||
# our destination FS path and then make any required directories.
|
||||
|
||||
my $dest = $self->exportGetUrlAsPath;
|
||||
my $parent = $dest->parent;
|
||||
|
||||
eval { File::Path::mkpath($parent->absolute->stringify) };
|
||||
eval { $parent->absolute->mkpath };
|
||||
if($@) {
|
||||
WebGUI::Error->throw(error => "could not make directory " . $parent->absolute->stringify);
|
||||
}
|
||||
|
|
@ -792,8 +801,6 @@ sub exportWriteFile {
|
|||
if($@) {
|
||||
WebGUI::Error->throw(error => "can't open " . $dest->absolute->stringify . " for writing: $!");
|
||||
}
|
||||
my $previousHandle = $self->session->{_handle};
|
||||
my $previousDefaultAsset = $self->session->asset;
|
||||
$self->session->asset($self);
|
||||
$self->session->output->setHandle($fh);
|
||||
my $contents = $self->exportHtml_view;
|
||||
|
|
@ -802,8 +809,6 @@ sub exportWriteFile {
|
|||
unless($contents eq 'chunked') {
|
||||
$self->session->output->print($contents);
|
||||
}
|
||||
|
||||
$self->session->output->setHandle($previousHandle);
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
|
@ -886,7 +891,7 @@ sub www_export {
|
|||
);
|
||||
$f->submit;
|
||||
my $message;
|
||||
eval { WebGUI::Asset->exportCheckPath($self->session) };
|
||||
eval { $self->exportCheckPath };
|
||||
if($@) {
|
||||
$message = $@;
|
||||
}
|
||||
|
|
@ -911,7 +916,7 @@ sub www_exportStatus {
|
|||
$iframeUrl = $self->session->url->append($iframeUrl, $formVar . '=' . $self->session->form->process($formVar));
|
||||
}
|
||||
|
||||
my $output = '<iframe src="' . $iframeUrl . '" title="' . $i18n->get('Page Export Status') . '" width="700" height="500"></iframe>';
|
||||
my $output = '<iframe src="' . $iframeUrl . '" title="' . $i18n->get('Page Export Status') . '" width="100%" height="500"></iframe>';
|
||||
$self->getAdminConsole->render($output, $i18n->get('Page Export Status'), "Asset");
|
||||
}
|
||||
|
||||
|
|
@ -927,30 +932,40 @@ Executes the export process and displays real time status. This operation is dis
|
|||
|
||||
sub www_exportGenerate {
|
||||
my $self = shift;
|
||||
return $self->session->privilege->insufficient() unless ($self->session->user->isInGroup(13));
|
||||
my $session = $self->session;
|
||||
return $session->privilege->insufficient
|
||||
unless $session->user->isInGroup(13);
|
||||
|
||||
# Unbuffered data output
|
||||
$|++;
|
||||
$self->session->style->useEmptyStyle(1);
|
||||
$self->session->http->sendHeader;
|
||||
$session->style->useEmptyStyle(1);
|
||||
$session->http->sendHeader;
|
||||
my $splitter = $self->getSeparator;
|
||||
my $style = $session->style->process($splitter);
|
||||
my ($head, $foot) = split /\Q$splitter/, $style;
|
||||
$session->output->print($head, 1);
|
||||
|
||||
my $i18n = WebGUI::International->new($self->session, 'Asset');
|
||||
my ($success, $description) = $self->exportAsHtml( {
|
||||
my $i18n = WebGUI::International->new($session, 'Asset');
|
||||
my $args = {
|
||||
quiet => 0,
|
||||
userId => $self->session->form->process('userId'),
|
||||
indexFileName => $self->session->form->process('index'),
|
||||
extrasUploadAction => $self->session->form->process('extrasUploadsAction'),
|
||||
rootUrlAction => $self->session->form->process('rootUrlAction'),
|
||||
depth => $self->session->form->process('depth'),
|
||||
exportUrl => $self->session->form->process('exportUrl'),
|
||||
});
|
||||
if (!$success) {
|
||||
$self->session->output->print($description, 1);
|
||||
return "chunked";
|
||||
userId => $session->form->process('userId'),
|
||||
indexFileName => $session->form->process('index'),
|
||||
extrasUploadAction => $session->form->process('extrasUploadsAction'),
|
||||
rootUrlAction => $session->form->process('rootUrlAction'),
|
||||
depth => $session->form->process('depth'),
|
||||
exportUrl => $session->form->process('exportUrl'),
|
||||
};
|
||||
eval {
|
||||
my $message = $self->exportAsHtml( $args );
|
||||
$self->session->output->print($message, 1);
|
||||
$self->session->output->print(
|
||||
'<a target="_parent" href="' . $self->getUrl . '">' . $i18n->get(493, 'WebGUI') . '</a>'
|
||||
);
|
||||
};
|
||||
if ($@) {
|
||||
$self->session->output->print("$@", 1);
|
||||
}
|
||||
|
||||
$self->session->output->print($description, 1);
|
||||
$self->session->output->print('<a target="_parent" href="' . $self->getUrl . '">' . $i18n->get(493, 'WebGUI') . '</a>');
|
||||
$session->output->print($foot, 1);
|
||||
return "chunked";
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -269,6 +269,14 @@ sub definition {
|
|||
label => $i18n->get('global head tags label'),
|
||||
hoverHelp => $i18n->get('global head tags description'),
|
||||
defaultValue => $setting->get('globalHeadTags'),
|
||||
};
|
||||
push @fields, {
|
||||
tab => 'ui',
|
||||
fieldType => 'yesNo',
|
||||
name => 'useMobileStyle',
|
||||
label => $i18n->get('mobile style label'),
|
||||
hoverHelp => $i18n->get('mobile style description'),
|
||||
defaultValue => $setting->get('useMobileStyle'),
|
||||
};
|
||||
# messaging settings
|
||||
push(@fields, {
|
||||
|
|
|
|||
|
|
@ -239,6 +239,26 @@ sub DESTROY {
|
|||
$self->close;
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
=head2 duplicate ( )
|
||||
|
||||
Creates a new session using the same WebGUI root, config file, and user.
|
||||
|
||||
=cut
|
||||
|
||||
sub duplicate {
|
||||
my $self = shift;
|
||||
my $newSession = WebGUI::Session->open(
|
||||
$self->config->getWebguiRoot,
|
||||
$self->config->getFilename,
|
||||
undef,
|
||||
undef,
|
||||
$self->getId,
|
||||
);
|
||||
return $newSession;
|
||||
}
|
||||
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
|
|
|
|||
|
|
@ -120,6 +120,51 @@ sub makePrintable {
|
|||
$self->{_makePrintable} = shift;
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
=head2 useMobileStyle
|
||||
|
||||
Returns a true value if we are on a mobile display.
|
||||
|
||||
=cut
|
||||
|
||||
sub useMobileStyle {
|
||||
my $self = shift;
|
||||
my $session = $self->session;
|
||||
my $scratchCheck = $session->scratch->get('useMobileStyle');
|
||||
if (defined $scratchCheck) {
|
||||
return $scratchCheck;
|
||||
}
|
||||
if (exists $self->{_useMobileStyle}) {
|
||||
return $self->{_useMobileStyle};
|
||||
}
|
||||
|
||||
if (! $session->setting->get('useMobileStyle')) {
|
||||
return $self->{_useMobileStyle} = 0;
|
||||
}
|
||||
my $ua = $session->env->get('HTTP_USER_AGENT');
|
||||
for my $mobileUA (@{ $self->session->config->get('mobileUserAgents') }) {
|
||||
if ($ua =~ m/$mobileUA/) {
|
||||
return $self->{_useMobileStyle} = 1;
|
||||
}
|
||||
}
|
||||
return $self->{_useMobileStyle} = 0;
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
=head2 setMobileStyle
|
||||
|
||||
Sets whether the mobile style should be used for this session.
|
||||
|
||||
=cut
|
||||
|
||||
sub setMobileStyle {
|
||||
my $self = shift;
|
||||
my $enableMobile = shift;
|
||||
$self->session->scratch->set('useMobileStyle', $enableMobile);
|
||||
return $enableMobile;
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------
|
||||
|
||||
|
|
|
|||
|
|
@ -139,6 +139,13 @@ be useful, others may not.|,
|
|||
lastUpdated => 1210967539
|
||||
},
|
||||
|
||||
'mobileTemplateId label' => {
|
||||
message => 'Mobile Template',
|
||||
},
|
||||
|
||||
'mobileTemplateId description' => {
|
||||
message => 'Choose the template to use if viewing this Page Layout in a mobile browser.',
|
||||
},
|
||||
};
|
||||
|
||||
1;
|
||||
|
|
|
|||
|
|
@ -115,6 +115,13 @@ is displayed as part of a Layout Asset, the Layout Asset's <b>Style Template</b>
|
|||
lastUpdated => 1167374430,
|
||||
},
|
||||
|
||||
'mobileStyleTemplateId label' => {
|
||||
message => 'Mobile Style Template'
|
||||
},
|
||||
'mobileStyleTemplateId description' => {
|
||||
message => q|Select a style template from the list to enclose your asset if it is viewed on a mobile browser|,
|
||||
},
|
||||
|
||||
};
|
||||
|
||||
1;
|
||||
|
|
|
|||
|
|
@ -4402,6 +4402,13 @@ Users may override this setting in their profile.
|
|||
lastUpdated => 1239057119,
|
||||
},
|
||||
|
||||
'mobile style label' => {
|
||||
message => 'Use Mobile Style',
|
||||
},
|
||||
'mobile style description' => {
|
||||
message => q{Enables displaying using a mobile style template and mobile page layout template. When enabled, the alternate templates are used when the browser's user agent string matches the list set in the config file.},
|
||||
},
|
||||
|
||||
};
|
||||
|
||||
1;
|
||||
|
|
|
|||
|
|
@ -128,6 +128,7 @@ checkModule('JavaScript::Packer', '0.02' );
|
|||
checkModule('CSS::Packer', '0.2' );
|
||||
checkModule('Business::Tax::VAT::Validation', '0.20' );
|
||||
checkModule('Crypt::SSLeay', '0.57' );
|
||||
checkModule('Scope::Guard', '0.03' );
|
||||
|
||||
failAndExit("Required modules are missing, running no more checks.") if $missingModule;
|
||||
|
||||
|
|
|
|||
|
|
@ -56,7 +56,7 @@ isa_ok($e, 'WebGUI::Error::InvalidObject', 'exportCheckPath tests that its argum
|
|||
cmp_deeply(
|
||||
$e,
|
||||
methods(
|
||||
error => "first param to exportCheckPath must be a WebGUI::Session",
|
||||
error => 'first param to exportCheckPath as a class method must be a WebGUI::Session',
|
||||
),
|
||||
"exportCheckPath tests that its argument is a WebGUI::Session"
|
||||
);
|
||||
|
|
@ -150,7 +150,7 @@ $config->set('exportPath', $tempDirectory);
|
|||
|
||||
eval { $returnCode = WebGUI::Asset->exportCheckPath($session) };
|
||||
is($@, '', "exportCheckPath with valid path lives");
|
||||
is($returnCode, 1, "exportCheckPath returns true value");
|
||||
ok($returnCode, "exportCheckPath returns true value");
|
||||
|
||||
# now, let's try a directory to which we know we have access, but a path within
|
||||
# it that doesn't exist.
|
||||
|
|
@ -159,7 +159,7 @@ $config->set('exportPath', $accessibleDirectory->stringify); # now accessible!
|
|||
|
||||
eval { $returnCode = WebGUI::Asset->exportCheckPath($session) };
|
||||
is($@, '', "exportCheckPath creating subdirectory lives");
|
||||
is($returnCode, 1, "exportCheckPath creating subdirectory returns true value");
|
||||
ok($returnCode, "exportCheckPath creating subdirectory returns true value");
|
||||
is(-d $accessibleDirectory, 1, "exportCheckPath creating subdirectory actually creates said subdirectory");
|
||||
|
||||
#----------------------------------------------------------------------------
|
||||
|
|
@ -492,7 +492,7 @@ isa_ok($e, 'WebGUI::Error::InvalidObject', 'exportSymlinkExtrasUploads without s
|
|||
cmp_deeply(
|
||||
$e,
|
||||
methods(
|
||||
error => 'first param to exportSymlinkExtrasUploads must be a WebGUI::Session',
|
||||
error => 'first param to exportSymlinkExtrasUploads as a class method must be a WebGUI::Session',
|
||||
),
|
||||
'exportSymlinkExtrasUploads without session object throws',
|
||||
);
|
||||
|
|
@ -504,7 +504,7 @@ isa_ok($e, 'WebGUI::Error::InvalidObject', 'exportSymlinkExtrasUploads called wi
|
|||
cmp_deeply(
|
||||
$e,
|
||||
methods(
|
||||
error => 'first param to exportSymlinkExtrasUploads must be a WebGUI::Session',
|
||||
error => 'first param to exportSymlinkExtrasUploads as a class method must be a WebGUI::Session',
|
||||
),
|
||||
'exportSymlinkExtrasUploads called with memetic parameter throws',
|
||||
);
|
||||
|
|
@ -541,7 +541,7 @@ $e = Exception::Class->caught;
|
|||
isa_ok($e, 'WebGUI::Error::InvalidObject', 'exportSymlinkRoot without session object throws');
|
||||
cmp_deeply($e,
|
||||
methods(
|
||||
error => 'first param to exportSymlinkRoot must be a WebGUI::Session'
|
||||
error => 'first param to exportSymlinkRoot as a class method must be a WebGUI::Session'
|
||||
),
|
||||
'exportSymlinkRoot without session object throws',
|
||||
);
|
||||
|
|
@ -553,7 +553,7 @@ $e = Exception::Class->caught;
|
|||
isa_ok($e, 'WebGUI::Error::InvalidObject', 'exportSymlinkRoot called with memetic parameter throws');
|
||||
cmp_deeply($e,
|
||||
methods(
|
||||
error => 'first param to exportSymlinkRoot must be a WebGUI::Session'
|
||||
error => 'first param to exportSymlinkRoot as a class method must be a WebGUI::Session'
|
||||
),
|
||||
'exportSymlinkRoot called with memetic parameter throws',
|
||||
);
|
||||
|
|
@ -590,18 +590,18 @@ cmp_deeply(
|
|||
$home->exportWriteFile;
|
||||
my $symlinkedRoot = Path::Class::File->new($exportPath, 'index.html');
|
||||
my $homePath = $home->exportGetUrlAsPath;
|
||||
eval { WebGUI::Asset->exportSymlinkRoot($session, $home, '', 1) };
|
||||
eval { WebGUI::Asset->exportSymlinkRoot($session, $home, '') };
|
||||
is($@, '', 'exportSymlinkRoot works when it should');
|
||||
ok(-e $symlinkedRoot->stringify, 'exportSymlinkRoot sets up link correctly and supplies default index');
|
||||
is($homePath, readlink $symlinkedRoot->stringify, 'exportSymlinkRoot sets up link correctly and supplies default index');
|
||||
is(readlink $symlinkedRoot->stringify, $homePath, 'exportSymlinkRoot sets up link correctly and supplies default index');
|
||||
unlink $symlinkedRoot->stringify;
|
||||
|
||||
|
||||
# give it an index and ensure it works
|
||||
eval { WebGUI::Asset->exportSymlinkRoot($session, $home, 'index.html', 1) };
|
||||
eval { WebGUI::Asset->exportSymlinkRoot($session, $home, 'index.html') };
|
||||
is($@, '', 'exportSymlinkRoot works when it should');
|
||||
ok(-e $symlinkedRoot->stringify, 'exportSymlinkRoot sets up link correctly and supplies default index');
|
||||
is($homePath, readlink $symlinkedRoot->stringify, 'exportSymlinkRoot sets up link correctly and supplies default index');
|
||||
is(readlink $symlinkedRoot->stringify, $homePath, 'exportSymlinkRoot sets up link correctly and supplies default index');
|
||||
unlink $symlinkedRoot->stringify;
|
||||
|
||||
|
||||
|
|
@ -644,26 +644,7 @@ $descendants = $grandChild->exportGetDescendants( WebGUI::User->new($session, 1)
|
|||
|
||||
cmp_deeply($descendants, $gcDescendants, "exportGetDescendants returns correct data for getting-started");
|
||||
|
||||
# finally, ensure that calling exportGetDescendants without a userID throws an exception.
|
||||
|
||||
eval { $home->exportGetDescendants };
|
||||
|
||||
$e = Exception::Class->caught;
|
||||
isa_ok($e, 'WebGUI::Error::InvalidObject', 'exportGetDescendants called without a user object throws');
|
||||
cmp_deeply(
|
||||
$e,
|
||||
methods(
|
||||
expected => 'WebGUI::User',
|
||||
got => '',
|
||||
error => 'Need a WebGUI::User object',
|
||||
param => undef,
|
||||
),
|
||||
"exportGetDescendants called without a user object throws",
|
||||
);
|
||||
|
||||
# make sure calling exportGetDescendants without a depth throws an exception.
|
||||
|
||||
eval { $home->exportGetDescendants( WebGUI::User->new($session, 1) ) };
|
||||
$e = Exception::Class->caught;
|
||||
isa_ok($e, 'WebGUI::Error::InvalidParam', 'exportGetDescendants called without a depth throws');
|
||||
cmp_deeply(
|
||||
|
|
@ -699,26 +680,23 @@ my $exportPath = Path::Class::Dir->new($session->config->get('exportPath'));
|
|||
# default. exportAsHtml is supposed to catch exceptions, not throw them, so
|
||||
# we'll be testing the return values rather than for an exception.
|
||||
|
||||
($success, $message) = $home->exportAsHtml;
|
||||
is($success, 0, "exportAsHtml returns 0 when not given a userId");
|
||||
is($message, "need a userId parameter", "exportAsHtml returns correct message when not given a userId");
|
||||
eval { $message = $home->exportAsHtml };
|
||||
is($@, "need a userId parameter", "exportAsHtml returns correct error when not given a userId");
|
||||
|
||||
# omitting the userId works, so let's give it a bogus userId
|
||||
($success, $message) = $home->exportAsHtml( { userId => '<rizen> perlDreamer is a 500 lb test mandating gorilla' } );
|
||||
is($success, 0, "exportAsHtml returns 0 when given a bogus (but nonetheless funny) userId");
|
||||
is($message, "'<rizen> perlDreamer is a 500 lb test mandating gorilla' is not a valid userId", "exportAsHtml returns correct message when given a bogus (but nonetheless funny) userId");
|
||||
eval { $message = $home->exportAsHtml( { userId => '<rizen> perlDreamer is a 500 lb test mandating gorilla' } ) };
|
||||
is($@, "'<rizen> perlDreamer is a 500 lb test mandating gorilla' is not a valid userId", "exportAsHtml throws correct error when given a bogus (but nonetheless funny) userId");
|
||||
|
||||
# checking an autogenerated userId
|
||||
my $randomUser = WebGUI::User->new($session, 'new');
|
||||
($success, $message) = $home->exportAsHtml( { userId => $randomUser->userId, depth => 99} );
|
||||
is($success, 1, "exportAsHtml returns 1 when given a valid userId");
|
||||
eval { $message = $home->exportAsHtml( { userId => $randomUser->userId, depth => 99} ) };
|
||||
is($@, '', "exportAsHtml doesn't throw error when given a valid userId");
|
||||
$randomUser->delete;
|
||||
undef $randomUser;
|
||||
|
||||
# checking userId works, so check extrasUploadAction next.
|
||||
($success, $message) = $home->exportAsHtml( { userId => 3, depth => 99, extrasUploadAction => 'o hai' } );
|
||||
is($success, 0, "exportAsHtml returns 0 when given bogus, memetic extrasUploadAction parameter");
|
||||
is($message, "'o hai' is not a valid extrasUploadAction", "exportAsHtml returns 0 when given bogus, memetic extrasUploadAction parameter");
|
||||
eval { $message = $home->exportAsHtml( { userId => 3, depth => 99, extrasUploadAction => 'o hai' } ) };
|
||||
is($@, "'o hai' is not a valid extrasUploadAction", "exportAsHtml throws correct error when given bogus, memetic extrasUploadAction parameter");
|
||||
|
||||
# rootUrlAction
|
||||
($success, $message) = $home->exportAsHtml( { userId => 3, depth => 99, rootUrlAction => 'NO U' } );
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@ is_deeply($wf->getCrons, [], 'workflow has no crons');
|
|||
isa_ok(WebGUI::Workflow->getList($session), 'HASH', 'getList returns a hashref');
|
||||
|
||||
ok(!isIn($wfId, keys %{WebGUI::Workflow->getList($session)}), 'workflow not in enabled list');
|
||||
is(scalar keys %{WebGUI::Workflow->getList($session)}, 11, 'There are eleven default workflows, of all types, shipped with WebGUI');
|
||||
is(scalar keys %{WebGUI::Workflow->getList($session)}, 12, 'There are twelve default workflows, of all types, shipped with WebGUI');
|
||||
|
||||
$wf->set({enabled => 1});
|
||||
ok($wf->get('enabled'), 'workflow is enabled');
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue