Example #1
0
 /**
  * do the plugin action
  *
  */
 function process(&$data, &$tableModel)
 {
     //jimport('joomla.mail.helper');
     $params =& $this->getParams();
     $app =& Jfactory::getApplication();
     $gcal_url = $params->get('gcal_sync_gcal_url');
     $matches = array();
     // this matches a standard GCal URL, found under the Google "Calender Details" tab, using the XML button.
     // It should match any form, for public or private ...
     // http://www.google.com/calendar/feeds/hugh.messenger%40gmail.com/public/basic
     // http://www.google.com/calendar/feeds/hugh.messenger%40gmail.com/private-3081eca2b0asdfasdf8f106ea6f63343056/basic
     $gcal_url = str_replace('/basic', '/full', $gcal_url);
     $gcal_url = preg_replace('#/private-\\w+/#', '/private/', $gcal_url);
     if (preg_match('#feeds/(.*?)/(\\w+-\\w+|\\w+)/(\\w+)#', $gcal_url, $matches)) {
         // grab the bits of the URL we need for the Zend framework call
         $gcal_user = $matches[1];
         $gcal_visibility = $matches[2];
         $gcal_projection = $matches[3];
         $gcal_email = urldecode($gcal_user);
         // grab the table model and find table name and PK
         $table =& $tableModel->getTable();
         $table_name = $table->db_table_name;
         $primary_key = $table->db_primary_key;
         $primary_key_element_long = FabrikString::safeColNameToArrayKey($table->db_primary_key);
         // for now, we have to read the table ourselves.  We can't rely on the $data passed to us
         // because it can be filtered, and we need to see all records to know if the GCal events
         // already exist in the table
         /*
         $mydata = array();
         $db = JFactory::getDBO();
         $db->setQuery("SELECT * FROM $table_name");
         $mydata[0] = $db->loadObjectList();
         */
         $db = JFactory::getDBO();
         $mydata =& $data;
         // grab all the field names to use
         $gcal_label_element_long = $params->get('gcal_sync_label_element');
         $gcal_label_element = FabrikString::shortColName($gcal_label_element_long);
         $gcal_desc_element_long = $params->get('gcal_sync_desc_element');
         $gcal_desc_element = FabrikString::shortColName($gcal_desc_element_long);
         $gcal_start_date_element_long = $params->get('gcal_sync_startdate_element');
         $gcal_start_date_element = FabrikString::shortColName($gcal_start_date_element_long);
         $gcal_end_date_element_long = $params->get('gcal_sync_enddate_element');
         $gcal_end_date_element = FabrikString::shortColName($gcal_end_date_element_long);
         $gcal_id_element_long = $params->get('gcal_sync_id_element');
         $gcal_id_element = FabrikString::shortColName($gcal_id_element_long);
         $gcal_userid_element_long = $params->get('gcal_sync_userid_element');
         $gcal_userid_element = FabrikString::shortColName($gcal_userid_element_long);
         // sanity check, make sure required elements have been specified
         if (empty($gcal_label_element_long) || empty($gcal_start_date_element_long) || empty($gcal_end_date_element_long) || empty($gcal_id_element_long)) {
             JError::raiseNotice(500, 'missing gcal data');
             return;
         }
         // if they selected a User ID element to use, see if we can find a J! user with matching email to this feed's owner
         $our_userid = 0;
         if ($gcal_userid_element_long) {
             $db->setQuery("SELECT id FROM " . $db->nameQuote('#__users') . " WHERE " . $db->nameQUote('email') . " = " . $db->Quote($gcal_email));
             $our_userid = $db->loadResult();
             // better make sure it's not NULL, in case underlying column is NOT NULL
             if (empty($our_userid)) {
                 $our_userid = 0;
             }
         }
         // include the Zend stuff
         $path = JPATH_SITE . DS . 'libraries';
         set_include_path(get_include_path() . PATH_SEPARATOR . $path);
         $path = get_include_path();
         require_once 'Zend/Loader.php';
         Zend_Loader::loadClass('Zend_Gdata');
         Zend_Loader::loadClass('Zend_Uri_Http');
         // Won't need these loaded until we add sync'ing events back to Google
         //Zend_Loader::loadClass('Zend_Gdata_AuthSub');
         //Zend_Loader::loadClass('Zend_Gdata_ClientLogin');
         Zend_Loader::loadClass('Zend_Gdata_Calendar');
         // see if they want to sync to gcal, and provided a login
         $gcal_sync_upload = $params->get('gcal_sync_upload_events', 'from');
         if ($gcal_sync_upload == 'both' || $gcal_sync_upload == 'to') {
             Zend_Loader::loadClass('Zend_Gdata_ClientLogin');
             $email = $params->get('gcal_sync_login', '');
             $passwd = $params->get('gcal_sync_passwd', '');
             try {
                 $client = Zend_Gdata_ClientLogin::getHttpClient($email, $passwd, 'cl');
             } catch (Zend_Gdata_App_CaptchaRequiredException $cre) {
                 echo 'URL of CAPTCHA image: ' . $cre->getCaptchaUrl() . "\n";
                 echo 'Token ID: ' . $cre->getCaptchaToken() . "\n";
                 return;
             } catch (Zend_Gdata_App_AuthException $ae) {
                 echo 'Problem authenticating: ' . $ae->exception() . "\n";
                 return;
             }
             $gdataCal = new Zend_Gdata_calendar($client);
         } else {
             $gdataCal = new Zend_Gdata_calendar();
         }
         // set up and execute the call to grab the feed from google
         $query = $gdataCal->newEventQuery();
         $query->setUser($gcal_user);
         $query->setVisibility($gcal_visibility);
         $query->setProjection($gcal_projection);
         $eventFeed = $gdataCal->getCalendarEventFeed($query);
         // build an array of the events from the feed, indexed by the Google ID
         $event_ids = array();
         foreach ($eventFeed as $key => $event) {
             $short_id = $this->_getGcalShortId($event->id->text);
             $gcal_event_ids[$short_id] =& $eventFeed[$key];
         }
         // run through our table data, and build an array of our events indexed by the Google ID
         // (of course not all events may have a Google ID)
         $our_event_ids = array();
         $our_upload_ids = array();
         foreach ($mydata as $gkey => $group) {
             if (is_array($group)) {
                 foreach ($group as $rkey => $row) {
                     if ($row->{$gcal_id_element_long}) {
                         $our_event_ids[$row->{$gcal_id_element_long}] =& $mydata[$gkey][$rkey];
                     } else {
                         $our_upload_ids[] =& $mydata[$gkey][$rkey];
                     }
                 }
             }
         }
         // now go through the google events id's, and process the ones which aren't in our table.
         $our_event_adds = array();
         foreach ($gcal_event_ids as $id => $event) {
             if (!array_key_exists($id, $our_event_ids)) {
                 // we don't have the ID, so add the event to our table
                 $row = array();
                 $row[$gcal_start_date_element_long] = strftime('%Y-%m-%d %H:%M:%S', strtotime($event->when[0]->startTime));
                 if ($gcal_end_date_element_long) {
                     $row[$gcal_end_date_element_long] = strftime('%Y-%m-%d %H:%M:%S', strtotime($event->when[0]->endTime));
                 }
                 $row[$gcal_label_element_long] = $event->title->text;
                 if ($gcal_desc_element_long) {
                     $row[$gcal_desc_element_long] = $event->content->text;
                 }
                 $row[$gcal_id_element_long] = $id;
                 if ($gcal_userid_element_long) {
                     $row[$gcal_userid_element_long] = $our_userid;
                 }
                 $tableModel->storeRow($row, 0);
             }
             $our_event_adds[$id] = $row;
         }
         $app->enqueueMessage(count($our_event_adds) . ' events added ');
         // if upload syncing (from us to gcal) is enabled ...
         if ($gcal_sync_upload == 'both' || $gcal_sync_upload == 'to') {
             // Grab the tzOffset.  Note that gcal want +/-XX (like -06)
             // but J! gives us +/-X (like -6) so we sprintf it to the right format
             $config =& JFactory::getConfig();
             $tzOffset = (int) $config->getValue('config.offset');
             $tzOffset = sprintf('%+03d', $tzOffset);
             // loop thru the array we built earlier of events we have that aren't in gcal
             $uploadCount = 0;
             foreach ($our_upload_ids as $id => $event) {
                 // skip if a userid element is specified, and doesn't match the owner of this gcal
                 if ($gcal_userid_element_long) {
                     if ($event->{$gcal_userid_element_long} != $our_userid) {
                         continue;
                     }
                 }
                 // now start building the gcal event structure
                 $newEvent = $gdataCal->newEventEntry();
                 $newEvent->title = $gdataCal->newTitle($event->{$gcal_label_element_long});
                 if ($gcal_desc_element_long) {
                     $newEvent->content = $gdataCal->newContent($event->{$gcal_desc_element_long});
                 } else {
                     $newEvent->content = $gdataCal->newContent($event->{$gcal_label_element_long});
                 }
                 $when = $gdataCal->newWhen();
                 // grab the start date, apply the tx offset, and format it for gcal
                 $start_date = JFactory::getDate($event->{$gcal_start_date_element_long});
                 $start_date->setOffset($tzOffset);
                 $start_fdate = $start_date->toFormat('%Y-%m-%d %H:%M:%S');
                 $date_array = explode(' ', $start_fdate);
                 $when->startTime = "{$date_array[0]}T{$date_array[1]}.000{$tzOffset}:00";
                 // we have to provide an end date for gcal, so if we don't have one,
                 // default it to start date + 1 hour
                 if (empty($gcal_end_date_element_long) || empty($event->{$gcal_end_date_element_long}) || $event->{$gcal_end_date_element_long} == '0000-00-00 00:00:00') {
                     $startstamp = strtotime($event->{$gcal_start_date_element_long});
                     $endstamp = $startstamp + 60 * 60;
                     $event->{$gcal_end_date_element_long} = strftime('%Y-%m-%d %H:%M:%S', $endstamp);
                 }
                 // grab the end date, apply the tx offset, and format it for gcal
                 $end_date = JFactory::getDate($event->{$gcal_end_date_element_long});
                 $end_date->setOffset($tzOffset);
                 $end_fdate = $end_date->toFormat('%Y-%m-%d %H:%M:%S');
                 $date_array = explode(' ', $end_fdate);
                 $when->endTime = "{$date_array[0]}T{$date_array[1]}.000{$tzOffset}:00";
                 $newEvent->when = array($when);
                 // fire off the insertEvent to gcal, catch any errors
                 try {
                     $retEvent = $gdataCal->insertEvent($newEvent, $gcal_url);
                 } catch (Zend_Gdata_App_HttpException $he) {
                     $errStr = 'Problem adding event: ' . $he->getRawResponseBody() . "\n";
                     continue;
                 }
                 $uploadCount++;
                 // insertEvent worked, so grab the gcal ID from the returned event data,
                 // and update our event record with the short version of the ID
                 $gcal_id = $this->_getGcalShortId($retEvent->id->text);
                 $our_id = $event->__pk_val;
                 $db->setQuery("\n\t\t\t\t\t\tUPDATE {$table_name}\n\t\t\t\t\t\tSET {$gcal_id_element} = " . $db->Quote($gcal_id) . "\n\t\t\t\t\t\tWHERE {$primary_key} = " . (int) $our_id);
                 $db->query();
             }
             $app->enqueueMessage($uploadCount . ' events uploaded to GCal');
         }
     } else {
         JError::raiseNotice(500, 'Incorrect url');
     }
 }
Example #2
0
 private function _process(&$params, &$formModel)
 {
     $app =& Jfactory::getApplication();
     $gcal_url = $params->get('gcal_url', '');
     $matches = array();
     // this matches a standard GCal URL, found under the Google "Calender Details" tab, using the XML button.
     // Because we are adding events, we need the private URL, and it needs to end in /full
     // But the default URL Google show when you look at setting is the /basic ...
     // http://www.google.com/calendar/feeds/hugh.messenger%40gmail.com/private-3081eca2b0asdfasdf8f106ea6f63343056/basic
     // So we need to replace /basic with /full before we do anything.
     // Also need to remove the magic cookie, if present.
     $gcal_url = str_replace('/basic', '/full', $gcal_url);
     $gcal_url = preg_replace('#/private-\\w+/#', '/private/', $gcal_url);
     if (preg_match('#feeds/(.*?)/(\\w+-\\w+|\\w+)/(\\w+)#', $gcal_url, $matches)) {
         // grab the bits of the URL we need for the Zend framework call
         $gcal_user = $matches[1];
         $gcal_visibility = $matches[2];
         $gcal_projection = $matches[3];
         $gcal_email = urldecode($gcal_user);
         // grab all the field names to use
         /*
         $gcal_label_element_long = $params->get('gcal_label_element');
         $gcal_label_element = FabrikString::shortColName($gcal_label_element_long);
         $gcal_desc_element_long = $params->get('gcal_desc_element');
         $gcal_desc_element = FabrikString::shortColName($gcal_desc_element_long);
         $gcal_start_date_element_long = $params->get('gcal_start_date_element');
         $gcal_start_date_element = FabrikString::shortColName($gcal_start_date_element_long);
         $gcal_end_date_element_long = $params->get('gcal_end_date_element');
         $gcal_end_date_element = FabrikString::shortColName($gcal_end_date_element_long);
         $gcal_id_element_long = $params->get('gcal_id_element');
         $gcal_id_element = FabrikString::shortColName($gcal_id_element_long);
         $email = $params->get('gcal_login', '');
         $passwd = $params->get('gcal_passwd', '');
         */
         $data =& $formModel->_formData;
         $email = $params->get('gcal_login', '');
         $passwd = $params->get('gcal_passwd', '');
         $gcal_label = $this->getFieldValue($params, 'gcal_label_element', $data);
         $gcal_desc = $this->getFieldValue($params, 'gcal_desc_element', $data);
         $gcal_start_date = $this->getFieldValue($params, 'gcal_start_date_element', $data);
         $gcal_end_date = $this->getFieldValue($params, 'gcal_end_date_element', $data);
         $gcal_event_id = $this->getFieldValue($params, 'gcal_id_element', $data);
         $gcal_id_element = FabrikString::shortColName($this->getFieldName($params, 'gcal_id_element'));
         // sanity check, make sure required elements have been specified
         if (empty($email) || empty($passwd) || empty($gcal_label) || empty($gcal_start_date) || empty($gcal_id_element)) {
             JError::raiseNotice(500, 'missing gcal data');
             return;
         }
         // grab the table model and find table name and PK
         $tableModel =& $formModel->getTableModel();
         $table =& $tableModel->getTable();
         $table_name = $table->db_table_name;
         $primary_key = $tableModel->_shortKey(null, true);
         $db =& $tableModel->getDb();
         // include the Zend stuff
         $path = JPATH_SITE . DS . 'libraries';
         set_include_path(get_include_path() . PATH_SEPARATOR . $path);
         $path = get_include_path();
         require_once 'Zend/Loader.php';
         Zend_Loader::loadClass('Zend_Gdata');
         Zend_Loader::loadClass('Zend_Uri_Http');
         Zend_Loader::loadClass('Zend_Gdata_Calendar');
         Zend_Loader::loadClass('Zend_Gdata_ClientLogin');
         try {
             $client = Zend_Gdata_ClientLogin::getHttpClient($email, $passwd, 'cl');
         } catch (Zend_Gdata_App_CaptchaRequiredException $cre) {
             echo 'URL of CAPTCHA image: ' . $cre->getCaptchaUrl() . "\n";
             echo 'Token ID: ' . $cre->getCaptchaToken() . "\n";
             return;
         } catch (Zend_Gdata_App_AuthException $ae) {
             echo 'Problem authenticating: ' . $ae->exception() . "\n";
             return;
         }
         $gdataCal = new Zend_Gdata_calendar($client);
         // set up query
         $query = $gdataCal->newEventQuery();
         $query->setUser($gcal_user);
         $query->setVisibility($gcal_visibility);
         $query->setProjection($gcal_projection);
         if (!empty($gcal_event_id)) {
             $query->setEvent($gcal_event_id);
             try {
                 $event = $gdataCal->getCalendarEventEntry($query);
             } catch (Zend_Gdata_App_Exception $e) {
                 //echo "Error: " . $e->getMessage();
                 JError::raiseNotice(500, 'Error retrieving GCal event: ' . $e->getMessage());
                 return;
             }
         } else {
             $event = $gdataCal->newEventEntry();
         }
         // Grab the tzOffset.  No need to offset dates from form, as they are already offset,
         // but need it for the gcal date string format.
         // Note that gcal want +/-XX (like -06)
         // but J! gives us +/-X (like -6) so we sprintf it to the right format
         $config =& JFactory::getConfig();
         $tzOffset = (int) $config->getValue('config.offset');
         $tzOffset = sprintf('%+03d', $tzOffset);
         $event->title = $gdataCal->newTitle($gcal_label);
         if (!empty($gcal_desc)) {
             $event->content = $gdataCal->newContent($gcal_desc);
         } else {
             $event->content = $gdataCal->newContent($gcal_label);
         }
         $when = $gdataCal->newWhen();
         // grab the start date, apply the tx offset, and format it for gcal
         $start_date = JFactory::getDate($gcal_start_date);
         $start_date->setOffset($tzOffset);
         $start_fdate = $start_date->toFormat('%Y-%m-%d %H:%M:%S');
         $date_array = explode(' ', $start_fdate);
         $when->startTime = "{$date_array[0]}T{$date_array[1]}.000{$tzOffset}:00";
         // we have to provide an end date for gcal, so if we don't have one,
         // default it to start date + 1 hour
         if (empty($gcal_end_date) || $gcal_end_date == '0000-00-00 00:00:00') {
             $startstamp = strtotime($gcal_start_date);
             $endstamp = $startstamp + 60 * 60;
             $gcal_end_date = strftime('%Y-%m-%d %H:%M:%S', $endstamp);
         }
         // grab the end date, apply the tx offset, and format it for gcal
         $end_date = JFactory::getDate($gcal_end_date);
         $end_date->setOffset($tzOffset);
         $end_fdate = $end_date->toFormat('%Y-%m-%d %H:%M:%S');
         $date_array = explode(' ', $end_fdate);
         $when->endTime = "{$date_array[0]}T{$date_array[1]}.000{$tzOffset}:00";
         $event->when = array($when);
         if (!empty($gcal_event_id)) {
             try {
                 $event->save();
             } catch (Zend_Gdata_App_Exception $e) {
                 JError::raiseNotice(500, 'Error saving GCal event: ' . $e->getMessage());
                 return;
             }
         } else {
             // fire off the insertEvent to gcal, catch any errors
             try {
                 $retEvent = $gdataCal->insertEvent($event, $gcal_url);
             } catch (Zend_Gdata_App_HttpException $he) {
                 JError::raiseNotice(500, 'Problem adding event: ' . $he->getRawResponseBody());
                 return;
             }
             // insertEvent worked, so grab the gcal ID from the returned event data,
             // and update our event record with the short version of the ID
             $gcal_event_id = $this->_getGcalShortId($retEvent->id->text);
         }
         $our_id = $formModel->_formData[$primary_key];
         if (!empty($our_id)) {
             $db->setQuery("\n\t\t\t\t\t\t\tUPDATE {$table_name}\n\t\t\t\t\t\t\tSET {$gcal_id_element} = " . $db->Quote($gcal_event_id) . "\n\t\t\t\t\t\t\tWHERE {$primary_key} = " . $db->Quote($our_id));
             $db->query();
         } else {
             JError::raiseNotice(500, 'No rowid for GCal ID update!');
         }
         $app->enqueueMessage('Event syncronized with GCal');
     } else {
         JError::raiseNotice(500, 'Incorrect GCal url');
     }
 }