Log in

View Full Version : Confused about datamanagers


Antivirus
06-03-2007, 05:20 PM
I have been looking at datamanagers and trying to write a custom one based upon Alan@CIT's article (https://vborg.vbsupport.ru/showthread.php?t=119376) .

I have been looking at the simplest datamanager in vbulletin which seems to be class_dm_announcement.php and have the following question which i hope to have answered by someone as the following issue makes no sense to me...

In looking at the class file, the $validfields array is as follows:

var $validfields = array(
'announcementid' => array(TYPE_UINT, REQ_INCR, 'return ($data > 0);'),
'forumid' => array(TYPE_INT, REQ_YES, VF_METHOD),
'userid' => array(TYPE_UINT, REQ_YES, VF_METHOD),
'title' => array(TYPE_STR, REQ_YES, 'return ($data != \'\');'),
'pagetext' => array(TYPE_STR, REQ_YES, 'return ($data != \'\');'),
'startdate' => array(TYPE_UNIXTIME, REQ_YES),
'enddate' => array(TYPE_UNIXTIME, REQ_YES),
'views' => array(TYPE_UINT, REQ_NO),
'allowhtml' => array(TYPE_BOOL, REQ_NO),
'allowbbcode' => array(TYPE_BOOL, REQ_NO),
'allowsmilies' => array(TYPE_BOOL, REQ_NO),
'announcementoptions' => array(TYPE_UINT, REQ_NO)
);


The table which is declared is

var $table = 'announcement';




And the fields in the table `announcement` are as follows:

announcementid
title
userid
startdate
enddate
pagetext
forumid
views
announcementoptions


Now, the thing that is confusing me is the following...

Since the class needs considers 'allowhtml', 'allowbbcode', and 'allowsmilies' valid fields, but since the fields do not exist within the announcement table, how does the class use these fields to get the data into the post table?

Also, how does the class know to utilize any other table than announcement?:confused:

Eikinskjaldi
06-03-2007, 11:05 PM
Now, the thing that is confusing me is the following...

Since the class needs considers 'allowhtml', 'allowbbcode', and 'allowsmilies' valid fields, but since the fields do not exist within the announcement table, how does the class use these fields to get the data into the post table?

Also, how does the class know to utilize any other table than announcement?:confused:

Those kinds of options are stored in a single bit field (announcement options)

in pseudo code:

for each key, val in bitfield_type_of_option in array
$forum_manager->set_bitfield('announcement',key, val)



try starting with this...

var $validfields = array(
'announcementid' => array(TYPE_UINT, REQ_INCR, 'return ($data > 0);'),
'forumid' => array(TYPE_INT, REQ_YES, VF_METHOD),
'userid' => array(TYPE_UINT, REQ_YES, VF_METHOD),
'title' => array(TYPE_STR, REQ_YES, 'return ($data != \'\');'),
'pagetext' => array(TYPE_STR, REQ_YES, 'return ($data != \'\');'),
'startdate' => array(TYPE_UNIXTIME, REQ_YES),
'enddate' => array(TYPE_UNIXTIME, REQ_YES),
'views' => array(TYPE_UINT, REQ_NO),
'announcementoptions' => array(
'allowhtml' => 0,
'allowbbcode' => 1,
'allowsmilies' => 0,
)
);

Antivirus
06-04-2007, 02:57 PM
ah, i didn't notice those being in bitfields. Thanks for pointing that out.

Is it possible then to use a datamanager to save data into 2 different tables at the same time? Would the primary info be inserted into the table through the class's normal functions of class vB_DataManager, then the repeating data (1 or more details related to the primary data) be inserted by including the actual query info within the class vB_DataManager_Multiple?

Here's the class in progress:

if (!class_exists('vB_DataManager'))
{
exit;
}

/**
* Class to do data save/delete operations for FEEDBACK
*
*/
class vB_DataManager_Feedback extends vB_DataManager
{
/**
* Array of recognised and required fields for feedbacks, and their types
*
* @var array
*/
var $validfields = array(
// following data is for table scst_fb
'fbid' => array(TYPE_UINT, REQ_INCR, 'verify_nonzero'),
'title' => array(TYPE_STR, REQ_YES, 'return ($data != \'\');'),
'userid' => array(TYPE_UINT, REQ_YES, VF_METHOD),
'taskid' => array(TYPE_UINT, REQ_YES, VF_METHOD),
'eventid' => array(TYPE_UINT, REQ_YES, VF_METHOD),
// following data is for scst_fbposts (1 or more records linked to above by way of field fbid)
'fbid' => array(TYPE_UINT, REQ_YES), // same fbid as above for each record
'userid' => array(TYPE_UINT, REQ_YES, VF_METHOD), // same userid as above for each record
'fbscore' => array(TYPE_UINT, REQ_NO),
'postid' => array(TYPE_UINT, REQ_INCR, 'verify_nonzero'),
'statusid' => array(TYPE_UINT, REQ_NO),
'teamid' => array(TYPE_UINT, REQ_NO),
'dateline' => array(TYPE_UNIXTIME, REQ_YES),
'infraction' => array(TYPE_UINT, REQ_NO),
'allowsmile' => array(TYPE_BOOL, REQ_NO),
'showsignature' => array(TYPE_BOOL, REQ_NO),
'hide' => array(TYPE_BOOL, REQ_NO),
'score' => array(TYPE_UINT, REQ_NO),
'attach' => array(TYPE_UINT, REQ_NO),
'pagetext' => array(TYPE_STR, REQ_YES, 'return ($data != \'\');'),
'pagetexted' => array(TYPE_STR, REQ_NO, 'return ($data != \'\');'),
'url' => array(TYPE_STR, REQ_NO, 'verify_link')
);

/**
* The main table this class deals with
*
* @var string
*/
var $table = 'scst_fb';

/**
* Condition for update query
*
* @var array
*/
var $condition_construct = array('fbid = %1$d', 'fbid');

/**
* Constructor - checks that the registry object has been passed correctly.
*
* @param vB_Registry Instance of the vBulletin data registry object - expected to have the database object as one of its $this->db member.
* @param integer One of the ERRTYPE_x constants
*/
function vB_DataManager_Feedback(&$registry, $errtype = ERRTYPE_STANDARD)
{
parent::vB_DataManager($registry, $errtype);

}

/**
* Verifies that the specified taskid is valid
*
* @param integer Task ID
*
* @return boolean
*/
function verify_taskid(&$taskid)
{
$db =& $this->registry->db;

$taskresult = $db->query_first("SELECT FROM " . TABLE_PREFIX . "scst_task WHERE taskid = $taskid");

if ($taskid == $taskresult['taskid'])
{
return true;
}
else
{
$this->error('invalid_task_specified');
return false;
}
}

/**
* Verifies that the specified eventid is valid
*
* @param integer Event ID
*
* @return boolean
*/
function verify_eventid(&$eventid)
{
$db =& $this->registry->db;

$eventresult = $db->query_first("SELECT FROM " . TABLE_PREFIX . "scst_event WHERE eventid = $eventid");

if ($eventid == $eventresult['eventid'])
{
return true;
}
else
{
$this->error('invalid_event_specified');
return false;
}
}

/**
* Any checks to run immediately before saving. If returning false, the save will not take place.
*
* @param boolean Do the query?
*
* @return boolean True on success; false if an error occurred
*/
function pre_save($doquery = true)
{
if ($this->presave_called !== null)
{
return $this->presave_called;
}

$return_value = true;

$this->presave_called = $return_value;
return $return_value;
}

/**
* Additional data to update after a delete call (such as denormalized values in other tables).
*
* @param boolean Do the query?
*/
function post_delete($doquery = true)
{
$fbid = intval($this->existing['fbid']);
$db =& $this->registry->db;

$db->query_write("DELETE FROM " . TABLE_PREFIX . "scst_fbposts WHERE fbid = $fbid");

return true;
}
}



I think it has something to do with placing just the repeating data for each record for secondary table into an array within the var $children. Is that all I need to do then? Where do I identify the secondary var $table?

:confused:

Eikinskjaldi
06-05-2007, 02:06 AM
The idea of a data manager is that it...manages data. It takes a request, such as building a forum, and updates all the tables and fields and whatever so that the update takes place. Note for instance that the vb forum datamanager does something to update the datastore (I don't know what, I have never looked).

In summary then your one data manager should manage all the data.

If the secondary table is fixed, just hard wire it into your code.

/**
* The main table this class deals with
*
* @var string
*/
var $table = 'scst_fb';

/**
* and here is my other table
* @var string
*/
var $otherttable = 'other table';


Then just build up your code to do whatever it is that needs to be done. You can always add extra setters to include subsidiary data if required.

Antivirus
06-05-2007, 07:59 PM
Forgive me, I couldn't find any info on the datastore within class_dm_forum.php but I do see that it does update the forum table (for applying forum password to child forums) within function post_save_each so i know i'm on the right track - i just have to keep trying to understand how the datamanager works. OOP is still somewhat confusing to me, i usually write straight code, but the project i am working on now is at a point where I need to use a DM to simplify things, so until i can grasp it well enough i'll just keep asking questions, reading the vbulletin manual Appendix 4, and experimenting, thanks!

Dismounted
06-06-2007, 09:25 AM
Have a read through class_dm.php, it will give you some ideas.

Antivirus
06-07-2007, 10:38 AM
yeah, I have been looking at that. It seems that class_dm.php is the base class, and in any datamanagers that "extend" the main class, if there's a function with the same name as the one in the main class, override it with the new function, and also declares new functions for doing anything unique within the new class.

I have creades some simple dms for handling things with just a few fields, but I think for my situation i explained above, it would be easier to create 2 different datamanagers, one for the main record, and another to handle the related records because even after looking at class_dm.php for an entire day (along with just about every other dm, I cant figure out how the class knows to loop through related records , i.e. the way class_multiple is called for the specific multiple records.