addonManager() public static method

Get the addon manager.
public static addonManager ( ) : AddonManager
return Vanilla\AddonManager
Example #1
0
 /**
  *
  */
 public function __construct()
 {
     $this->Dispatcher = new Gdn_Dispatcher(Gdn::addonManager());
     $EnabledApplications = Gdn::config('EnabledApplications');
     $this->Dispatcher->enabledApplicationFolders($EnabledApplications);
     $this->Dispatcher->passProperty('EnabledApplications', $EnabledApplications);
 }
 /**
  * Find available social plugins.
  *
  * @return array|mixed
  * @throws Exception
  */
 protected function getConnections()
 {
     $this->fireEvent('GetConnections');
     $connections = [];
     $addons = Gdn::addonManager()->lookupAllByType(\Vanilla\Addon::TYPE_ADDON);
     foreach ($addons as $addonName => $addon) {
         $addonInfo = $addon->getInfo();
         // Limit to designated social addons.
         if (!array_key_exists('socialConnect', $addonInfo)) {
             continue;
         }
         // See if addon is enabled.
         $isEnabled = Gdn::addonManager()->isEnabled($addonName, \Vanilla\Addon::TYPE_ADDON);
         setValue('enabled', $addonInfo, $isEnabled);
         // See if we can detect whether connection is configured.
         $isConfigured = null;
         if ($isEnabled) {
             $pluginInstance = Gdn::pluginManager()->getPluginInstance($addonName, Gdn_PluginManager::ACCESS_PLUGINNAME);
             if (method_exists($pluginInstance, 'isConfigured')) {
                 $isConfigured = $pluginInstance->isConfigured();
             }
         }
         setValue('configured', $addonInfo, $isConfigured);
         // Add the connection.
         $connections[$addonName] = $addonInfo;
     }
     return $connections;
 }
Example #3
0
 /**
  * QnAPlugin constructor.
  */
 public function __construct()
 {
     parent::__construct();
     if (Gdn::addonManager()->isEnabled('Reactions', \Vanilla\Addon::TYPE_ADDON) && c('Plugins.QnA.Reactions', true)) {
         $this->Reactions = true;
     }
     if ((Gdn::addonManager()->isEnabled('Reputation', \Vanilla\Addon::TYPE_ADDON) || Gdn::addonManager()->isEnabled('badges', \Vanilla\Addon::TYPE_ADDON)) && c('Plugins.QnA.Badges', true)) {
         $this->Badges = true;
     }
 }
 public function enablePlugin($pluginName, $filter = 'all')
 {
     if (!Gdn::request()->isAuthenticatedPostBack(true)) {
         throw new Exception('Requires POST', 405);
     }
     $this->permission('Garden.Settings.Manage');
     $action = 'none';
     if ($filter == 'disabled') {
         $action = 'SlideUp';
     }
     $addon = Gdn::addonManager()->lookupAddon($pluginName);
     try {
         $validation = new Gdn_Validation();
         if (!Gdn::pluginManager()->enablePlugin($pluginName, $validation)) {
             $this->Form->setValidationResults($validation->results());
         } else {
             Gdn_LibraryMap::ClearCache();
             $this->informMessage(sprintf(t('%s Enabled.'), val('name', $addon->getInfo(), t('Plugin'))));
         }
         $this->EventArguments['PluginName'] = $pluginName;
         $this->EventArguments['Validation'] = $validation;
         $this->fireEvent('AfterEnablePlugin');
     } catch (Exception $e) {
         $this->Form->addError($e);
     }
     $this->handleAddonToggle($pluginName, $addon->getInfo(), 'plugins', true, $filter, $action);
 }
Example #5
0
 /**
  * Parses the query string looking for supplied request parameters.
  *
  * Places anything useful into this object's Controller properties.
  *
  * @param Gdn_Request $request The request to analyze.
  */
 private function analyzeRequest($request)
 {
     // Initialize the result of our request.
     $result = ['method' => $request->requestMethod(), 'path' => $request->path(), 'addon' => null, 'controller' => '', 'controllerMethod' => '', 'pathArgs' => [], 'query' => array_change_key_case($request->get()), 'post' => $request->post()];
     // Here is the basic format of a request:
     // [/application]/controller[/method[.json|.xml]]/argn|argn=valn
     // Here are some examples of what this method could/would receive:
     // /application/controller/method/argn
     // /controller/method/argn
     // /application/controller/argn
     // /controller/argn
     // /controller
     $parts = explode('/', str_replace('\\', '/', $request->path()));
     // Decode path parts at the dispatcher level.
     array_walk($parts, function (&$value) {
         $value = rawurldecode($value);
     });
     // Parse the file extension.
     list($parts, $deliveryMethod) = $this->parseDeliveryMethod($parts);
     // Set some special properties based on the deliver method.
     $deliveryType = $this->deliveryType;
     switch ($deliveryMethod) {
         case DELIVERY_METHOD_JSON:
         case DELIVERY_METHOD_XML:
             $deliveryType = DELIVERY_TYPE_DATA;
             break;
         case DELIVERY_METHOD_ATOM:
         case DELIVERY_METHOD_RSS:
             $result['syndicationMethod'] = DELIVERY_METHOD_RSS;
             //$deliveryMethod;
             break;
         case DELIVERY_METHOD_TEXT:
             $deliveryType = DELIVERY_TYPE_VIEW;
             break;
     }
     // An explicitly passed delivery type/method overrides the default.
     $result['deliveryMethod'] = self::requestVal('DeliveryMethod', $result['query'], $result['post'], $deliveryMethod ?: $this->deliveryMethod);
     $result['deliveryType'] = self::requestVal('DeliveryType', $result['query'], $result['post'], $deliveryType);
     // Figure out the controller.
     list($controllerName, $pathArgs) = $this->findController($parts);
     $result['pathArgs'] = $pathArgs;
     if ($controllerName) {
         // The controller was found based on the path.
         $result['controller'] = $controllerName;
     } elseif (Gdn::pluginManager()->hasNewMethod('RootController', val(0, $parts))) {
         // There is a plugin defining a new root method.
         $result['controller'] = 'RootController';
     } else {
         // No controller was found, fire a not found event.
         // TODO: Move this outside this method.
         $this->EventArguments['Handled'] = false;
         $Handled =& $this->EventArguments['Handled'];
         $this->fireEvent('NotFound');
         if (!$Handled) {
             safeHeader("HTTP/1.1 404 Not Found");
             return $this->passData('Reason', 'controller_notfound')->analyzeRequest($request->withRoute('Default404'));
         }
         return;
     }
     // A controller has been found. Find the addon that manages it.
     $addon = Gdn::addonManager()->lookupByClassname($result['controller']);
     // The result should be properly set now. Set the legacy properties though.
     if ($addon) {
         $result['addon'] = $addon;
         $this->applicationFolder = stringBeginsWith($addon->getSubdir(), 'applications/', true, true);
     }
     $this->ControllerName = $result['controller'];
     $this->controllerMethodArgs = [];
     $this->syndicationMethod = val('syndicationMethod', $result, SYNDICATION_NONE);
     $this->deliveryMethod = $result['deliveryMethod'];
     return $result;
 }
Example #6
0
/**
 * Converts addon info into a media item.
 *
 * @param $addonName
 * @param $addonInfo
 * @param $isEnabled
 * @param $addonType
 * @param $filter
 */
function writeAddonMedia($addonName, $addonInfo, $isEnabled, $addonType, $filter)
{
    $capitalCaseSheme = new \Vanilla\Utility\CapitalCaseScheme();
    $addonInfo = $capitalCaseSheme->convertArrayKeys($addonInfo, ['RegisterPermissions']);
    $screenName = Gdn_Format::display(val('Name', $addonInfo, $addonName));
    $description = Gdn_Format::html(t(val('Name', $addonInfo, $addonName) . ' Description', val('Description', $addonInfo, '')));
    $id = Gdn_Format::url($addonName) . '-addon';
    $media = new MediaItemModule($screenName, '', $description, 'li', ['id' => $id]);
    $media->setView('media-addon');
    // Icon
    $addon = Gdn::addonManager()->lookupAddon($addonName);
    $iconPath = '';
    if ($addon) {
        $iconPath = $addon->getIcon();
    }
    if (!$iconPath) {
        $iconPath = val('IconUrl', $addonInfo, 'applications/dashboard/design/images/addon-placeholder.png');
    }
    $media->setImage($iconPath);
    // Settings button
    $settingsUrl = $isEnabled ? val('SettingsUrl', $addonInfo, '') : '';
    $settingsPopupClass = val('UsePopupSettings', $addonInfo, true) ? ' js-modal' : '';
    if ($settingsUrl != '') {
        $attr['class'] = 'btn btn-icon-border' . $settingsPopupClass;
        $attr['aria-label'] = sprintf(t('Settings for %s'), $screenName);
        $attr['data-reload-page-on-save'] = false;
        $media->addButton(dashboardSymbol('settings'), $settingsUrl, $attr);
    }
    // Toggle
    if ($addonType === 'locales') {
        $action = $isEnabled ? 'disable' : 'enable';
    } else {
        $action = $filter;
    }
    if ($isEnabled) {
        $label = sprintf(t('Disable %s'), $screenName);
    } else {
        $label = sprintf(t('Enable %s'), $screenName);
    }
    $url = '/settings/' . $addonType . '/' . $action . '/' . $addonName;
    $media->setToggle(slugify($addonName), $isEnabled, $url, $label);
    // Meta
    $info = [];
    // Requirements
    $requiredApplications = val('RequiredApplications', $addonInfo, false);
    $requiredPlugins = val('RequiredPlugins', $addonInfo, false);
    $requirements = [];
    if (is_array($requiredApplications)) {
        foreach ($requiredApplications as $requiredApplication => $versionInfo) {
            $requirements[] = sprintf(t('%1$s Version %2$s'), $requiredApplication, $versionInfo);
        }
    }
    if (is_array($requiredPlugins)) {
        foreach ($requiredPlugins as $requiredPlugin => $versionInfo) {
            $requirements[] = sprintf(t('%1$s Version %2$s'), $requiredPlugin, $versionInfo);
        }
    }
    if (!empty($requirements)) {
        $requirementsMeta = sprintf(t('Requires: %s'), implode(', ', $requirements));
        $info[] = $requirementsMeta;
    }
    // Authors
    $author = val('Author', $addonInfo, '');
    $authors = [];
    // Check if singular author is set
    if ($author) {
        $authorUrl = val('AuthorUrl', $addonInfo, '');
        if ($authorUrl) {
            $authors[] = anchor($author, $authorUrl);
        } else {
            $authors[] = $author;
        }
    }
    // Check for multiple authors
    foreach (val('Authors', $addonInfo, []) as $author) {
        if (val('Homepage', $author)) {
            $authors[] = anchor(val('Name', $author), val('Homepage', $author));
        } else {
            $authors[] = val('Name', $author);
        }
    }
    if ($authors) {
        $authors = implode(', ', $authors);
        $info[] = sprintf(t('Created by %s'), $authors);
    }
    // Version Info
    $version = Gdn_Format::display(val('Version', $addonInfo, ''));
    $newVersion = val('NewVersion', $addonInfo, '');
    $upgrade = $newVersion != '' && version_compare($newVersion, $version, '>');
    if ($version != '') {
        $info[] = sprintf(t('Version %s'), $version);
    }
    $pluginUrl = val('PluginUrl', $addonInfo, '');
    if ($upgrade && $pluginUrl) {
        $info[] = anchor(printf(t('%1$s version %2$s is available.'), $screenName, $newVersion), combinePaths(array($pluginUrl, 'find', urlencode($screenName)), '/'));
    }
    if ($pluginUrl != '') {
        $info[] = anchor(t('Visit Site'), $pluginUrl);
    }
    // Extra meta in addon array
    if ($meta = val('Meta', $addonInfo)) {
        foreach ($meta as $key => $value) {
            if (is_numeric($key)) {
                $info[] = $value;
            } else {
                $info[] = t($key) . ': ' . $value;
            }
        }
    }
    $media->setMeta($info);
    echo $media;
}
Example #7
0
 /**
  * Generate an e-tag for the application from the versions of all of its enabled applications/plugins.
  *
  * @return string etag
  **/
 public static function eTag()
 {
     $data = [];
     $data['vanilla-core-' . APPLICATION_VERSION] = true;
     // Look through the enabled addons.
     /* @var Addon $addon */
     foreach (Gdn::addonManager()->getEnabled() as $addon) {
         if ($addon->getType() == Addon::TYPE_THEME) {
             // Themes have to figured out separately.
             continue;
         }
         $key = $addon->getKey();
         $version = $addon->getVersion();
         $type = $addon->getType();
         $data[strtolower("{$key}-{$type}-{$version}")] = true;
     }
     // Add the desktop theme version.
     $themes = ['' => Gdn::addonManager()->lookupTheme(Gdn::themeManager()->desktopTheme()), 'Mobile' => Gdn::addonManager()->lookupTheme(Gdn::themeManager()->mobileTheme())];
     foreach ($themes as $optionsPx => $theme) {
         if (!$theme instanceof Addon) {
             continue;
         }
         $data[$theme->getKey() . '-theme-' . $theme->getVersion()] = true;
         // Look for theme options.
         $options = c("Garden.{$optionsPx}ThemeOptions");
         if (!empty($options)) {
             $data[valr('Styles.Value', $options)] = true;
         }
     }
     $info = Gdn::themeManager()->getThemeInfo(Gdn::themeManager()->desktopTheme());
     if (!empty($info)) {
         $version = val('Version', $info, 'v0');
         $data[strtolower("{$info['Index']}-theme-{$version}")] = true;
         if (Gdn::controller()->Theme && Gdn::controller()->ThemeOptions) {
             $filenames = valr('Styles.Value', Gdn::controller()->ThemeOptions);
             $data[$filenames] = true;
         }
     }
     // Add the mobile theme version.
     $info = Gdn::themeManager()->getThemeInfo(Gdn::themeManager()->mobileTheme());
     if (!empty($info)) {
         $version = val('Version', $info, 'v0');
         $data[strtolower("{$info['Index']}-theme-{$version}")] = true;
     }
     Gdn::pluginManager()->EventArguments['ETagData'] =& $data;
     $suffix = '';
     Gdn::pluginManager()->EventArguments['Suffix'] =& $suffix;
     Gdn::pluginManager()->fireAs('AssetModel')->fireEvent('GenerateETag');
     unset(Gdn::pluginManager()->EventArguments['ETagData']);
     ksort($data);
     $result = substr(md5(implode(',', array_keys($data))), 0, 8) . $suffix;
     return $result;
 }
 /**
  * Handle toggling this version of embedding on and off. Take care of disabling the other version of embed (the old plugin).
  *
  * @param string $Toggle
  * @param string $TransientKey
  * @return boolean
  * @throws Gdn_UserException
  */
 private function toggle($Toggle = '', $TransientKey = '')
 {
     if (in_array($Toggle, array('enable', 'disable')) && Gdn::session()->validateTransientKey($TransientKey)) {
         if ($Toggle == 'enable' && Gdn::addonManager()->isEnabled('embedvanilla', \Vanilla\Addon::TYPE_ADDON)) {
             throw new Gdn_UserException('You must disable the "Embed Vanilla" plugin before continuing.');
         }
         // Do the toggle
         saveToConfig('Garden.Embed.Allow', $Toggle == 'enable' ? true : false);
         return true;
     }
     return false;
 }
 /**
  * Display flood control options.
  *
  * @since 2.0.0
  * @access public
  */
 public function floodControl()
 {
     // Check permission
     $this->permission('Garden.Settings.Manage');
     // Display options
     $this->title(t('Flood Control'));
     Gdn_Theme::section('Moderation');
     $this->setHighlightRoute('vanilla/settings/floodcontrol');
     // Check to see if Conversation is enabled.
     $IsConversationsEnabled = Gdn::addonManager()->isEnabled('Conversations', \Vanilla\Addon::TYPE_ADDON);
     $this->setData('IsConversationsEnabled', $IsConversationsEnabled);
     $ConfigurationFields = array('Vanilla.Discussion.SpamCount', 'Vanilla.Discussion.SpamTime', 'Vanilla.Discussion.SpamLock', 'Vanilla.Comment.SpamCount', 'Vanilla.Comment.SpamTime', 'Vanilla.Comment.SpamLock');
     if ($IsConversationsEnabled) {
         $ConfigurationFields = array_merge($ConfigurationFields, array('Conversations.Conversation.SpamCount', 'Conversations.Conversation.SpamTime', 'Conversations.Conversation.SpamLock', 'Conversations.ConversationMessage.SpamCount', 'Conversations.ConversationMessage.SpamTime', 'Conversations.ConversationMessage.SpamLock'));
     }
     // Load up config options we'll be setting
     $Validation = new Gdn_Validation();
     $ConfigurationModel = new Gdn_ConfigurationModel($Validation);
     $ConfigurationModel->setField($ConfigurationFields);
     // Set the model on the form.
     $this->Form->setModel($ConfigurationModel);
     // If seeing the form for the first time...
     if ($this->Form->authenticatedPostBack() === false) {
         // Apply the config settings to the form.
         $this->Form->setData($ConfigurationModel->Data);
     } else {
         // Define some validation rules for the fields being saved
         $ConfigurationModel->Validation->applyRule('Vanilla.Discussion.SpamCount', 'Required');
         $ConfigurationModel->Validation->applyRule('Vanilla.Discussion.SpamCount', 'Integer');
         $ConfigurationModel->Validation->applyRule('Vanilla.Discussion.SpamTime', 'Required');
         $ConfigurationModel->Validation->applyRule('Vanilla.Discussion.SpamTime', 'Integer');
         $ConfigurationModel->Validation->applyRule('Vanilla.Discussion.SpamLock', 'Required');
         $ConfigurationModel->Validation->applyRule('Vanilla.Discussion.SpamLock', 'Integer');
         $ConfigurationModel->Validation->applyRule('Vanilla.Comment.SpamCount', 'Required');
         $ConfigurationModel->Validation->applyRule('Vanilla.Comment.SpamCount', 'Integer');
         $ConfigurationModel->Validation->applyRule('Vanilla.Comment.SpamTime', 'Required');
         $ConfigurationModel->Validation->applyRule('Vanilla.Comment.SpamTime', 'Integer');
         $ConfigurationModel->Validation->applyRule('Vanilla.Comment.SpamLock', 'Required');
         $ConfigurationModel->Validation->applyRule('Vanilla.Comment.SpamLock', 'Integer');
         if ($IsConversationsEnabled) {
             $ConfigurationModel->Validation->applyRule('Conversations.Conversation.SpamCount', 'Required');
             $ConfigurationModel->Validation->applyRule('Conversations.Conversation.SpamCount', 'Integer');
             $ConfigurationModel->Validation->applyRule('Conversations.Conversation.SpamTime', 'Required');
             $ConfigurationModel->Validation->applyRule('Conversations.Conversation.SpamTime', 'Integer');
             $ConfigurationModel->Validation->applyRule('Conversations.Conversation.SpamLock', 'Required');
             $ConfigurationModel->Validation->applyRule('Conversations.Conversation.SpamLock', 'Integer');
             $ConfigurationModel->Validation->applyRule('Conversations.ConversationMessage.SpamCount', 'Required');
             $ConfigurationModel->Validation->applyRule('Conversations.ConversationMessage.SpamCount', 'Integer');
             $ConfigurationModel->Validation->applyRule('Conversations.ConversationMessage.SpamTime', 'Required');
             $ConfigurationModel->Validation->applyRule('Conversations.ConversationMessage.SpamTime', 'Integer');
             $ConfigurationModel->Validation->applyRule('Conversations.ConversationMessage.SpamLock', 'Required');
             $ConfigurationModel->Validation->applyRule('Conversations.ConversationMessage.SpamLock', 'Integer');
         }
         if ($this->Form->save() !== false) {
             $this->informMessage(t("Your changes have been saved."));
         }
     }
     // Render default view
     $this->render();
 }
Example #10
0
}
// Define 'Answer' badges
if (Gdn::addonManager()->isEnabled('badges', \Vanilla\Addon::TYPE_ADDON) && c('Plugins.QnA.Badges', true)) {
    $this->Badges = true;
}
if ($this->Badges && class_exists('BadgeModel')) {
    $BadgeModel = new BadgeModel();
    // Answer Counts
    $BadgeModel->define(array('Name' => 'First Answer', 'Slug' => 'answer', 'Type' => 'UserCount', 'Body' => 'Answering questions is a great way to show your support for a community!', 'Photo' => 'http://badges.vni.la/100/answer.png', 'Points' => 2, 'Attributes' => array('Column' => 'CountAcceptedAnswers'), 'Threshold' => 1, 'Class' => 'Answerer', 'Level' => 1, 'CanDelete' => 0));
    $BadgeModel->define(array('Name' => '5 Answers', 'Slug' => 'answer-5', 'Type' => 'UserCount', 'Body' => 'Your willingness to share knowledge has definitely been noticed.', 'Photo' => 'http://badges.vni.la/100/answer-2.png', 'Points' => 3, 'Attributes' => array('Column' => 'CountAcceptedAnswers'), 'Threshold' => 5, 'Class' => 'Answerer', 'Level' => 2, 'CanDelete' => 0));
    $BadgeModel->define(array('Name' => '25 Answers', 'Slug' => 'answer-25', 'Type' => 'UserCount', 'Body' => 'Looks like you’re starting to make a name for yourself as someone who knows the score!', 'Photo' => 'http://badges.vni.la/100/answer-3.png', 'Points' => 5, 'Attributes' => array('Column' => 'CountAcceptedAnswers'), 'Threshold' => 25, 'Class' => 'Answerer', 'Level' => 3, 'CanDelete' => 0));
    $BadgeModel->define(array('Name' => '50 Answers', 'Slug' => 'answer-50', 'Type' => 'UserCount', 'Body' => 'Why use Google when we could just ask you?', 'Photo' => 'http://badges.vni.la/100/answer-4.png', 'Points' => 10, 'Attributes' => array('Column' => 'CountAcceptedAnswers'), 'Threshold' => 50, 'Class' => 'Answerer', 'Level' => 4, 'CanDelete' => 0));
    $BadgeModel->define(array('Name' => '100 Answers', 'Slug' => 'answer-100', 'Type' => 'UserCount', 'Body' => 'Admit it, you read Wikipedia in your spare time.', 'Photo' => 'http://badges.vni.la/100/answer-5.png', 'Points' => 15, 'Attributes' => array('Column' => 'CountAcceptedAnswers'), 'Threshold' => 100, 'Class' => 'Answerer', 'Level' => 5, 'CanDelete' => 0));
    $BadgeModel->define(array('Name' => '250 Answers', 'Slug' => 'answer-250', 'Type' => 'UserCount', 'Body' => 'Is there *anything* you don’t know?', 'Photo' => 'http://badges.vni.la/100/answer-6.png', 'Points' => 20, 'Attributes' => array('Column' => 'CountAcceptedAnswers'), 'Threshold' => 250, 'Class' => 'Answerer', 'Level' => 6, 'CanDelete' => 0));
}
// Define 'Accept' reaction
if (Gdn::addonManager()->isEnabled('Reactions', \Vanilla\Addon::TYPE_ADDON) && c('Plugins.QnA.Reactions', true)) {
    $this->Reactions = true;
}
if ($this->Reactions && class_exists('ReactionModel')) {
    $Rm = new ReactionModel();
    if (Gdn::structure()->table('ReactionType')->columnExists('Hidden')) {
        $points = 3;
        if (c('QnA.Points.Enabled', false)) {
            $points = c('QnA.Points.AcceptedAnswer', 1);
        }
        // AcceptAnswer
        $Rm->defineReactionType(['UrlCode' => 'AcceptAnswer', 'Name' => 'Accept Answer', 'Sort' => 0, 'Class' => 'Positive', 'IncrementColumn' => 'Score', 'IncrementValue' => 5, 'Points' => $points, 'Permission' => 'Garden.Curation.Manage', 'Hidden' => 1, 'Description' => "When someone correctly answers a question, they are rewarded with this reaction."]);
    }
    Gdn::structure()->reset();
}
 protected function PollFeed($FeedURL, $LastImportDate)
 {
     $Pr = new ProxyRequest();
     $FeedRSS = $Pr->Request(array('URL' => $FeedURL));
     if (!$FeedRSS) {
         return FALSE;
     }
     $RSSData = simplexml_load_string($FeedRSS);
     if (!$RSSData) {
         return FALSE;
     }
     $Channel = GetValue('channel', $RSSData, FALSE);
     if (!$Channel) {
         return FALSE;
     }
     if (!array_key_exists('item', $Channel)) {
         return FALSE;
     }
     $Feed = $this->GetFeed($FeedURL, FALSE);
     $DiscussionModel = new DiscussionModel();
     $DiscussionModel->SpamCheck = FALSE;
     $LastPublishDate = GetValue('LastPublishDate', $Feed, date('c'));
     $LastPublishTime = strtotime($LastPublishDate);
     $FeedLastPublishTime = 0;
     foreach (GetValue('item', $Channel) as $Item) {
         $FeedItemGUID = trim((string) GetValue('guid', $Item));
         if (empty($FeedItemGUID)) {
             Trace('guid is not set in each item of the RSS.  Will attempt to use link as unique identifier.');
             $FeedItemGUID = GetValue('link', $Item);
         }
         $FeedItemID = substr(md5($FeedItemGUID), 0, 30);
         $ItemPubDate = (string) GetValue('pubDate', $Item, NULL);
         if (is_null($ItemPubDate)) {
             $ItemPubTime = time();
         } else {
             $ItemPubTime = strtotime($ItemPubDate);
         }
         if ($ItemPubTime > $FeedLastPublishTime) {
             $FeedLastPublishTime = $ItemPubTime;
         }
         if ($ItemPubTime < $LastPublishTime && !$Feed['Historical']) {
             continue;
         }
         $ExistingDiscussion = $DiscussionModel->GetWhere(array('ForeignID' => $FeedItemID));
         if ($ExistingDiscussion && $ExistingDiscussion->NumRows()) {
             continue;
         }
         $this->EventArguments['Publish'] = TRUE;
         $this->EventArguments['FeedURL'] = $FeedURL;
         $this->EventArguments['Feed'] =& $Feed;
         $this->EventArguments['Item'] =& $Item;
         $this->FireEvent('FeedItem');
         if (!$this->EventArguments['Publish']) {
             continue;
         }
         $StoryTitle = array_shift($Trash = explode("\n", (string) GetValue('title', $Item)));
         $StoryBody = (string) GetValue('description', $Item);
         $StoryPublished = date("Y-m-d H:i:s", $ItemPubTime);
         $ParsedStoryBody = $StoryBody;
         $ParsedStoryBody = '<div class="AutoFeedDiscussion">' . $ParsedStoryBody . '</div> <br /><div class="AutoFeedSource">Source: ' . $FeedItemGUID . '</div>';
         $DiscussionData = array('Name' => $StoryTitle, 'Format' => 'Html', 'CategoryID' => $Feed['Category'], 'ForeignID' => substr($FeedItemID, 0, 30), 'Body' => $ParsedStoryBody);
         // Post as Minion (if one exists) or the system user
         if (Gdn::addonManager()->isEnabled('Minion', \Vanilla\Addon::TYPE_ADDON)) {
             $Minion = Gdn::PluginManager()->GetPluginInstance('MinionPlugin');
             $InsertUserID = $Minion->GetMinionUserID();
         } else {
             $InsertUserID = Gdn::UserModel()->GetSystemUserID();
         }
         $DiscussionData[$DiscussionModel->DateInserted] = $StoryPublished;
         $DiscussionData[$DiscussionModel->InsertUserID] = $InsertUserID;
         $DiscussionData[$DiscussionModel->DateUpdated] = $StoryPublished;
         $DiscussionData[$DiscussionModel->UpdateUserID] = $InsertUserID;
         $this->EventArguments['FeedDiscussion'] =& $DiscussionData;
         $this->FireEvent('Publish');
         if (!$this->EventArguments['Publish']) {
             continue;
         }
         $InsertID = $DiscussionModel->Save($DiscussionData);
         $this->EventArguments['DiscussionID'] = $InsertID;
         $this->EventArguments['Validation'] = $DiscussionModel->Validation;
         $this->FireEvent('Published');
         // Reset discussion validation
         $DiscussionModel->Validation->Results(TRUE);
     }
     $FeedKey = self::EncodeFeedKey($FeedURL);
     $this->UpdateFeed($FeedKey, array('LastImport' => date('Y-m-d H:i:s'), 'LastPublishDate' => date('c', $FeedLastPublishTime)));
 }
Example #12
0
 /**
  *
  *
  * @param $Path
  * @param bool $Text
  * @param null $Format
  * @param array $Options
  * @return mixed|null|string
  */
 public static function link($Path, $Text = false, $Format = null, $Options = array())
 {
     $Session = Gdn::session();
     $Class = val('class', $Options, '');
     $WithDomain = val('WithDomain', $Options);
     $Target = val('Target', $Options, '');
     if ($Target == 'current') {
         $Target = trim(url('', true), '/ ');
     }
     if (is_null($Format)) {
         $Format = '<a href="%url" class="%class">%text</a>';
     }
     switch ($Path) {
         case 'activity':
             touchValue('Permissions', $Options, 'Garden.Activity.View');
             break;
         case 'category':
             $Breadcrumbs = Gdn::controller()->data('Breadcrumbs');
             if (is_array($Breadcrumbs) && count($Breadcrumbs) > 0) {
                 $Last = array_pop($Breadcrumbs);
                 $Path = val('Url', $Last);
                 $DefaultText = val('Name', $Last, T('Back'));
             } else {
                 $Path = '/';
                 $DefaultText = c('Garden.Title', T('Back'));
             }
             if (!$Text) {
                 $Text = $DefaultText;
             }
             break;
         case 'dashboard':
             $Path = 'dashboard/settings';
             touchValue('Permissions', $Options, array('Garden.Settings.Manage', 'Garden.Settings.View'));
             if (!$Text) {
                 $Text = t('Dashboard');
             }
             break;
         case 'home':
             $Path = '/';
             if (!$Text) {
                 $Text = t('Home');
             }
             break;
         case 'inbox':
             $Path = 'messages/inbox';
             touchValue('Permissions', $Options, 'Garden.SignIn.Allow');
             if (!$Text) {
                 $Text = t('Inbox');
             }
             if ($Session->isValid() && $Session->User->CountUnreadConversations) {
                 $Class = trim($Class . ' HasCount');
                 $Text .= ' <span class="Alert">' . $Session->User->CountUnreadConversations . '</span>';
             }
             if (!$Session->isValid() || !Gdn::addonManager()->lookupAddon('conversations')) {
                 $Text = false;
             }
             break;
         case 'forumroot':
             $Route = Gdn::router()->getDestination('DefaultForumRoot');
             if (is_null($Route)) {
                 $Path = '/';
             } else {
                 $Path = combinePaths(array('/', $Route));
             }
             break;
         case 'profile':
             touchValue('Permissions', $Options, 'Garden.SignIn.Allow');
             if (!$Text && $Session->isValid()) {
                 $Text = $Session->User->Name;
             }
             if ($Session->isValid() && $Session->User->CountNotifications) {
                 $Class = trim($Class . ' HasCount');
                 $Text .= ' <span class="Alert">' . $Session->User->CountNotifications . '</span>';
             }
             break;
         case 'user':
             $Path = 'profile';
             touchValue('Permissions', $Options, 'Garden.SignIn.Allow');
             if (!$Text && $Session->isValid()) {
                 $Text = $Session->User->Name;
             }
             break;
         case 'photo':
             $Path = 'profile';
             TouchValue('Permissions', $Options, 'Garden.SignIn.Allow');
             if (!$Text && $Session->isValid()) {
                 $IsFullPath = strtolower(substr($Session->User->Photo, 0, 7)) == 'http://' || strtolower(substr($Session->User->Photo, 0, 8)) == 'https://';
                 $PhotoUrl = $IsFullPath ? $Session->User->Photo : Gdn_Upload::url(changeBasename($Session->User->Photo, 'n%s'));
                 $Text = img($PhotoUrl, array('alt' => $Session->User->Name));
             }
             break;
         case 'drafts':
             TouchValue('Permissions', $Options, 'Garden.SignIn.Allow');
             if (!$Text) {
                 $Text = t('My Drafts');
             }
             if ($Session->isValid() && $Session->User->CountDrafts) {
                 $Class = trim($Class . ' HasCount');
                 $Text .= ' <span class="Alert">' . $Session->User->CountDrafts . '</span>';
             }
             break;
         case 'discussions/bookmarked':
             TouchValue('Permissions', $Options, 'Garden.SignIn.Allow');
             if (!$Text) {
                 $Text = t('My Bookmarks');
             }
             if ($Session->isValid() && $Session->User->CountBookmarks) {
                 $Class = trim($Class . ' HasCount');
                 $Text .= ' <span class="Count">' . $Session->User->CountBookmarks . '</span>';
             }
             break;
         case 'discussions/mine':
             TouchValue('Permissions', $Options, 'Garden.SignIn.Allow');
             if (!$Text) {
                 $Text = t('My Discussions');
             }
             if ($Session->isValid() && $Session->User->CountDiscussions) {
                 $Class = trim($Class . ' HasCount');
                 $Text .= ' <span class="Count">' . $Session->User->CountDiscussions . '</span>';
             }
             break;
         case 'register':
             if (!$Text) {
                 $Text = t('Register');
             }
             $Path = registerUrl($Target);
             break;
         case 'signin':
         case 'signinout':
             // The destination is the signin/signout toggle link.
             if ($Session->isValid()) {
                 if (!$Text) {
                     $Text = T('Sign Out');
                 }
                 $Path = signOutUrl($Target);
                 $Class = concatSep(' ', $Class, 'SignOut');
             } else {
                 if (!$Text) {
                     $Text = t('Sign In');
                 }
                 $Path = signInUrl($Target);
                 if (signInPopup() && strpos(Gdn::Request()->Url(), 'entry') === false) {
                     $Class = concatSep(' ', $Class, 'SignInPopup');
                 }
             }
             break;
     }
     if ($Text == false && strpos($Format, '%text') !== false) {
         return '';
     }
     if (val('Permissions', $Options) && !$Session->checkPermission($Options['Permissions'], false)) {
         return '';
     }
     $Url = Gdn::request()->url($Path, $WithDomain);
     if ($TK = val('TK', $Options)) {
         if (in_array($TK, array(1, 'true'))) {
             $TK = 'TransientKey';
         }
         $Url .= (strpos($Url, '?') === false ? '?' : '&') . $TK . '=' . urlencode(Gdn::session()->transientKey());
     }
     if (strcasecmp(trim($Path, '/'), Gdn::request()->path()) == 0) {
         $Class = concatSep(' ', $Class, 'Selected');
     }
     // Build the final result.
     $Result = $Format;
     $Result = str_replace('%url', $Url, $Result);
     $Result = str_replace('%text', $Text, $Result);
     $Result = str_replace('%class', $Class, $Result);
     return $Result;
 }
Example #13
0
 $CNotifications = is_numeric($CountNotifications) && $CountNotifications > 0 ? '<span class="Alert NotificationsAlert">' . $CountNotifications . '</span>' : '';
 echo '<span class="ToggleFlyout" rel="/profile/notificationspopin">';
 echo anchor(sprite('SpNotifications', 'Sprite Sprite16') . Wrap(t('Notifications'), 'em') . $CNotifications, userUrl($User), 'MeButton FlyoutButton js-clear-notifications', array('title' => t('Notifications')));
 echo sprite('SpFlyoutHandle', 'Arrow');
 echo '<div class="Flyout FlyoutMenu"></div></span>';
 // Inbox
 if (Gdn::addonManager()->lookupAddon('conversations')) {
     $CountInbox = val('CountUnreadConversations', Gdn::session()->User);
     $CInbox = is_numeric($CountInbox) && $CountInbox > 0 ? ' <span class="Alert">' . $CountInbox . '</span>' : '';
     echo '<span class="ToggleFlyout" rel="/messages/popin">';
     echo anchor(sprite('SpInbox', 'Sprite Sprite16') . Wrap(t('Inbox'), 'em') . $CInbox, '/messages/all', 'MeButton FlyoutButton', array('title' => t('Inbox')));
     echo sprite('SpFlyoutHandle', 'Arrow');
     echo '<div class="Flyout FlyoutMenu"></div></span>';
 }
 // Bookmarks
 if (Gdn::addonManager()->lookupAddon('Vanilla')) {
     echo '<span class="ToggleFlyout" rel="/discussions/bookmarkedpopin">';
     echo anchor(sprite('SpBookmarks', 'Sprite Sprite16') . Wrap(t('Bookmarks'), 'em'), '/discussions/bookmarked', 'MeButton FlyoutButton', array('title' => t('Bookmarks')));
     echo sprite('SpFlyoutHandle', 'Arrow');
     echo '<div class="Flyout FlyoutMenu"></div></span>';
 }
 // Profile Settings & Logout
 echo '<span class="ToggleFlyout">';
 $CDashboard = $DashboardCount > 0 ? wrap($DashboardCount, 'span class="Alert"') : '';
 echo anchor(sprite('SpOptions', 'Sprite Sprite16') . Wrap(t('Account Options'), 'em') . $CDashboard, '/profile/edit', 'MeButton FlyoutButton', array('title' => t('Account Options')));
 echo sprite('SpFlyoutHandle', 'Arrow');
 echo '<div class="Flyout MenuItems">';
 echo '<ul>';
 // echo wrap(Wrap(t('My Account'), 'strong'), 'li');
 // echo wrap('<hr />', 'li');
 if (hasEditProfile(Gdn::session()->UserID)) {
Example #14
0
 /**
  * Run the structure for all addons.
  *
  * The structure runs the addons in priority order so that higher priority addons override lower priority ones.
  *
  * @param bool $captureOnly Run the structure or just capture the SQL changes.
  * @throws Exception Throws an exception if in debug mode and something goes wrong.
  */
 public function runStructure($captureOnly = false)
 {
     $addons = array_reverse(Gdn::addonManager()->getEnabled());
     // These variables are required for included structure files.
     $Database = Gdn::database();
     $SQL = $this->SQL;
     $SQL->CaptureModifications = $captureOnly;
     $Structure = Gdn::structure();
     $Structure->CaptureOnly = $captureOnly;
     /* @var Addon $addon */
     foreach ($addons as $addon) {
         // Look for a structure file.
         if ($structure = $addon->getSpecial('structure')) {
             Logger::event('addon_structure', Logger::INFO, "Executing structure for {addonKey}.", ['addonKey' => $addon->getKey(), 'structureType' => 'file']);
             try {
                 include $addon->path($structure);
             } catch (\Exception $ex) {
                 if (debug()) {
                     throw $ex;
                 }
             }
         }
         // Look for a structure method on the plugin.
         if ($addon->getPluginClass()) {
             $plugin = Gdn::pluginManager()->getPluginInstance($addon->getPluginClass(), Gdn_PluginManager::ACCESS_CLASSNAME);
             if (is_object($plugin) && method_exists($plugin, 'structure')) {
                 Logger::event('addon_structure', Logger::INFO, "Executing structure for {addonKey}.", ['addonKey' => $addon->getKey(), 'structureType' => 'method']);
                 try {
                     call_user_func([$plugin, 'structure']);
                 } catch (\Exception $ex) {
                     if (debug()) {
                         throw $ex;
                     }
                 }
             }
         }
         // Register permissions.
         $permissions = $addon->getInfoValue('registerPermissions');
         if (!empty($permissions)) {
             Logger::event('addon_permissions', Logger::INFO, "Defining permissions for {addonKey}.", ['addonKey' => $addon->getKey(), 'permissions' => $permissions]);
             Gdn::permissionModel()->define($permissions);
         }
     }
     $this->fireEvent('AfterStructure');
     if ($captureOnly && property_exists($Structure->Database, 'CapturedSql')) {
         return $Structure->Database->CapturedSql;
     }
     return [];
 }
Example #15
0
            <?php 
// Only show the vanilla pages if Vanilla is enabled
$CurrentTarget = $this->data('CurrentTarget');
if (Gdn::addonManager()->isEnabled('Vanilla', \Vanilla\Addon::TYPE_ADDON)) {
    echo WriteHomepageOption('Discussions', 'discussions', 'disc-modern', $CurrentTarget);
    echo WriteHomepageOption('Categories', 'categories', 'cat-modern', $CurrentTarget);
    // echo WriteHomepageOption('Categories &amp; Discussions', 'categories/discussions', 'categoriesdiscussions', $CurrentTarget);
}
//echo WriteHomepageOption('Activity', 'activity', 'SpActivity', $CurrentTarget);
if (Gdn::addonManager()->isEnabled('Reactions', \Vanilla\Addon::TYPE_ADDON)) {
    echo WriteHomepageOption('Best Of', 'bestof', 'best-of', $CurrentTarget);
}
?>
        </div>
        <?php 
if (Gdn::addonManager()->isEnabled('Vanilla', \Vanilla\Addon::TYPE_ADDON)) {
    ?>
            <?php 
    echo subheading(t('Discussions Layout'), t('Choose the preferred layout for the discussions page.'));
    ?>
            <div class="LayoutOptions DiscussionsLayout label-selector">
                <?php 
    echo WriteHomepageOption('Modern Layout', 'modern', 'disc-modern', $CurrentDiscussionLayout, t('Modern non-table-based layout'));
    echo WriteHomepageOption('Table Layout', 'table', 'disc-table', $CurrentDiscussionLayout, t('Classic table layout used by traditional forums'));
    ?>
            </div>
            <?php 
    echo subheading(t('Categories Layout'), t('Choose the preferred layout for the categories page.'));
    ?>
            <div class="LayoutOptions CategoriesLayout label-selector">
                <?php 
Example #16
0
        $bootstrapPath = $addon->path($bootstrapPath);
        include $bootstrapPath;
    }
}
// Themes startup
Gdn::themeManager()->start();
// Plugins startup
Gdn::pluginManager()->start();
/**
 * Locales
 *
 * Install any custom locales provided by applications and plugins, and set up
 * the locale management system.
 */
// Load the Garden locale system
$gdnLocale = new Gdn_Locale(c('Garden.Locale', 'en'), Gdn::addonManager());
Gdn::factoryInstall(Gdn::AliasLocale, 'Gdn_Locale', null, Gdn::FactorySingleton, $gdnLocale);
unset($gdnLocale);
require_once PATH_LIBRARY_CORE . '/functions.validation.php';
// Start Authenticators
Gdn::authenticator()->startAuthenticator();
/**
 * Bootstrap After
 *
 * After the bootstrap has finished loading, this hook allows developers a last
 * chance to customize Garden's runtime environment before the actual request
 * is handled.
 */
if (file_exists(PATH_ROOT . '/conf/bootstrap.after.php')) {
    require_once PATH_ROOT . '/conf/bootstrap.after.php';
}
Example #17
0
 /**
  * Get a version string for a given asset.
  *
  * @param string $destination The path of the asset.
  * @param string|null $version A known version for the asset or **null** to grab it from the addon's info array.
  * @return string Returns a version string.
  */
 function assetVersion($destination, $version = null)
 {
     static $gracePeriod = 90;
     // Figure out which version to put after the asset.
     if (is_null($version)) {
         $version = APPLICATION_VERSION;
         if (preg_match('`^/([^/]+)/([^/]+)/`', $destination, $matches)) {
             $type = $matches[1];
             $key = $matches[2];
             static $themeVersion = null;
             switch ($type) {
                 case 'plugins':
                 case 'applications':
                     $addon = Gdn::addonManager()->lookupAddon($key);
                     if ($addon) {
                         $version = $addon->getVersion();
                     }
                     break;
                 case 'themes':
                     if ($themeVersion === null) {
                         $theme = Gdn::addonManager()->lookupTheme(theme());
                         if ($theme) {
                             $themeVersion = $theme->getVersion();
                         }
                     }
                     $version = $themeVersion;
                     break;
             }
         }
     }
     // Add a timestamp component to the version if available.
     if ($timestamp = c('Garden.Deployed')) {
         $graced = $timestamp + $gracePeriod;
         if (time() >= $graced) {
             $timestamp = $graced;
         }
         $version .= '.' . dechex($timestamp);
     }
     return $version;
 }