Version 4.3.6
This commit is contained in:
1 parent
fe1acf984a
commit
1a0c7fd3c2
609 files changed
+14707
-5726
No files matched your search
@@ -115,7 +115,7 @@ class _Announcement extends \IPS\Content\Item
|
||||
$announcement = static::constructFromData( $announce );
|
||||
|
||||
/* Check page location, active status and permissions */
|
||||
if( !in_array( $location, $announcement->page_location ) OR !$announcement->active OR ( $announcement->end !== 0 AND $announcement->end <= time() ) OR !$announcement->canView() )
|
||||
if( !in_array( $location, $announcement->page_location ) OR !$announcement->active OR ( $announcement->start !== 0 AND $announcement->start >= time() ) OR ( $announcement->end !== 0 AND $announcement->end <= time() ) OR !$announcement->canView() )
|
||||
{
|
||||
continue;
|
||||
}
|
||||
@@ -127,36 +127,64 @@ class _Announcement extends \IPS\Content\Item
|
||||
continue;
|
||||
}
|
||||
|
||||
/* App and container specific announcements */
|
||||
foreach ( \IPS\Dispatcher::i()->application->extensions( 'core', 'Announcements' ) as $key => $extension )
|
||||
/* If the dispatcher did not finish loading (perhaps we hit an error that occurred early in execution) we can't check per-app locations */
|
||||
if( !\IPS\Dispatcher::i()->application )
|
||||
{
|
||||
$id = $extension::$idField;
|
||||
continue;
|
||||
}
|
||||
|
||||
if ( isset( \IPS\Request::i()->$id ) )
|
||||
$extensions = \IPS\Dispatcher::i()->application->extensions( 'core', 'Announcements' );
|
||||
|
||||
/* If we have no extension, we can only check the global setting */
|
||||
if ( !$extensions AND $announcement->app == \IPS\Dispatcher::i()->application->directory )
|
||||
{
|
||||
$return[] = $announcement;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* App and container specific announcements */
|
||||
foreach ( $extensions as $key => $extension )
|
||||
{
|
||||
if ( \IPS\Dispatcher::i()->dispatcherController instanceof \IPS\Content\Controller )
|
||||
$id = $extension::$idField;
|
||||
|
||||
if ( $announcement->ids AND isset( \IPS\Request::i()->$id ) )
|
||||
{
|
||||
foreach( \IPS\Dispatcher::i()->application->extensions( 'core', 'ContentRouter' ) AS $contentRouter )
|
||||
/* Are we viewing a content item */
|
||||
if ( \IPS\Dispatcher::i()->dispatcherController instanceof \IPS\Content\Controller )
|
||||
{
|
||||
foreach( $contentRouter->classes AS $class )
|
||||
foreach( \IPS\Dispatcher::i()->application->extensions( 'core', 'ContentRouter' ) AS $contentRouter )
|
||||
{
|
||||
try
|
||||
foreach( $contentRouter->classes AS $class )
|
||||
{
|
||||
if( $announcement->location == $key AND in_array( $class::load( \IPS\Request::i()->$id )->mapped('container'), explode( ',', $announcement->ids ) ) )
|
||||
try
|
||||
{
|
||||
$return[] = $announcement;
|
||||
if( $announcement->location == $key AND in_array( $class::load( \IPS\Request::i()->$id )->mapped('container'), explode( ',', $announcement->ids ) ) )
|
||||
{
|
||||
$return[] = $announcement;
|
||||
}
|
||||
}
|
||||
catch( \OutOfRangeException $e ){}
|
||||
}
|
||||
catch( \OutOfRangeException $e ){}
|
||||
break 2;
|
||||
}
|
||||
}
|
||||
/* Or are we inside an allowed controller */
|
||||
else if ( in_array( get_class( \IPS\Dispatcher::i()->dispatcherController ), $extension::$controllers ) )
|
||||
{
|
||||
try
|
||||
{
|
||||
if( $announcement->location == $key AND in_array( \IPS\Request::i()->$id , explode( ',', $announcement->ids ) ) )
|
||||
{
|
||||
$return[] = $announcement;
|
||||
}
|
||||
}
|
||||
catch( \OutOfRangeException $e ){}
|
||||
}
|
||||
}
|
||||
/* App specific, doesn't matter which container we're in */
|
||||
elseif( $announcement->location == $key AND !$announcement->ids )
|
||||
{
|
||||
$return[] = $announcement;
|
||||
}
|
||||
}
|
||||
/* App specific, doesn't matter which container we're in */
|
||||
elseif( $announcement->location == $key )
|
||||
{
|
||||
$return[] = $announcement;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -281,6 +309,10 @@ class _Announcement extends \IPS\Content\Item
|
||||
$obj->page_location = $values['announce_page_location'];
|
||||
$obj->color = $values['announce_color'];
|
||||
|
||||
/* We need to set the data, before we then iterate over the toggled extension form fields */
|
||||
$obj->location = "*";
|
||||
$obj->ids = NULL;
|
||||
|
||||
if( in_array( $obj->app, array_keys(\IPS\Application::applications() ) ) )
|
||||
{
|
||||
foreach ( \IPS\Application::load( $obj->app )->extensions( 'core', 'Announcements' ) as $key => $extension )
|
||||
@@ -293,11 +325,6 @@ class _Announcement extends \IPS\Content\Item
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
$obj->location = "*";
|
||||
$obj->ids = NULL;
|
||||
}
|
||||
|
||||
$obj->save();
|
||||
|
||||
@@ -357,7 +384,7 @@ class _Announcement extends \IPS\Content\Item
|
||||
*/
|
||||
protected function unclaimAttachments()
|
||||
{
|
||||
\IPS\File::unclaimAttachments( 'core_Admin', $this->id, NULL, 'announcement' );
|
||||
\IPS\File::unclaimAttachments( 'core_Announcement', $this->id, NULL, 'announcement' );
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -377,7 +404,8 @@ class _Announcement extends \IPS\Content\Item
|
||||
|
||||
if( $type == 'hide' OR $type == 'unhide' OR $type == 'active' OR $type == 'inactive' )
|
||||
{
|
||||
return TRUE;
|
||||
$member = $member ?: \IPS\Member::loggedIn();
|
||||
return $member->modPermission( "can_manage_announcements" );
|
||||
}
|
||||
|
||||
return parent::modPermission( $type, $member, $container );
|
||||
|
||||
@@ -121,9 +121,18 @@ class _Bulkmailer extends \IPS\Patterns\ActiveRecord
|
||||
$content = str_replace( $k, '*|' . str_replace( array( '{', '}' ), '', $k ) . '|*', $content );
|
||||
}
|
||||
}
|
||||
|
||||
/* Format content */
|
||||
$content = \IPS\Email::staticParseTextForEmail( $content, \IPS\Lang::load( \IPS\Lang::defaultLanguage() ) );
|
||||
|
||||
foreach( array_keys( static::getTags() ) as $k )
|
||||
{
|
||||
$content = str_replace( '%7B' . mb_substr( $k, 1, -1 ) . '%7D', '*|' . mb_substr( $k, 1, -1 ) . '|*', $content );
|
||||
$content = str_replace( '*%7' . mb_substr( $k, 1, -1 ) . '%7C*', '*|' . mb_substr( $k, 1, -1 ) . '|*', $content );
|
||||
}
|
||||
|
||||
/* Send it */
|
||||
$email = \IPS\Email::buildFromContent( $this->_data['subject'], \IPS\Email::staticParseTextForEmail( $content, \IPS\Lang::load( \IPS\Lang::defaultLanguage() ) ), NULL, \IPS\Email::TYPE_BULK )
|
||||
$email = \IPS\Email::buildFromContent( $this->_data['subject'], $content, NULL, \IPS\Email::TYPE_BULK )
|
||||
->setUnsubscribe( 'core', 'unsubscribeBulk' );
|
||||
$sent = 0;
|
||||
foreach ( $recipients as $languageId => $_recipients )
|
||||
@@ -158,7 +167,7 @@ class _Bulkmailer extends \IPS\Patterns\ActiveRecord
|
||||
* @return \IPS\Db\Select
|
||||
*/
|
||||
public function getQuery( $option=NULL )
|
||||
{
|
||||
{
|
||||
/* Compile where */
|
||||
$where = array();
|
||||
$where[] = array( "core_members.allow_admin_mails=1" );
|
||||
@@ -175,19 +184,14 @@ class _Bulkmailer extends \IPS\Patterns\ActiveRecord
|
||||
{
|
||||
if( $_where = $extension->getQueryWhereClause( $this->_options[ $key ] ) )
|
||||
{
|
||||
if ( is_string( $_where ) )
|
||||
{
|
||||
$_where = array( $_where );
|
||||
}
|
||||
|
||||
$where = array_merge( $where, $_where );
|
||||
$where[] = $_where;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Compile query */
|
||||
$select = ( $option !== static::GET_COUNT_ONLY ) ? 'core_members.member_id AS my_member_id, core_members.*' : 'COUNT(DISTINCT member_id)';
|
||||
$select = ( $option !== static::GET_COUNT_ONLY ) ? 'core_members.member_id AS my_member_id, core_members.*' : 'COUNT(DISTINCT core_members.member_id)';
|
||||
$limit = is_array( $option ) ? $option : NULL;
|
||||
$query = \IPS\Db::i()->select( $select, 'core_members', $where, ( $option !== static::GET_COUNT_ONLY ) ? 'core_members.member_id' : NULL, $limit, NULL, NULL, \IPS\Db::SELECT_DISTINCT );
|
||||
|
||||
|
||||
@@ -100,7 +100,15 @@ class _Digest
|
||||
if ( property_exists( $class, 'contentItemClass' ) )
|
||||
{
|
||||
$itemClass= $class::$contentItemClass;
|
||||
|
||||
|
||||
/* Force custom profile fields not to be returned, as they can reference templates */
|
||||
if( isset( $itemClass::$commentClass ) )
|
||||
{
|
||||
$commentClass = $itemClass::$commentClass;
|
||||
|
||||
$commentClass::$joinProfileFields = FALSE;
|
||||
}
|
||||
|
||||
foreach ( $itemClass::getItemsWithPermission( array(
|
||||
array( $itemClass::$databaseTable . '.' . $itemClass::$databasePrefix . $itemClass::$databaseColumnMap['container'] . '=? AND ' . $itemClass::$databaseTable . '.' . $itemClass::$databasePrefix . $itemClass::$databaseColumnMap['date'] . ' > ? AND ' . $itemClass::$databaseTable . '.' .$itemClass::$databasePrefix . $itemClass::$databaseColumnMap['author'] . '!=?', $follow['follow_rel_id'], $follow['follow_notify_sent'] ?: $follow['follow_added'], $follow['follow_member_id'] ) ),
|
||||
$itemClass::$databaseTable . '.' . $itemClass::$databasePrefix . $itemClass::$databaseColumnMap['date'] . ' ASC',
|
||||
@@ -140,6 +148,14 @@ class _Digest
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Force custom profile fields not to be returned, as they can reference templates */
|
||||
if( isset( $item::$commentClass ) )
|
||||
{
|
||||
$commentClass = $item::$commentClass;
|
||||
|
||||
$commentClass::$joinProfileFields = FALSE;
|
||||
}
|
||||
|
||||
foreach( $item->comments( 5, NULL, 'date', 'asc', NULL, FALSE, \IPS\DateTime::ts( $follow['follow_notify_sent'] ?: $follow['follow_added'] ), NULL, FALSE, FALSE, FALSE ) as $comment )
|
||||
{
|
||||
|
||||
|
||||
@@ -103,7 +103,7 @@ class _Pixel extends \IPS\Patterns\Singleton
|
||||
|
||||
if ( is_array( $params ) and count( $params ) )
|
||||
{
|
||||
$url .= '&' . http_build_query( array( 'cd' => $params ) );
|
||||
$url .= '&' . http_build_query( array( 'cd' => $params ), '', '&' );
|
||||
}
|
||||
|
||||
$return[] = '<img alt="" height="1" width="1" style="display:none" src="' . $url . '"/>';
|
||||
|
||||
@@ -60,7 +60,6 @@ class _Follow extends \IPS\Patterns\ActiveRecord
|
||||
$this->visible = 1;
|
||||
$this->notify_sent = 0;
|
||||
$this->added = time();
|
||||
$this->index_id = NULL;
|
||||
}
|
||||
|
||||
$this->id = md5( $this->app . ';' . $this->area . ';' . $this->rel_id . ';' . $this->member_id );
|
||||
|
||||
@@ -82,6 +82,7 @@ class _SocialProfiles extends \IPS\Helpers\Form\KeyValue
|
||||
'twitter' => "siteprofilelink_twitter",
|
||||
'youtube' => "siteprofilelink_youtube",
|
||||
'google-plus' => "siteprofilelink_googleplus",
|
||||
'tumblr' => "siteprofilelink_tumblr",
|
||||
'deviantart' => "siteprofilelink_deviantart",
|
||||
'etsy' => "siteprofilelink_etsy",
|
||||
'flickr' => "siteprofilelink_flickr",
|
||||
|
||||
@@ -38,6 +38,17 @@ abstract class _MainTab
|
||||
$this->member = $member;
|
||||
}
|
||||
|
||||
/**
|
||||
* Can View this Tab
|
||||
*
|
||||
* @return bool
|
||||
*/
|
||||
public function canView()
|
||||
{
|
||||
/* Extensions can override */
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get Title
|
||||
*
|
||||
|
||||
@@ -406,9 +406,23 @@ class _Profanity extends \IPS\Patterns\ActiveRecord implements \JsonSerializable
|
||||
/* Make sure we're not doing something weird like storing a blank URL */
|
||||
if ( $url )
|
||||
{
|
||||
/* If this is an attachment, we never want to do this. */
|
||||
if ( preg_match( '/<fileStore\.(.+)>/i', $urlToCheck ) )
|
||||
{
|
||||
$good = TRUE;
|
||||
break;
|
||||
}
|
||||
|
||||
/* IF we are moderating all URL's and it's not an attachment, return here. */
|
||||
if ( $good !== TRUE AND \IPS\Settings::i()->ipb_url_filter_option == 'none' )
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
$url = preg_quote( $url, '/' );
|
||||
$url = str_replace( '\*', "(.*?)", $url );
|
||||
|
||||
/* If it's a blacklist, check that */
|
||||
if ( \IPS\Settings::i()->ipb_url_filter_option == 'black' )
|
||||
{
|
||||
if ( preg_match( '/' . $url . '/i', $urlToCheck ) )
|
||||
@@ -416,6 +430,7 @@ class _Profanity extends \IPS\Patterns\ActiveRecord implements \JsonSerializable
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
/* If it's a whitelist, check that */
|
||||
else if ( \IPS\Settings::i()->ipb_url_filter_option == 'white' )
|
||||
{
|
||||
/* @note http:// is hard-coded here as we're simply validating that the URL is on the same domain, so the protocol doesn't matter for the base_url replacement */
|
||||
|
||||
@@ -356,7 +356,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
|
||||
throw new \OutofRangeException('object_not_valid');
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get the number and indefinite article for replies/children where applicable
|
||||
*
|
||||
@@ -364,7 +364,19 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
*/
|
||||
public function get_objectDataCount()
|
||||
{
|
||||
$object = $this->object();
|
||||
return $this->objectDataCount( NULL );
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the number and indefinite article for replies/children where applicable
|
||||
*
|
||||
* @param \IPS\Lang|null $language Language to use (or NULL for currently logged in member's language)
|
||||
* @return array|null
|
||||
*/
|
||||
public function objectDataCount( $language=NULL )
|
||||
{
|
||||
$language = $language ?: \IPS\Member::loggedIn()->language();
|
||||
$object = $this->object();
|
||||
|
||||
if ( $object instanceof \IPS\Content\Item )
|
||||
{
|
||||
@@ -383,14 +395,14 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
$count--;
|
||||
}
|
||||
|
||||
return array( 'count' => $count, 'words' => \IPS\Member::loggedIn()->language()->addToStack( 'num_replies', NULL, array( 'pluralize' => array( $count ) ) ) );
|
||||
return array( 'count' => $count, 'words' => $language->addToStack( 'num_replies', NULL, array( 'pluralize' => array( $count ) ) ) );
|
||||
}
|
||||
|
||||
if ( $object::supportsReviews( NULL, $container ) )
|
||||
{
|
||||
$count = $object->mapped('num_reviews');
|
||||
|
||||
return array( 'count' => $count, 'words' => \IPS\Member::loggedIn()->language()->addToStack( 'num_reviews', NULL, array( 'pluralize' => array( $count ) ) ) );
|
||||
return array( 'count' => $count, 'words' => $language->addToStack( 'num_reviews', NULL, array( 'pluralize' => array( $count ) ) ) );
|
||||
}
|
||||
|
||||
/* Valid object, but there isn't any date data available */
|
||||
@@ -406,7 +418,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
{
|
||||
$count = $object->_items;
|
||||
|
||||
return array( 'count' => $count, 'words' => \IPS\Member::loggedIn()->language()->addToStack( $object->_countLanguageString, NULL, array( 'pluralize' => array( $count ) ) ) );
|
||||
return array( 'count' => $count, 'words' => $language->addToStack( $object->_countLanguageString, NULL, array( 'pluralize' => array( $count ) ) ) );
|
||||
}
|
||||
|
||||
return NULL;
|
||||
@@ -452,7 +464,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
else
|
||||
{
|
||||
return $plaintextLanguage->addToStack( 'promote_metadescription_container_nolink', NULL, array(
|
||||
'sprintf' => array( $object->indefiniteArticle( $plaintextLanguage ), $container->_title, $author->name, $this->objectDatePosted->relative( \IPS\DateTime::RELATIVE_FORMAT_NORMAL, $plaintextLanguage ) ),
|
||||
'sprintf' => array( $object->indefiniteArticle( $plaintextLanguage ), $container->getTitleForLanguage( $plaintextLanguage ), $author->name, $this->objectDatePosted->relative( \IPS\DateTime::RELATIVE_FORMAT_NORMAL, $plaintextLanguage ) ),
|
||||
) );
|
||||
}
|
||||
}
|
||||
@@ -501,7 +513,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
else
|
||||
{
|
||||
return $plaintextLanguage->addToStack( 'promote_metadescription_node_nolink', NULL, array(
|
||||
'sprintf' => array( $object->_title, $author->name )
|
||||
'sprintf' => array( $object->getTitleForLanguage( $plaintextLanguage ), $author->name )
|
||||
) );
|
||||
}
|
||||
}
|
||||
@@ -512,7 +524,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
/**
|
||||
* Get reactions class for this object
|
||||
*
|
||||
* @return array|null
|
||||
* @return \IPS\Content\Reactable|null
|
||||
*/
|
||||
public function get_objectReactionClass()
|
||||
{
|
||||
@@ -655,7 +667,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
public function imageObjects()
|
||||
{
|
||||
$photos = array();
|
||||
if ( count( $this->images ) )
|
||||
if ( \count( $this->images ) )
|
||||
{
|
||||
foreach( $this->images as $image )
|
||||
{
|
||||
@@ -666,7 +678,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
}
|
||||
}
|
||||
|
||||
if ( count( $this->media ) )
|
||||
if ( \count( $this->media ) )
|
||||
{
|
||||
foreach( $this->media as $media )
|
||||
{
|
||||
@@ -674,7 +686,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
}
|
||||
}
|
||||
|
||||
return ( count( $photos ) ) ? $photos : NULL;
|
||||
return ( \count( $photos ) ) ? $photos : NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -726,7 +738,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
* Shorten URL.
|
||||
*
|
||||
* @param string $service Service key, (such as facebook or twitter)
|
||||
* @returns boolean
|
||||
* @return boolean
|
||||
*/
|
||||
public function serviceFailed( $service )
|
||||
{
|
||||
@@ -772,12 +784,12 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
$allText[ $service ] = $text;
|
||||
$this->text = $allText;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Return the published URL for this post
|
||||
*
|
||||
* @param string $service Service key, (such as facebook or twitter)
|
||||
* @returns string|NULL
|
||||
* @param string $service Service key, (such as facebook or twitter)
|
||||
* @return string|NULL
|
||||
*/
|
||||
public function getPublishedUrl( $service )
|
||||
{
|
||||
@@ -822,7 +834,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return count( $responses ) ? $responses : NULL;
|
||||
return \count( $responses ) ? $responses : NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -842,7 +854,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
}
|
||||
}
|
||||
|
||||
return count( $this->history[ $this->id ] ) ? $this->history[ $this->id ] : NULL;
|
||||
return \count( $this->history[ $this->id ] ) ? $this->history[ $this->id ] : NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -920,6 +932,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
* @param object $object Object (node or content item)
|
||||
* @param NULL|\IPS\Member $member Member object or NULL for current member
|
||||
* @return boolean
|
||||
* @throws \OutOfRangeException
|
||||
*/
|
||||
public static function objectCanView( $object, $member=NULL )
|
||||
{
|
||||
@@ -934,7 +947,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
return $object->can( 'view', $member );
|
||||
}
|
||||
|
||||
throw new \OutofRangeException('object_not_valid');
|
||||
throw new \OutOfRangeException('object_not_valid');
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -964,7 +977,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
}
|
||||
}
|
||||
|
||||
return count( $groups ) ? $groups : NULL;
|
||||
return \count( $groups ) ? $groups : NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1080,7 +1093,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
* @param integer $id Item ID
|
||||
* @param boolean $sent Only look for sent items
|
||||
* @param boolean $futureScheduled Only look for future scheduled items
|
||||
* @return \IPS\core\Promote item
|
||||
* @return static Item
|
||||
*/
|
||||
public static function loadByClassAndId( $class, $id, $sent=FALSE, $futureScheduled=FALSE )
|
||||
{
|
||||
@@ -1126,7 +1139,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
* We only have bit.ly as a shortener at the moment.
|
||||
*
|
||||
* @param string $longUrl The original URL
|
||||
* @returns string NULL if no shortnener available or it fails
|
||||
* @return string NULL if no shortnener available or it fails
|
||||
* @throws \RuntimeException if shortener fails
|
||||
* @throws \UnderflowException if no shortener available
|
||||
*/
|
||||
@@ -1154,7 +1167,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
throw new \RuntimeException;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get the next auto schedule timestamp
|
||||
*
|
||||
@@ -1195,10 +1208,28 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
/* Still here? Then pick the earliest time for the next day */
|
||||
if ( $time === NULL )
|
||||
{
|
||||
$firstTime = array_shift( $times );
|
||||
list( $h, $m ) = explode( ':', $firstTime );
|
||||
|
||||
$time = $current->add( new \DateInterval( 'P1D' ) )->setTime( $h, $m );
|
||||
while( $time === NULL )
|
||||
{
|
||||
/* Set to midnight of current day */
|
||||
$current->setTime( 0, 0 );
|
||||
|
||||
/* We need to clone otherwise $test is always the same as $current */
|
||||
$test = clone $current;
|
||||
|
||||
foreach( $times as $entry )
|
||||
{
|
||||
list( $h, $m ) = explode( ':', $entry );
|
||||
$test->setTime( $h, $m );
|
||||
if ( ( $test->getTimeStamp() > time() ) and ( $current->getTimeStamp() <= $test->getTimeStamp() ) )
|
||||
{
|
||||
$time = $test;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Still here? */
|
||||
$current->add( new \DateInterval( 'P1D' ) );
|
||||
}
|
||||
}
|
||||
|
||||
return $time;
|
||||
@@ -1288,7 +1319,7 @@ class _Promote extends \IPS\Patterns\ActiveRecord
|
||||
}
|
||||
}
|
||||
|
||||
return count( $services ) ? $services : NULL;
|
||||
return \count( $services ) ? $services : NULL;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -339,6 +339,11 @@ class _Install
|
||||
$this->diagnostics = $diagnostics;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Custom Title
|
||||
*/
|
||||
protected $customTitle = NULL;
|
||||
|
||||
/**
|
||||
* Process
|
||||
*
|
||||
@@ -366,7 +371,7 @@ class _Install
|
||||
}
|
||||
$response = call_user_func( array( $this, "step{$step}" ), $data );
|
||||
|
||||
return array( $response, \IPS\Member::loggedIn()->language()->addToStack( 'install_step_' . $step ), ( ( ( 100/12 ) * $data[0] + ( ( 100/12 ) / 100 * $this->stepProgress ) ) ) ?: 1 );
|
||||
return array( $response, ( $this->customTitle ) ? $this->customTitle : \IPS\Member::loggedIn()->language()->addToStack( 'install_step_' . $step ), ( ( ( 100/12 ) * $data[0] + ( ( 100/12 ) / 100 * $this->stepProgress ) ) ) ?: 1 );
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -438,6 +443,8 @@ class _Install
|
||||
$data[2] = 0;
|
||||
}
|
||||
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_1_app'), $app, $data[2] );
|
||||
|
||||
if ( file_exists( \IPS\ROOT_PATH . "/applications/{$app}/data/schema.json" ) )
|
||||
{
|
||||
$schema = json_decode( file_get_contents( \IPS\ROOT_PATH . "/applications/{$app}/data/schema.json" ), TRUE );
|
||||
@@ -556,6 +563,7 @@ class _Install
|
||||
/* Get version data */
|
||||
if ( file_exists( \IPS\ROOT_PATH . "/applications/{$app}/data/versions.json" ) )
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_2_app'), $app );
|
||||
$versions = json_decode( file_get_contents( \IPS\ROOT_PATH . "/applications/{$app}/data/versions.json" ), TRUE );
|
||||
$keys = array_keys( $versions );
|
||||
|
||||
@@ -614,6 +622,7 @@ class _Install
|
||||
{
|
||||
return $this->appLoop( $data, function( $app )
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_3_app'), $app );
|
||||
\IPS\Application::load( $app )->installSettings();
|
||||
|
||||
if ( $app === 'core' )
|
||||
@@ -676,6 +685,7 @@ class _Install
|
||||
{
|
||||
return $this->appLoop( $data, function( $app )
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_5_app'), $app );
|
||||
\IPS\Application::load( $app )->installTasks();
|
||||
|
||||
} );
|
||||
@@ -738,7 +748,7 @@ class _Install
|
||||
{
|
||||
$data[2] = 0;
|
||||
}
|
||||
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_7_app'), $app, $data[2] );
|
||||
$inserted = \IPS\Application::load( $app )->installLanguages( $data[2], 250 );
|
||||
|
||||
if ( $inserted )
|
||||
@@ -763,6 +773,7 @@ class _Install
|
||||
{
|
||||
return $this->appLoop( $data, function( $app )
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_8_app'), $app );
|
||||
\IPS\Application::load( $app )->installEmailTemplates();
|
||||
} );
|
||||
}
|
||||
@@ -781,7 +792,8 @@ class _Install
|
||||
{
|
||||
$data[2] = 0;
|
||||
}
|
||||
|
||||
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_9_app'), $app, $data[2] );
|
||||
if( $data[2] == 0 )
|
||||
{
|
||||
\IPS\Application::load( $app )->installThemeSettings();
|
||||
@@ -817,6 +829,7 @@ class _Install
|
||||
$data[2] = 0;
|
||||
}
|
||||
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_10_app'), $app, $data[2] );
|
||||
$inserted = \IPS\Application::load( $app )->installJavascript( $data[2], 250 );
|
||||
|
||||
if ( $inserted )
|
||||
@@ -841,6 +854,7 @@ class _Install
|
||||
{
|
||||
return $this->appLoop( $data, function( $app )
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_11_app'), $app );
|
||||
\IPS\Application::load( $app )->installSearchKeywords();
|
||||
} );
|
||||
}
|
||||
@@ -865,7 +879,8 @@ class _Install
|
||||
{
|
||||
throw new \RuntimeException( sprintf( \IPS\Member::loggedIn()->language()->get("hook_file_not_writable"), \IPS\ROOT_PATH . '/plugins/hooks.php' ) );
|
||||
}
|
||||
|
||||
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('install_step_12_app'), $app );
|
||||
try
|
||||
{
|
||||
\IPS\Application::load( $app )->installHooks();
|
||||
|
||||
@@ -135,15 +135,23 @@ class _Upgrade
|
||||
|
||||
/* MySQL timeouts */
|
||||
$db = $db ?: \IPS\Db::i();
|
||||
$query = $db->query( "SHOW VARIABLES LIKE '%wait_timeout%'" );
|
||||
|
||||
while( $row = $query->fetch_assoc() )
|
||||
try
|
||||
{
|
||||
if ( $row['Variable_name'] == 'wait_timeout' AND $row['Value'] < 20 )
|
||||
$query = $db->query( "SHOW VARIABLES LIKE '%wait_timeout%'" );
|
||||
|
||||
while( $row = $query->fetch_assoc() )
|
||||
{
|
||||
$return['advice'][] = \IPS\Member::loggedIn()->language()->addToStack( 'requirements_mysql_timeout', FALSE, array( 'sprintf' => array( $row['Variable_name'], $row['Value'] ) ) );
|
||||
if ( $row['Variable_name'] == 'wait_timeout' AND $row['Value'] < 20 )
|
||||
{
|
||||
$return['advice'][] = \IPS\Member::loggedIn()->language()->addToStack( 'requirements_mysql_timeout', FALSE, array( 'sprintf' => array( $row['Variable_name'], $row['Value'] ) ) );
|
||||
}
|
||||
}
|
||||
}
|
||||
catch( \IPS\Db\Exception $e )
|
||||
{
|
||||
$return['advice'][] = $e->getMessage();
|
||||
}
|
||||
|
||||
return $return;
|
||||
}
|
||||
@@ -218,6 +226,9 @@ class _Upgrade
|
||||
/* Clear member menu cache */
|
||||
\IPS\Member::clearCreateMenu();
|
||||
|
||||
/* Clear javascript caches */
|
||||
\IPS\Output::clearJsFiles();
|
||||
|
||||
/* Clear widget caches */
|
||||
\IPS\Widget::deleteCaches();
|
||||
|
||||
@@ -674,6 +685,7 @@ class _Upgrade
|
||||
{
|
||||
return $this->appLoop( $data, function( $app ) use( $data )
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_2_app'), $app );
|
||||
$changesToMake = \IPS\Application::load( $app )->databaseCheck();
|
||||
if ( count( $changesToMake ) )
|
||||
{
|
||||
@@ -711,6 +723,7 @@ class _Upgrade
|
||||
|
||||
try
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_3_app'), $app );
|
||||
$application = \IPS\Application::load( $app );
|
||||
$application->installJsonData( TRUE );
|
||||
|
||||
@@ -774,7 +787,7 @@ class _Upgrade
|
||||
return $this->appLoop( $data, function( $app )
|
||||
{
|
||||
\IPS\Log::debug( "Installing settings, tasks and keywords for " . $app, 'upgrade' );
|
||||
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_4_app'), $app );
|
||||
\IPS\Application::load( $app )->installSettings();
|
||||
\IPS\Application::load( $app )->installTasks();
|
||||
\IPS\Application::load( $app )->installSearchKeywords();
|
||||
@@ -798,6 +811,7 @@ class _Upgrade
|
||||
|
||||
try
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_5_app'), $app, $data[2] );
|
||||
$inserted = \IPS\Application::load( $app )->installLanguages( $data[2], 250 );
|
||||
|
||||
\IPS\Log::debug( "Inserted language keys for " . $app . ", offset of " . $data[2], 'upgrade' );
|
||||
@@ -831,6 +845,7 @@ class _Upgrade
|
||||
{
|
||||
return $this->appLoop( $data, function( $app )
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_6_app'), $app );
|
||||
\IPS\Application::load( $app )->installEmailTemplates();
|
||||
} );
|
||||
}
|
||||
@@ -847,6 +862,7 @@ class _Upgrade
|
||||
{
|
||||
try
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_7_app'), $app );
|
||||
\IPS\Application::load( $app )->installThemeSettings( TRUE );
|
||||
}
|
||||
catch( \Exception $e )
|
||||
@@ -881,6 +897,7 @@ class _Upgrade
|
||||
try
|
||||
{
|
||||
/* Deletes old data from the database */
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_8_app'), $app );
|
||||
\IPS\Application::load( $app )->clearTemplates();
|
||||
}
|
||||
catch( \Exception $e )
|
||||
@@ -914,6 +931,7 @@ class _Upgrade
|
||||
|
||||
try
|
||||
{
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_9_app'), $app, $data[2] );
|
||||
$inserted = \IPS\Application::load( $app )->installTemplates( TRUE, $data[2], 150 );
|
||||
}
|
||||
catch( \Exception $e )
|
||||
@@ -951,7 +969,8 @@ class _Upgrade
|
||||
{
|
||||
$data[2] = 0;
|
||||
}
|
||||
|
||||
|
||||
$this->customTitle = sprintf( \IPS\Member::loggedIn()->language()->get('upgrade_step_10_app'), $app, $data[2] );
|
||||
$inserted = \IPS\Application::load( $app )->installJavascript( $data[2], 100 );
|
||||
|
||||
\IPS\Log::debug( "Installed javascript for " . $app, 'upgrade' );
|
||||
|
||||
@@ -212,4 +212,17 @@ class _Reply extends \IPS\Content\Comment implements \IPS\Content\Hideable
|
||||
{
|
||||
return 'status_reply_id';
|
||||
}
|
||||
|
||||
/**
|
||||
* Check Moderator Permission
|
||||
*
|
||||
* @param string $type 'edit', 'hide', 'unhide', 'delete', etc.
|
||||
* @param \IPS\Member|NULL $member The member to check for or NULL for the currently logged in member
|
||||
* @param \IPS\Node\Model|NULL $container The container
|
||||
* @return bool
|
||||
*/
|
||||
public static function modPermission( $type, \IPS\Member $member = NULL, \IPS\Node\Model $container = NULL )
|
||||
{
|
||||
return \IPS\core\Statuses\Status::modPermission( $type, $member, $container );
|
||||
}
|
||||
}
|
||||
@@ -764,4 +764,29 @@ class _Status extends \IPS\Content\Item implements \IPS\Content\Lockable, \IPS\C
|
||||
|
||||
return parent::canViewHiddenItems( $member, $container );
|
||||
}
|
||||
|
||||
/**
|
||||
* Check Moderator Permission
|
||||
*
|
||||
* @param string $type 'edit', 'hide', 'unhide', 'delete', etc.
|
||||
* @param \IPS\Member|NULL $member The member to check for or NULL for the currently logged in member
|
||||
* @param \IPS\Node\Model|NULL $container The container
|
||||
* @return bool
|
||||
*/
|
||||
public static function modPermission( $type, \IPS\Member $member = NULL, \IPS\Node\Model $container = NULL )
|
||||
{
|
||||
$return = parent::modPermission( $type, $member, $container );
|
||||
|
||||
if( $member !== NULL AND $return === FALSE )
|
||||
{
|
||||
$title = static::$title;
|
||||
|
||||
if ( $member->modPermission( "can_{$type}_{$title}" ) )
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
return $return;
|
||||
}
|
||||
}
|
||||
@@ -525,8 +525,8 @@ class _Stream extends \IPS\Node\Model
|
||||
}, NULL, NULL, 'stream_date_range' ) );
|
||||
|
||||
/* Default View */
|
||||
$form->add( new \IPS\Helpers\Form\Radio( 'stream_default_view', $this->default_view, TRUE, array( 'options' => array(
|
||||
'condensed' => 'stream_default_view_condensed',
|
||||
$form->add( new \IPS\Helpers\Form\Radio( 'stream_default_view', $this->default_view ?: 'expanded', TRUE, array( 'options' => array(
|
||||
'condensed' => 'stream_default_view_condensed',
|
||||
'expanded' => 'stream_default_view_expanded',
|
||||
) ) ) );
|
||||
|
||||
|
||||
@@ -62,7 +62,7 @@ class _Reason extends \IPS\Node\Model
|
||||
*/
|
||||
protected static $restrictions = array(
|
||||
'app' => 'core',
|
||||
'module' => 'membersettings',
|
||||
'module' => 'moderation',
|
||||
'prefix' => 'reasons_',
|
||||
);
|
||||
|
||||
|
||||
@@ -360,14 +360,6 @@ class _Warning extends \IPS\Content\Item
|
||||
\IPS\Output::i()->error( 'no_module_permission', '2C150/3', 403, '' );
|
||||
}
|
||||
|
||||
foreach( $values['warn_punishment'] AS $p )
|
||||
{
|
||||
if ( $values['warn_' . $p ] === NULL )
|
||||
{
|
||||
\IPS\Output::i()->error( 'no_warning_action_time', '1C150/2', 403, '' );
|
||||
}
|
||||
}
|
||||
|
||||
/* Work out points and expiry date */
|
||||
$this->expire_date = NULL;
|
||||
$this->points = $values['warn_points'];
|
||||
@@ -470,6 +462,15 @@ class _Warning extends \IPS\Content\Item
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* We do this after the action is checked because the moderator may not be able to override the action, in which case the actual values won't have been submitted */
|
||||
foreach( $values['warn_punishment'] AS $p )
|
||||
{
|
||||
if ( $values['warn_' . $p ] === NULL )
|
||||
{
|
||||
\IPS\Output::i()->error( 'no_warning_action_time', '1C150/2', 403, '' );
|
||||
}
|
||||
}
|
||||
|
||||
/* Set notes */
|
||||
$this->note_member = $values['warn_member_note'];
|
||||
|
||||
Reference in new issue
Block a user