Forums / Developer / Module/view redirect while preserving POST variables

Module/view redirect while preserving POST variables

Author Message

Piotrek Karaś

Monday 18 February 2008 10:10:41 pm

Let's say we have a standard form with NewButton and 'content/action' action, which is supposed to initiate an object:

  <form method="post" action="/index.php/pl/content/action">
    <input name="ClassIdentifier" value="some_class" type="hidden">
    <input name="NodeID" value="64" type="hidden">
    <input name="ContentLanguageCode" value="pol-PL" type="hidden">
    <input class="button" name="NewButton" value="Create some object" type="submit">
  </form>

Now, before we actually perform this action, we would like to perform some other operations in order to determine whether 'content/action' action should actually be performed. So, I create my own module and view, for example 'check/new', and modify the above form:

  <form method="post" action="/index.php/pl/check/new">
    <input name="ClassIdentifier" value="some_class" type="hidden">
    <input name="NodeID" value="64" type="hidden">
    <input name="ContentLanguageCode" value="pol-PL" type="hidden">
    <input class="button" name="NewButton" value="Create some object" type="submit">
  </form>

Now, in my own module I process the variables, and decide that new object can be created. <b>How do I redirect to 'content/action' with all those hidden post vars preserved? Is it possible with eZ API?</b>. Standard $Module->redirectTo(...) methods do not seem to pass the post variables.

I'd be grateful for any hints!

--
Company: mediaSELF Sp. z o.o., http://www.mediaself.pl
eZ references: http://ez.no/partners/worldwide_partners/mediaself
eZ certified developer: http://ez.no/certification/verify/272585
eZ blog: http://ez.ryba.eu

Bruce Morrison

Monday 18 February 2008 11:47:53 pm

Hi Piotrek

Without knowing the details it sounds as if you might be better off with a before_publish workflow.

If that doesn't work for your situation you can try doing a module redirect via the eZModule class:
http://pubsvn.ez.no/doxygen/trunk/html/classeZModule.html#6ddeaa1f5e2cfac8f5b56533c51d53df though that might still use redirects.

You might be able to do something list this:

$module = eZModule::exists( 'content' );
$module->run('action');

Cheers
Bruce

My Blog: http://www.stuffandcontent.com/
Follow me on twitter: http://twitter.com/brucemorrison
Consolidated eZ Publish Feed : http://friendfeed.com/rooms/ez-publish

Piotrek Karaś

Tuesday 19 February 2008 1:17:18 am

Bruce,

<i>You might be able to do something list this:</i>

Seems like something worked, the action.php view file was indeed executed (I was able to check that and even POST variables are there). The problem is that it didn't perform what I expected, it is supposed to do what it would have normally done - assign a new node and proceed to the edit view. Unfortunately, that didn't happen ;(

Thanks,

PS. Not sure if before_publish is what I need plus hoped to avoid that and carry out the task in my own module/view.

--
Company: mediaSELF Sp. z o.o., http://www.mediaself.pl
eZ references: http://ez.no/partners/worldwide_partners/mediaself
eZ certified developer: http://ez.no/certification/verify/272585
eZ blog: http://ez.ryba.eu

Gaetano Giunta

Tuesday 19 February 2008 1:29:45 am

As a side note: did anybody ever try to make use of content/search (or advanced search) functionality as an object picker instead of content/browse for any action involving choosing a location/object, such as move or copy?
It would be a better way to select content when eg you have one folder with 100.000 objects inside (think large user bases)

Principal Consultant International Business
Member of the Community Project Board

Bruce Morrison

Tuesday 19 February 2008 1:41:11 am

Hi Piotrek

Try this

$module = eZModule::exists( 'content' );
$module->setCurrentAction('NewObjectAddNodeAssignment','action');
$module->run('action');

@Gaetano
Your are right, though probably should be it's own thread?

Cheers
Bruce

My Blog: http://www.stuffandcontent.com/
Follow me on twitter: http://twitter.com/brucemorrison
Consolidated eZ Publish Feed : http://friendfeed.com/rooms/ez-publish

Piotrek Karaś

Tuesday 19 February 2008 2:02:41 am

$module = eZModule::exists( 'content');
$module->setCurrentAction('NewObjectAddNodeAssignment','action');
$module->run('action');

Hehe, yes, I tried that in the meantime, after having looked through the action.php file. But that doesn't seem to change anything, NewObjectAddNodeAssignment seems the default setting, because whether I use that additional line or not, I get inside that if-statement. It must fail further...

Thanks anyway!

--
Company: mediaSELF Sp. z o.o., http://www.mediaself.pl
eZ references: http://ez.no/partners/worldwide_partners/mediaself
eZ certified developer: http://ez.no/certification/verify/272585
eZ blog: http://ez.ryba.eu

Bruce Morrison

Tuesday 19 February 2008 2:52:00 am

Hi Piotrek

Try storing the POST variables in the session then redirecting to content/action...from user/login.php

    
    // Save array of previous post variables in session variable
    $post = $http->attribute( 'post' );
    $lastPostVars = array();
    foreach ( array_keys( $post ) as $postKey )
    {
        if ( substr( $postKey, 0, 5 ) == 'Last_' )
            $lastPostVars[ substr( $postKey, 5, strlen( $postKey ) )] = $post[ $postKey ];
    }
    if ( count( $lastPostVars ) > 0 )
    {
        $postData = $lastPostVars;
        $http->setSessionVariable( 'LastPostVars', $lastPostVars );
    }

content/action.php merges these with it's own POST variables. I think the is the mechanism that allows object creation to continue after a login is required.

I'll leave it for now but I'm positive it's possible and not difficult ;)

Cheers
Bruce

My Blog: http://www.stuffandcontent.com/
Follow me on twitter: http://twitter.com/brucemorrison
Consolidated eZ Publish Feed : http://friendfeed.com/rooms/ez-publish

Piotrek Karaś

Tuesday 19 February 2008 10:57:27 am

Hey Bruce,

You were right, that wasn't that hard, eventually ;) Just like you wrote, "Last_" as session variables + standard redirection did the trick. Funny, I have recently reported a bug in those very lines in action.php ;)

Thanks for your help!

--
Company: mediaSELF Sp. z o.o., http://www.mediaself.pl
eZ references: http://ez.no/partners/worldwide_partners/mediaself
eZ certified developer: http://ez.no/certification/verify/272585
eZ blog: http://ez.ryba.eu

Piotrek Karaś

Tuesday 19 February 2008 11:48:22 am

It got tricky again when loggedin/anonymous user redirections came to play, but managed to shape it like this:

$http = eZHTTPTool::instance();

$currentUser = eZUser::instance();
if( !$currentUser->isLoggedIn() )
{
    $http->setSessionVariable( '$_POST_BeforeLogin', $http->attribute( 'post' ) );
    return $Module->handleError( eZError::KERNEL_ACCESS_DENIED, 'kernel' );
}

// Merge post variables and variables that were used before login
if ( $http->hasSessionVariable( 'LastPostVars' ) )
{
    $post = $http->attribute( 'post' );
    $currentPostVarNames = array_keys( $post );
    foreach ( $http->sessionVariable( 'LastPostVars' ) as $var => $value )
    {
        if ( !in_array( $var, $currentPostVarNames ) )
        {
            $http->setPostVariable( $var, $value );
        }
    }
    $http->removeSessionVariable( 'LastPostVars' );
}


$hasValidCreateAction = false;
$canCreate = false;
if( $http->hasPostVariable( 'NewButton' ) )
{
    if( $http->hasPostVariable( 'ClassIdentifier' ) )
    {
        $hasValidCreateAction = true;
        $newObjectClassIdentifier = $http->postVariable( 'ClassIdentifier' );
        $newObjectClass = eZContentClass::fetchByIdentifier( $newObjectClassIdentifier );
        $newObjectClassID = $newObjectClass->ID;

        $canCreate = true;
        if( !eZUserCreateLimitTools::canCurrentUserCreate( $newObjectClassID ) )
        {
            $canCreate = false;
        }
    }
    elseif( $http->hasPostVariable( 'ClassID' ) )
    {
        $hasValidCreateAction = true;
        $newObjectClassID = $http->hasPostVariable( 'ClassID' );
        $newObjectClass = eZContentClass::fetch( $newObjectClassID );

        $canCreate = true;
        if( !eZUserCreateLimitTools::canCurrentUserCreate( $newObjectClassID ) )
        {
            $canCreate = false;
        }
    }
}

if( $hasValidCreateAction )
{
    if( $canCreate )
    {
        $post = $http->attribute( 'post' );
        $lastPostVars = array();
        foreach ( array_keys( $post ) as $postKey )
        {
            $lastPostVars[ $postKey ] = $post[ $postKey ];
        }
        if ( count( $lastPostVars ) > 0 )
        {
            $postData = $lastPostVars;
            $http->setSessionVariable( 'LastPostVars', $lastPostVars );
        }
        $Module->redirectTo( 'content/action' );
    }
    else
    {
        $Result['content'] = $tpl->fetch( "design:createlimit/cannot_create.tpl" );
    }
}
else
{
    $Result['content'] = $tpl->fetch( "design:createlimit/lost_info.tpl" );
}

;)

--
Company: mediaSELF Sp. z o.o., http://www.mediaself.pl
eZ references: http://ez.no/partners/worldwide_partners/mediaself
eZ certified developer: http://ez.no/certification/verify/272585
eZ blog: http://ez.ryba.eu

Maxime Thomas

Friday 22 February 2008 6:11:13 am

Hi,

You can also write a module that will translate your post variables in module params. By this way, you can redirect as many time as you want saving all your post data in the url.

For example, you've got two input : val1 and val2. You can post on a specific module redirect/redirect and this one will convert 1 and 2 to your desired module mymodule/myfunction/val1/val2.

It's another point to avoid putting data in the session.

Hope it helps.

Maxime Thomas
[email protected] | www.wascou.org | http://twitter.com/wascou

Company Blog : http://www.wascou.org/eng/Company/Blog
Technical Blog : http://share.ez.no/blogs/maxime-thomas

Piotrek Karaś

Saturday 23 February 2008 5:17:31 am

Hello Maxime,

Yes, that's a good idea, even though I try to avoid putting most of POST/SESSION values in the URL, unless they are ids or identifiers. I also didn't make that clear enough, but it was a user-dedicated operation that I was after, so sessions served me just fine and secure enough.

Thanks anyways!

--
Company: mediaSELF Sp. z o.o., http://www.mediaself.pl
eZ references: http://ez.no/partners/worldwide_partners/mediaself
eZ certified developer: http://ez.no/certification/verify/272585
eZ blog: http://ez.ryba.eu