diff options
author | Thomas Bruederli <thomas@roundcube.net> | 2014-08-13 19:15:12 +0200 |
---|---|---|
committer | Thomas Bruederli <thomas@roundcube.net> | 2014-08-13 19:15:12 +0200 |
commit | 06fdaf88cb1a355e445294beba4a89d0209ac71e (patch) | |
tree | 53ce0a305a69773169b00bbeae92069d20d3403c | |
parent | 48e340a82938a83ff337eadb7d6d64c2b13acffe (diff) |
Extend rcmail::url() to produce absolute and fully qualified URLs
-rw-r--r-- | program/include/rcmail.php | 45 | ||||
-rw-r--r-- | tests/RcmailFunc.php | 85 | ||||
-rw-r--r-- | tests/phpunit.xml | 1 |
3 files changed, 123 insertions, 8 deletions
diff --git a/program/include/rcmail.php b/program/include/rcmail.php index ceb369af8..bb2346f5e 100644 --- a/program/include/rcmail.php +++ b/program/include/rcmail.php @@ -789,11 +789,13 @@ class rcmail extends rcube /** * Build a valid URL to this instance of Roundcube * - * @param mixed Either a string with the action or url parameters as key-value pairs + * @param mixed Either a string with the action or url parameters as key-value pairs + * @param boolean Build an URL absolute to document root + * @param boolean Create fully qualified URL including http(s):// and hostname * * @return string Valid application URL */ - public function url($p) + public function url($p, $absolute = false, $full = false) { if (!is_array($p)) { if (strpos($p, 'http') === 0) { @@ -803,14 +805,15 @@ class rcmail extends rcube $p = array('_action' => @func_get_arg(0)); } - $task = $p['_task'] ? $p['_task'] : ($p['task'] ? $p['task'] : $this->task); - $p['_task'] = $task; - unset($p['task']); + $pre = array(); + $task = $p['_task'] ?: ($p['task'] ?: $this->task); + $pre['_task'] = $task; + unset($p['task'], $p['_task']); - $url = './' . $this->filename; + $url = $this->filename; $delm = '?'; - foreach (array_reverse($p) as $key => $val) { + foreach (array_merge($pre, $p) as $key => $val) { if ($val !== '' && $val !== null) { $par = $key[0] == '_' ? $key : '_'.$key; $url .= $delm.urlencode($par).'='.urlencode($val); @@ -818,7 +821,33 @@ class rcmail extends rcube } } - return $url; + if ($absolute || $full) { + $prefix = ''; + + // prepend protocol://hostname:port + if ($full) { + $schema = 'http'; + $default_port = 80; + if (rcube_utils::https_check()) { + $schema = 'https'; + $default_port = 443; + } + $prefix = $schema . '://' . preg_replace('/:\d+$/', '', $_SERVER['HTTP_HOST']); + if ($_SERVER['SERVER_PORT'] != $default_port) { + $prefix .= ':' . $_SERVER['SERVER_PORT']; + } + } + + // add base path to this Roundcube installation + $base_path = preg_replace('![^/]+$!', '', strval($_SERVER['SCRIPT_NAME'])); + if ($base_path == '') $base_path = '/'; + $prefix .= $base_path; + } + else { + $prefix = './'; + } + + return $prefix . $url; } /** diff --git a/tests/RcmailFunc.php b/tests/RcmailFunc.php new file mode 100644 index 000000000..09b54b22c --- /dev/null +++ b/tests/RcmailFunc.php @@ -0,0 +1,85 @@ +<?php + +/** + * Test class to test rcmail class + * + * @package Tests + */ +class RcmailFunc extends PHPUnit_Framework_TestCase +{ + function setUp() + { + // set some HTTP env vars + $_SERVER['HTTP_HOST'] = 'mail.example.org'; + $_SERVER['SERVER_PORT'] = '443'; + $_SERVER['SCRIPT_NAME'] = '/sub/index.php'; + $_SERVER['HTTPS'] = true; + + rcmail::get_instance()->filename = ''; + } + + /** + * Class constructor + */ + function test_class() + { + $object = rcmail::get_instance(); + $this->assertInstanceOf('rcmail', $object, "Class singleton"); + } + + /** + * Test rcmail::url() + */ + function test_url() + { + $rcmail = rcmail::get_instance(); + $this->assertEquals( + './?_task=cli&_action=test', + $rcmail->url('test'), + "Action only" + ); + $this->assertEquals( + './?_task=cli&_action=test&_a=AA', + $rcmail->url(array('action' => 'test', 'a' => 'AA')), + "Unprefixed parameters" + ); + $this->assertEquals( + './?_task=cli&_action=test&_b=BB', + $rcmail->url(array('_action' => 'test', '_b' => 'BB', '_c' => null)), + "Prefixed parameters (skip empty)" + ); + $this->assertEquals( + '/sub/?_task=cli&_action=test&_mode=ABS', + $rcmail->url(array('_action' => 'test', '_mode' => 'ABS'), true), + "Absolute URL" + ); + + $this->assertEquals( + 'https://mail.example.org/sub/?_task=calendar&_action=test&_mode=FQ', + $rcmail->url(array('task' => 'calendar', '_action' => 'test', '_mode' => 'FQ'), true, true), + "Fully Qualified URL" + ); + + // with different SCRIPT_NAME values + $_SERVER['SCRIPT_NAME'] = 'index.php'; + $this->assertEquals( + '/?_task=cli&_action=test&_mode=ABS', + $rcmail->url(array('_action' => 'test', '_mode' => 'ABS'), true), + "Absolute URL (root)" + ); + $_SERVER['SCRIPT_NAME'] = ''; + $this->assertEquals( + '/?_task=cli&_action=test&_mode=ABS', + $rcmail->url(array('_action' => 'test', '_mode' => 'ABS'), true), + "Absolute URL (root)" + ); + + $_SERVER['HTTPS'] = false; + $_SERVER['SERVER_PORT'] = '8080'; + $this->assertEquals( + 'http://mail.example.org:8080/?_task=cli&_action=test&_mode=ABS', + $rcmail->url(array('_action' => 'test', '_mode' => 'ABS'), true, true), + "Full URL with port" + ); + } +} diff --git a/tests/phpunit.xml b/tests/phpunit.xml index 4d50ad6a0..5c27d0e0d 100644 --- a/tests/phpunit.xml +++ b/tests/phpunit.xml @@ -46,6 +46,7 @@ <file>Framework/VCard.php</file> <file>Framework/Washtml.php</file> <file>MailFunc.php</file> + <file>RcmailFunc.php</file> </testsuite> <testsuite name="Plugins Tests"> <file>./../plugins/acl/tests/Acl.php</file> |