Forums / General / Poll unique vote options - summary and questions

Poll unique vote options - summary and questions

Author Message

Piotrek Karaś

Tuesday 30 October 2007 11:58:52 am

I have just gone through the forum and documentation looking for some details on poll configuration options. What I am basically looking for is any confirmed information on how the eZ Publish poll (info collector) deals with user uniqueness.

I know, that in order for information collection to collect data from users uniquely, we set up:

CollectionUserDataList[poll]=unique

However, the above setting will most probably behave differently depending on whether anonymous votes are allowed or not:

CollectAnonymousDataList[]
CollectAnonymousDataList[poll]=enabled/disabled

I suspect, that if enabled, eZ Publish will use session data/cookies to prevent double votes. <b>What exactly does it look like when only the logged-in users are allowed to vote?</b> I did some testing and eZ Publish doesn't seem to care about the session data and cookies in such case anymore. The question remains: <b>is that permanent? Will my users ever be able to vote again (without having to purge the collected information)? Any config-based way of setting up a time-based block rather than a permanent block?</b>

Wouldn't it be great to have an additional, modified unique mode with a time constrain?

--
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 30 October 2007 1:36:16 pm

Ok, I took some time and since kernel classes will have the ability of being overwritten soon, decided to dig a bit. The functionality I suggested above turned out to be comparatively easy to implement. I hope some of you take a look at it and if this doesn't violate anything, I'll add this little functionality as a suggestion - I believe many people may find it useful. I hope I didn't reinvent the wheel here ;)

The purpose is to let registered and logged-in users to vote in a poll, but only once over a given period of time.

I started with the settings file, where I declared a <b>new mode</b>:
<i>/settings/override/collect.ini.append.php</i>

CollectionUserDataList[poll]=timeunique

This will not work unless we extend the array a bit deeper:
<i>/kernel/classes/ezinformationcollection.php</i>

static function userDataHandling( $contentObject ) {
(...)
if ( !in_array( $userData, array( 'multiple', 'unique', 'overwrite', 'timeunique' ) ) )
$userData = 'unique';
(...)
}

In the same file we add a new fetching method dedicated for our new mode:

static function fetchByUserIdentifierTimeUnique( $userIdentifier, $contentObjectID = false, $asObject = true, $timeLimit = false ) {
 if ( $timeLimit == false)
  $timeLimit = time() - 86400;
 $conditions = array( 'user_identifier' => $userIdentifier, 'created' => array( '>=', $timeLimit ) );
 if ( $contentObjectID )
  $conditions['contentobject_id'] = $contentObjectID;
 return eZPersistentObject::fetchObject( eZInformationCollection::definition(), null, $conditions, $asObject );
}

All we've got to do now is to teach the content module to use our new fetching method:
<i>/kernel/content/collectinformation.php</i>

(...)
 $newCollection = false;
 $collection = false;
 $userDataHandling = eZInformationCollection::userDataHandling( $object );

 if ( $userDataHandling == 'unique' or
  $userDataHandling == 'overwrite' )
  $collection = eZInformationCollection::fetchByUserIdentifier( eZInformationCollection::currentUserIdentifier(), $object->attribute( 'id' ) );

 if ( $userDataHandling == 'timeunique' ) {
  $collectionTimeLimit = time() - 600; // you can vote every ten minutes
  $collection = eZInformationCollection::fetchByUserIdentifierTimeUnique( eZInformationCollection::currentUserIdentifier(), $object->attribute( 'id' ), $collectionTimeLimit);
}

 if ( ( !$isLoggedIn and !$allowAnonymous ) or
  ( $userDataHandling == 'unique' and $collection ) or 
  ( $userDataHandling == 'timeunique' and $collection) )
  {
(...)

And few lines below we can provide a new error variable for the template, or extend the existing one:

(...)
$tpl->setVariable( 'error_existing_data', ( ( $userDataHandling == 'unique' and $collection ) or ( $userDataHandling == 'timeunique' and $collection ) ) );
(...)

Of course, it would still be nice to move the time declaration (<i>time()-600</i>) out to the settings file and make it possible to declare it separately for each class.

I guess that also answers my own questions, at least some of them ;)

--
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