diff --git a/phpBB/phpbb/version_helper.php b/phpBB/phpbb/version_helper.php index a1e66ba8fe..b5f493de9d 100644 --- a/phpBB/phpbb/version_helper.php +++ b/phpBB/phpbb/version_helper.php @@ -200,6 +200,45 @@ class version_helper }); } + /** + * Gets the latest version for the current branch the user is on + * + * @param bool $force_update Ignores cached data. Defaults to false. + * @param bool $force_cache Force the use of the cache. Override $force_update. + * @return string + * @throws \RuntimeException + */ + public function get_update_on_branch($force_update = false, $force_cache = false) + { + $versions = $this->get_versions_matching_stability($force_update, $force_cache); + + $self = $this; + $current_version = $this->current_version; + + // Filter out any versions less than to the current version + $versions = array_filter($versions, function($data) use ($self, $current_version) { + return $self->compare($data['current'], $current_version, '>='); + }); + + // Get the lowest version from the previous list. + return array_reduce($versions, function($value, $data) use ($self, $current_version) { + if ($value === null && $self->compare($data['current'], $current_version, '>=')) + { + + if (!$data['eol'] && (!$data['security'] || $self->compare($data['security'], $data['current'], '<='))) + { + return ($self->compare($data['current'], $current_version, '>')) ? $data : array(); + } + else + { + return null; + } + } + + return $value; + }); + } + /** * Obtains the latest version information * diff --git a/tests/version/version_test.php b/tests/version/version_test.php index 528f1602d6..b9a6cf19ab 100644 --- a/tests/version/version_test.php +++ b/tests/version/version_test.php @@ -332,4 +332,204 @@ class phpbb_version_helper_test extends phpbb_test_case $this->assertSame($expected, $version_helper->get_latest_on_current_branch()); } + + public function get_update_on_branch_data() + { + return array( + array( + '1.0.0', + array( + '1.0' => array( + 'current' => '1.0.1', + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array( + 'current' => '1.0.1', + ), + ), + array( + '1.0.1', + array( + '1.0' => array( + 'current' => '1.0.1', + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array(), + ), + array( + '1.0.1-a1', + array( + '1.0' => array( + 'current' => '1.0.1-a2', + ), + '1.1' => array( + 'current' => '1.1.0', + ), + ), + array( + 'current' => '1.0.1-a2', + ), + ), + array( + '1.1.0', + array( + '1.0' => array( + 'current' => '1.0.1', + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array( + 'current' => '1.1.1', + ), + ), + array( + '1.1.1', + array( + '1.0' => array( + 'current' => '1.0.1', + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array(), + ), + array( + '1.1.0-a1', + array( + '1.0' => array( + 'current' => '1.0.1', + ), + '1.1' => array( + 'current' => '1.1.0-a2', + ), + ), + array( + 'current' => '1.1.0-a2', + ), + ), + array( + '1.1.0', + array(), + null, + ), + // Latest safe release is 1.0.1 + array( + '1.0.0', + array( + '1.0' => array( + 'current' => '1.0.1', + 'security' => '1.0.1', + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array( + 'current' => '1.0.1', + 'security' => '1.0.1', + ), + ), + // Latest safe release is 1.0.0 + array( + '1.0.0', + array( + '1.0' => array( + 'current' => '1.0.1', + 'security' => '1.0.1', + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array( + 'current' => '1.0.1', + 'security' => '1.0.1', + ), + ), + // Latest safe release is 1.1.0 + array( + '1.0.0', + array( + '1.0' => array( + 'current' => '1.0.1', + 'security' => '1.1.0', + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array( + 'current' => '1.1.1', + ), + ), + // Latest 1.0 release is EOL + array( + '1.0.0', + array( + '1.0' => array( + 'current' => '1.0.1', + 'eol' => true, + ), + '1.1' => array( + 'current' => '1.1.1', + ), + ), + array( + 'current' => '1.1.1', + ), + ), + // All are EOL -- somewhat undefined behavior + array( + '1.0.0', + array( + '1.0' => array( + 'current' => '1.0.1', + 'eol' => true, + ), + '1.1' => array( + 'current' => '1.1.1', + 'eol' => true, + ), + ), + null, + ), + ); + } + + /** + * @dataProvider get_update_on_branch_data + */ + public function test_get_update_on_branch($current_version, $versions, $expected) + { + $version_helper = $this + ->getMockBuilder('\phpbb\version_helper') + ->setMethods(array( + 'get_versions_matching_stability', + )) + ->setConstructorArgs(array( + $this->cache, + new \phpbb\config\config(array( + 'version' => $current_version, + )), + new \phpbb\file_downloader(), + new \phpbb\user('\phpbb\datetime'), + )) + ->getMock() + ; + + $version_helper->expects($this->any()) + ->method('get_versions_matching_stability') + ->will($this->returnValue($versions)); + + $this->assertSame($expected, $version_helper->get_update_on_branch()); + } }