aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--.gitlab-ci.yml47
-rw-r--r--Zotlabs/Lib/DReport.php6
-rw-r--r--Zotlabs/Lib/Libzot.php1
-rw-r--r--Zotlabs/Module/Chanview.php2
-rw-r--r--Zotlabs/Module/Dreport.php3
-rw-r--r--Zotlabs/Module/Embedphotos.php122
-rw-r--r--Zotlabs/Module/Group.php11
-rw-r--r--include/help.php26
-rwxr-xr-xinclude/plugin.php72
-rw-r--r--include/text.php64
-rw-r--r--tests/phpunit-pgsql.xml33
-rw-r--r--view/js/main.js11
-rwxr-xr-xview/tpl/group_edit.tpl1
13 files changed, 238 insertions, 161 deletions
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index 0b8e0430f..d162d57ba 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -11,13 +11,11 @@ variables:
MYSQL_DATABASE: hello_world_test
MYSQL_ROOT_PASSWORD: mysql
-
-services:
-- mysql:5.7
-
before_script:
+# prevent error installing buggy postgresql-client package
+- mkdir -p /usr/share/man/man1 /usr/share/man/man7
- apt-get update -yqq
-- apt-get install -yqq git mysql-server mysql-client libmcrypt-dev libpq-dev libcurl4-gnutls-dev libicu-dev libvpx-dev libjpeg-dev libpng-dev libxpm-dev zlib1g-dev libfreetype6-dev libxml2-dev libexpat1-dev libbz2-dev libgmp3-dev libldap2-dev unixodbc-dev libsqlite3-dev libaspell-dev libsnmp-dev libpcre3-dev libtidy-dev
+- apt-get install -yqq --no-install-recommends git mysql-client postgresql-client libmcrypt-dev libpq-dev libcurl4-gnutls-dev libicu-dev libvpx-dev libjpeg-dev libpng-dev libxpm-dev zlib1g-dev libfreetype6-dev libxml2-dev libexpat1-dev libbz2-dev libgmp3-dev libldap2-dev unixodbc-dev libaspell-dev libpcre3-dev libtidy-dev
# Install PHP extensions
- docker-php-ext-install mbstring mcrypt pdo_mysql pdo_pgsql curl json intl gd xml zip bz2 opcache
# Install & enable Xdebug for code coverage reports
@@ -25,12 +23,47 @@ before_script:
- docker-php-ext-enable xdebug
# Install and run Composer
- curl -sS https://getcomposer.org/installer | php
-- php composer.phar install
+# Install dev libraries from composer
+- php composer.phar install --no-progress
+# Configure PHP values, needed for phpunit code coverage HTML generation
+- echo "memory_limit = 256M" > /usr/local/etc/php/conf.d/hubzilla.ini
+
-# We test PHP7 with MySQL, but we allow it to fail
+# We test PHP7 with MySQL
test:php:mysql:
+ services:
+ - mysql:5.7
script:
- echo "USE $MYSQL_DATABASE; $(cat ./install/schema_mysql.sql)" | mysql --user=root --password="$MYSQL_ROOT_PASSWORD" --host=mysql "$MYSQL_DATABASE"
- echo "SHOW DATABASES;" | mysql --user=root --password="$MYSQL_ROOT_PASSWORD" --host=mysql "$MYSQL_DATABASE"
- echo "USE $MYSQL_DATABASE; SHOW TABLES;" | mysql --user=root --password="$MYSQL_ROOT_PASSWORD" --host=mysql "$MYSQL_DATABASE"
- vendor/bin/phpunit --configuration tests/phpunit.xml --coverage-text
+
+# test PHP7 with PostgreSQL
+test:php:postgres:
+ services:
+ - postgres:latest
+ variables:
+ POSTGRES_DB: ci-db
+ POSTGRES_USER: ci-user
+ POSTGRES_PASSWORD: ci-pass
+ script:
+ - export PGPASSWORD=$POSTGRES_PASSWORD
+ - psql --version
+ - psql -h "postgres" -U "$POSTGRES_USER" -d "$POSTGRES_DB" -c "SELECT VERSION();"
+ # Import hubzilla's DB schema
+ - psql -h "postgres" -U "$POSTGRES_USER" -v ON_ERROR_STOP=1 --quiet "$POSTGRES_DB" < ./install/schema_postgres.sql
+ # Show databases and relations/tables of hubzilla's database
+ #- psql -h "postgres" -U "$POSTGRES_USER" -l
+ #- psql -h "postgres" -U "$POSTGRES_USER" -d "$POSTGRES_DB" -c "\dt;"
+ # Run the actual tests
+ - vendor/bin/phpunit --configuration tests/phpunit-pgsql.xml --testdox
+ artifacts:
+ expire_in: 1 week
+ # Gitlab should show the results, but has problems parsing PHPUnit's junit file.
+ reports:
+ junit: tests/results/junit.xml
+ # Archive test results (coverage, testdox, junit)
+ name: "$CI_COMMIT_REF_SLUG-$CI_JOB_NAME"
+ paths:
+ - tests/results/
diff --git a/Zotlabs/Lib/DReport.php b/Zotlabs/Lib/DReport.php
index ef1ce2678..18087e29f 100644
--- a/Zotlabs/Lib/DReport.php
+++ b/Zotlabs/Lib/DReport.php
@@ -87,9 +87,11 @@ class DReport {
// Is the sender one of our channels?
- $c = q("select channel_id from channel where channel_hash = '%s' limit 1",
+ $c = q("select channel_id from channel where channel_hash = '%s' or channel_portable_id = '%s' limit 1",
+ dbesc($dr['sender']),
dbesc($dr['sender'])
);
+
if(! $c)
return false;
@@ -104,6 +106,8 @@ class DReport {
$rxchan = $dr['recipient'];
}
+
+
// is the recipient one of our connections, or do we want to store every report?
$pcf = get_pconfig($c[0]['channel_id'],'system','dreport_store_all');
diff --git a/Zotlabs/Lib/Libzot.php b/Zotlabs/Lib/Libzot.php
index 00dd13afb..a0f6e077a 100644
--- a/Zotlabs/Lib/Libzot.php
+++ b/Zotlabs/Lib/Libzot.php
@@ -995,6 +995,7 @@ class Libzot {
}
if(is_array($x) && array_key_exists('delivery_report',$x) && is_array($x['delivery_report'])) {
+
foreach($x['delivery_report'] as $xx) {
call_hooks('dreport_process',$xx);
if(is_array($xx) && array_key_exists('message_id',$xx) && DReport::is_storable($xx)) {
diff --git a/Zotlabs/Module/Chanview.php b/Zotlabs/Module/Chanview.php
index 779c7e646..2e653d030 100644
--- a/Zotlabs/Module/Chanview.php
+++ b/Zotlabs/Module/Chanview.php
@@ -106,7 +106,7 @@ class Chanview extends \Zotlabs\Web\Controller {
if (\App::$poi) {
$url = \App::$poi['xchan_url'];
- if(\App::$poi['xchan_network'] === 'zot') {
+ if(in_array(\App::$poi['xchan_network'], ['zot', 'zot6'])) {
$is_zot = true;
}
if(local_channel()) {
diff --git a/Zotlabs/Module/Dreport.php b/Zotlabs/Module/Dreport.php
index 16ae7941f..2c125b7a9 100644
--- a/Zotlabs/Module/Dreport.php
+++ b/Zotlabs/Module/Dreport.php
@@ -80,8 +80,9 @@ class Dreport extends \Zotlabs\Web\Controller {
return;
}
- $r = q("select * from dreport where dreport_xchan = '%s' and dreport_mid = '%s'",
+ $r = q("select * from dreport where (dreport_xchan = '%s' or dreport_xchan = '%s') and dreport_mid = '%s'",
dbesc($channel['channel_hash']),
+ dbesc($channel['channel_portable_id']),
dbesc($mid)
);
diff --git a/Zotlabs/Module/Embedphotos.php b/Zotlabs/Module/Embedphotos.php
index bcbb0e116..2df14c239 100644
--- a/Zotlabs/Module/Embedphotos.php
+++ b/Zotlabs/Module/Embedphotos.php
@@ -3,8 +3,10 @@
namespace Zotlabs\Module;
/**
- * @brief
+ * @brief Embedphoto endpoint.
*
+ * Provide an AJAX endpoint to fill the embedPhotoModal with folders and photos
+ * selection.
*/
class Embedphotos extends \Zotlabs\Web\Controller {
@@ -13,42 +15,42 @@ class Embedphotos extends \Zotlabs\Web\Controller {
}
/**
+ * @brief This is the POST destination for the embedphotos button.
*
- * This is the POST destination for the embedphotos button
- *
+ * @return string A JSON string.
*/
- function post() {
+ public function post() {
if (argc() > 1 && argv(1) === 'album') {
// API: /embedphotos/album
- $name = (x($_POST,'name') ? $_POST['name'] : null );
- if(!$name) {
+ $name = (x($_POST, 'name') ? $_POST['name'] : null );
+ if (!$name) {
json_return_and_die(array('errormsg' => 'Error retrieving album', 'status' => false));
}
$album = $this->embedphotos_widget_album(array('channel' => \App::get_channel(), 'album' => $name));
json_return_and_die(array('status' => true, 'content' => $album));
}
- if(argc() > 1 && argv(1) === 'albumlist') {
+ if (argc() > 1 && argv(1) === 'albumlist') {
// API: /embedphotos/albumlist
- $album_list = $this->embedphotos_album_list($a);
+ $album_list = $this->embedphotos_album_list();
json_return_and_die(array('status' => true, 'albumlist' => $album_list));
}
- if(argc() > 1 && argv(1) === 'photolink') {
+ if (argc() > 1 && argv(1) === 'photolink') {
// API: /embedphotos/photolink
- $href = (x($_POST,'href') ? $_POST['href'] : null );
- if(!$href) {
+ $href = (x($_POST, 'href') ? $_POST['href'] : null );
+ if (!$href) {
json_return_and_die(array('errormsg' => 'Error retrieving link ' . $href, 'status' => false));
}
- $resource_id = array_pop(explode("/", $href));
+ $resource_id = array_pop(explode('/', $href));
$r = q("SELECT obj from item where resource_type = 'photo' and resource_id = '%s' limit 1",
dbesc($resource_id)
);
- if(!$r) {
+ if (!$r) {
json_return_and_die(array('errormsg' => 'Error retrieving resource ' . $resource_id, 'status' => false));
}
$obj = json_decode($r[0]['obj'], true);
- if(x($obj,'body')) {
+ if (x($obj, 'body')) {
$photolink = $obj['body'];
- } elseif (x($obj,'bbcode')) {
+ } elseif (x($obj, 'bbcode')) {
$photolink = $obj['bbcode'];
} else {
json_return_and_die(array('errormsg' => 'Error retrieving resource ' . $resource_id, 'status' => false));
@@ -58,48 +60,51 @@ class Embedphotos extends \Zotlabs\Web\Controller {
}
/**
- * Copied from include/widgets.php::widget_album() with a modification to get the profile_uid from
- * the input array as in widget_item()
+ * @brief Get photos from an album.
+ *
+ * @see \\Zotlabs\\Widget\\Album::widget()
*
- * @param array $args
- * @return string with HTML
+ * @param array $args associative array with
+ * * \e array \b channel
+ * * \e string \b album
+ * @return string with HTML code from 'photo_album.tpl'
*/
- function embedphotos_widget_album($args) {
-
+ protected function embedphotos_widget_album($args) {
$channel_id = 0;
- if(array_key_exists('channel', $args))
+
+ if (array_key_exists('channel', $args)) {
$channel = $args['channel'];
- $channel_id = intval($channel['channel_id']);
- if(! $channel_id)
+ $channel_id = intval($channel['channel_id']);
+ }
+ if (! $channel_id)
$channel_id = \App::$profile_uid;
- if(! $channel_id)
+ if (! $channel_id)
return '';
- $owner_uid = $channel_id;
require_once('include/security.php');
$sql_extra = permissions_sql($channel_id);
- if(! perm_is_allowed($channel_id,get_observer_hash(),'view_storage'))
+ if (! perm_is_allowed($channel_id, get_observer_hash(), 'view_storage'))
return '';
- if($args['album'])
+ if (isset($args['album']))
$album = (($args['album'] === '/') ? '' : $args['album']);
- if($args['title'])
+ if (isset($args['title']))
$title = $args['title'];
/**
- * This may return incorrect permissions if you have multiple directories of the same name.
+ * @note This may return incorrect permissions if you have multiple directories of the same name.
* It is a limitation of the photo table using a name for a photo album instead of a folder hash
*/
- if($album) {
+ if ($album) {
require_once('include/attach.php');
$x = q("select hash from attach where filename = '%s' and uid = %d limit 1",
dbesc($album),
- intval($owner_uid)
+ intval($channel_id)
);
- if($x) {
- $y = attach_can_view_folder($owner_uid,get_observer_hash(),$x[0]['hash']);
- if(! $y)
+ if ($x) {
+ $y = attach_can_view_folder($channel_id, get_observer_hash(), $x[0]['hash']);
+ if (! $y)
return '';
}
}
@@ -110,30 +115,33 @@ class Embedphotos extends \Zotlabs\Web\Controller {
(SELECT resource_id, max(imgscale) imgscale FROM photo WHERE uid = %d AND album = '%s' AND imgscale <= 4 AND photo_usage IN ( %d, %d ) $sql_extra GROUP BY resource_id) ph
ON (p.resource_id = ph.resource_id AND p.imgscale = ph.imgscale)
ORDER BY created $order",
- intval($owner_uid),
+ intval($channel_id),
dbesc($album),
intval(PHOTO_NORMAL),
intval(PHOTO_PROFILE)
);
- $photos = array();
- if(count($r)) {
+ $photos = [];
+ if (count($r)) {
$twist = 'rotright';
- foreach($r as $rr) {
- if($twist == 'rotright')
+ foreach ($r as $rr) {
+ if ($twist == 'rotright')
$twist = 'rotleft';
else
$twist = 'rotright';
+ $ph = photo_factory('');
+ $phototypes = $ph->supportedTypes();
+
$ext = $phototypes[$rr['mimetype']];
$imgalt_e = $rr['filename'];
$desc_e = $rr['description'];
- $imagelink = (z_root() . '/photos/' . \App::$data['channel']['channel_address'] . '/image/' . $rr['resource_id']
+ $imagelink = (z_root() . '/photos/' . $channel['channel_address'] . '/image/' . $rr['resource_id']
. (($_GET['order'] === 'posted') ? '?f=&order=posted' : ''));
- $photos[] = array(
+ $photos[] = [
'id' => $rr['id'],
'twist' => ' ' . $twist . rand(2,4),
'link' => $imagelink,
@@ -143,35 +151,43 @@ class Embedphotos extends \Zotlabs\Web\Controller {
'desc'=> $desc_e,
'ext' => $ext,
'hash'=> $rr['resource_id'],
- 'unknown' => t('Unknown')
- );
+ 'unknown' => t('Unknown'),
+ ];
}
}
$tpl = get_markup_template('photo_album.tpl');
- $o .= replace_macros($tpl, array(
+ $o = replace_macros($tpl, [
'$photos' => $photos,
'$album' => (($title) ? $title : $album),
'$album_id' => rand(),
- '$album_edit' => array(t('Edit Album'), $album_edit),
+ '$album_edit' => array(t('Edit Album'), false),
'$can_post' => false,
'$upload' => array(t('Upload'), z_root() . '/photos/' . \App::$profile['channel_address'] . '/upload/' . bin2hex($album)),
'$order' => false,
- '$upload_form' => $upload_form,
- '$no_fullscreen_btn' => true
- ));
+ '$upload_form' => '',
+ '$no_fullscreen_btn' => true,
+ ]);
return $o;
}
- function embedphotos_album_list($a) {
+ /**
+ * @brief Get albums observer is allowed to see.
+ *
+ * @see photos_albums_list()
+ *
+ * @return NULL|array
+ */
+ protected function embedphotos_album_list() {
require_once('include/photos.php');
$p = photos_albums_list(\App::get_channel(), \App::get_observer());
- if($p['success']) {
+
+ if ($p['success']) {
return $p['albums'];
- } else {
- return null;
}
+
+ return null;
}
}
diff --git a/Zotlabs/Module/Group.php b/Zotlabs/Module/Group.php
index 3dcf903ad..12edf8428 100644
--- a/Zotlabs/Module/Group.php
+++ b/Zotlabs/Module/Group.php
@@ -66,6 +66,9 @@ class Group extends Controller {
$groupname = notags(trim($_POST['groupname']));
$public = intval($_POST['public']);
+ $hookinfo = [ 'pgrp_extras' => '', 'group'=>$group['id'] ];
+ call_hooks ('privacygroup_extras_post',$hookinfo);
+
if((strlen($groupname)) && (($groupname != $group['gname']) || ($public != $group['visible']))) {
$r = q("UPDATE pgrp SET gname = '%s', visible = %d WHERE uid = %d AND id = %d",
dbesc($groupname),
@@ -76,8 +79,6 @@ class Group extends Controller {
if($r)
info( t('Privacy group updated.') . EOL );
- $hookinfo = [ 'pgrp_extras' => '', 'group'=>$group['id'] ];
- call_hooks ('privacygroup_extras_post',$hookinfo);
build_sync_packet(local_channel(),null,true);
}
@@ -242,6 +243,10 @@ class Group extends Controller {
}
}
+ $hookinfo = [ 'pgrp_extras' => '', 'group'=>$group['id'] ];
+ call_hooks ('privacygroup_extras',$hookinfo);
+ $pgrp_extras = $hookinfo['pgrp_extras'];
+
$context = $context + array(
'$title' => sprintf(t('Privacy Group: %s'), $group['gname']),
'$details_label' => t('Edit'),
@@ -252,6 +257,7 @@ class Group extends Controller {
'$form_security_token_edit' => get_form_security_token('group_edit'),
'$delete' => t('Delete Group'),
'$form_security_token_drop' => get_form_security_token("group_drop"),
+ '$pgrp_extras' => $pgrp_extras,
);
}
@@ -295,6 +301,7 @@ class Group extends Controller {
$context['$groupeditor'] = $groupeditor;
$context['$desc'] = t('Click a channel to toggle membership');
+ $context['$pgrp_extras'] = $pgrp_extras;
if($change) {
$tpl = get_markup_template('groupeditor.tpl');
diff --git a/include/help.php b/include/help.php
index f2aa4add3..61dbc7bb3 100644
--- a/include/help.php
+++ b/include/help.php
@@ -12,12 +12,12 @@ use \Michelf\MarkdownExtra;
function get_help_fullpath($path,$suffix=null) {
$docroot = (\App::$override_helproot) ? \App::$override_helproot : 'doc/';
- $docroot = (substr($docroot,-1)!='/') ? $docroot .= '/' : $docroot;
+ $docroot = (substr($docroot,-1)!='/') ? $docroot .= '/' : $docroot;
// Determine the language and modify the path accordingly
$x = determine_help_language();
$lang = $x['language'];
- $url_idx = ($x['from_url'] ? 1 : 0);
+
// The English translation is at the root of /doc/. Other languages are in
// subfolders named by the language code such as "de", "es", etc.
if($lang !== 'en') {
@@ -53,15 +53,14 @@ function get_help_fullpath($path,$suffix=null) {
* @return string|unknown
*/
function get_help_content($tocpath = false) {
- global $lang;
$doctype = 'markdown';
$text = '';
$path = (($tocpath !== false) ? $tocpath : '');
- $docroot = (\App::$override_helproot) ? \App::$override_helproot : 'doc/';
- $docroot = (substr($docroot,-1)!='/') ? $docroot .= '/' : $docroot;
+ $docroot = (\App::$override_helproot) ? \App::$override_helproot : 'doc/';
+ $docroot = (substr($docroot,-1)!='/') ? $docroot .= '/' : $docroot;
if($tocpath === false && argc() > 1) {
$path = '';
@@ -74,7 +73,7 @@ function get_help_content($tocpath = false) {
if($path) {
- $fullpath = get_help_fullpath($path);
+ $fullpath = get_help_fullpath($path);
$title = basename($path);
if(! $tocpath)
\App::$page['title'] = t('Help:') . ' ' . ucwords(str_replace('-',' ',notags($title)));
@@ -88,10 +87,10 @@ function get_help_content($tocpath = false) {
load_doc_file($fullpath . '.md') === '' &&
load_doc_file($fullpath . '.bb') === '' &&
load_doc_file($fullpath . '.html') === ''
- ) {
+ ) {
$path = $title;
}
- $fullpath = get_help_fullpath($path);
+ $fullpath = get_help_fullpath($path);
$text = load_doc_file($fullpath . '.md');
if(! $text) {
@@ -111,15 +110,15 @@ function get_help_content($tocpath = false) {
if($tocpath === false) {
if(! $text) {
- $path = 'Site';
- $fullpath = get_help_fullpath($path,'.md');
+ $path = 'Site';
+ $fullpath = get_help_fullpath($path,'.md');
$text = load_doc_file($fullpath . '.md');
\App::$page['title'] = t('Help');
}
if(! $text) {
$doctype = 'bbcode';
- $path = 'main';
- $fullpath = get_help_fullpath($path,'.md');
+ $path = 'main';
+ $fullpath = get_help_fullpath($path,'.md');
$text = load_doc_file($fullpath . '.bb');
goaway('/help/about/about');
\App::$page['title'] = t('Help');
@@ -219,7 +218,6 @@ function find_doc_file($s) {
*/
function search_doc_files($s) {
-
\App::set_pager_itemspage(60);
$pager_sql = sprintf(" LIMIT %d OFFSET %d ", intval(\App::$pager['itemspage']), intval(\App::$pager['start']));
@@ -351,7 +349,7 @@ function store_doc_file($s) {
$x = item_store_update($item);
}
else {
- $item['uuid'] = $item_message_id();
+ $item['uuid'] = item_message_id();
$item['mid'] = $item['parent_mid'] = z_root() . '/item/' . $item['uuid'];
$x = item_store($item);
}
diff --git a/include/plugin.php b/include/plugin.php
index 7eeb39ce8..ec14fd945 100755
--- a/include/plugin.php
+++ b/include/plugin.php
@@ -213,8 +213,8 @@ function reload_plugins() {
try {
$func();
} catch (Exception $e) {
- handleerrors_plugin($plugin,"","UNLOAD FAILED (uninstalling) : ".$e->getMessage(),true);
- continue;
+ handleerrors_plugin($pl, '', 'UNLOAD FAILED (uninstalling) : ' . $e->getMessage(),true);
+ continue;
}
}
if(function_exists($pl . '_load')) {
@@ -222,8 +222,8 @@ function reload_plugins() {
try {
$func();
} catch (Exception $e) {
- handleerrors_plugin($plugin,"","LOAD FAILED (uninstalling): ".$e->getMessage(),true);
- continue;
+ handleerrors_plugin($pl, '', 'LOAD FAILED (uninstalling): ' . $e->getMessage(),true);
+ continue;
}
}
q("UPDATE addon SET tstamp = %d WHERE id = %d",
@@ -305,7 +305,7 @@ function plugins_sync() {
* @return array
*/
function visible_plugin_list() {
-
+
$r = q("select * from addon where hidden = 0 order by aname asc");
$x = (($r) ? ids_to_array($r,'aname') : array());
$y = [];
@@ -315,7 +315,7 @@ function visible_plugin_list() {
$y[] = $xv;
}
}
- }
+ }
return $y;
}
@@ -456,21 +456,21 @@ function insert_hook($hook, $fn, $version = 0, $priority = 0) {
function call_hooks($name, &$data = null) {
$a = 0;
- if (isset(App::$hooks[$name])) {
+ if (isset(App::$hooks[$name])) {
foreach(App::$hooks[$name] as $hook) {
if ($name != 'permit_hook') { // avoid looping
$checkhook = [
- 'name'=>$name,
- 'hook'=>$hook,
- 'data'=>$data,
+ 'name'=>$name,
+ 'hook'=>$hook,
+ 'data'=>$data,
// Note: Since PHP uses COPY-ON-WRITE
- // for variables, there is no cost to
+ // for variables, there is no cost to
// passing the $data structure (unless
// the permit_hook processors change the
// information it contains.
- 'permit'=>true
- ];
+ 'permit'=>true
+ ];
call_hooks('permit_hook',$checkhook);
if (!$checkhook['permit']) {
continue;
@@ -618,7 +618,7 @@ function get_widget_info($widget){
}
}
- if(! ($widget_found && $f))
+ if(! ($widget_found && $f))
return $info;
$f = escape_tags($f);
@@ -1041,7 +1041,7 @@ function get_intltext_template($s, $root = '') {
if (isset(\App::$override_intltext_templates[$testroot][$s]["content"])) {
return \App::$override_intltext_templates[$testroot][$s]["content"];
} else {
- if (isset(\App::$override_intltext_templates[$testroot][$s]["root"]) &&
+ if (isset(\App::$override_intltext_templates[$testroot][$s]["root"]) &&
isset(\App::$override_intltext_templates[$testroot][$s]["file"])) {
$s = \App::$override_intltext_templates[$testroot][$s]["file"];
$root = \App::$override_intltext_templates[$testroot][$s]["root"];
@@ -1058,30 +1058,30 @@ function get_intltext_template($s, $root = '') {
}
function get_markup_template($s, $root = '') {
- $testroot = ($root=='') ? $testroot = "ROOT" : $root;
+ $testroot = ($root=='') ? $testroot = "ROOT" : $root;
- $t = App::template_engine();
+ $t = App::template_engine();
- if (isset(\App::$override_markup_templates[$testroot][$s]["content"])) {
- return \App::$override_markup_templates[$testroot][$s]["content"];
- } else {
- if (isset(\App::$override_markup_templates[$testroot][$s]["root"]) &&
- isset(\App::$override_markup_templates[$testroot][$s]["file"])) {
- $root = \App::$override_markup_templates[$testroot][$s]["root"];
- $s = \App::$override_markup_templates[$testroot][$s]["file"];
- $template = $t->get_markup_template($s, $root);
- } elseif (\App::$override_templateroot) {
- $newroot = \App::$override_templateroot;
- if ($newroot != '' && substr($newroot,-1) != '/' ) {
- $newroot .= '/';
- }
- $newroot .= $root;
- $template = $t->get_markup_template($s, $newroot);
- } else {
- $template = $t->get_markup_template($s, $root);
+ if (isset(\App::$override_markup_templates[$testroot][$s]["content"])) {
+ return \App::$override_markup_templates[$testroot][$s]["content"];
+ } else {
+ if (isset(\App::$override_markup_templates[$testroot][$s]["root"]) &&
+ isset(\App::$override_markup_templates[$testroot][$s]["file"])) {
+ $root = \App::$override_markup_templates[$testroot][$s]["root"];
+ $s = \App::$override_markup_templates[$testroot][$s]["file"];
+ $template = $t->get_markup_template($s, $root);
+ } elseif (\App::$override_templateroot) {
+ $newroot = \App::$override_templateroot;
+ if ($newroot != '' && substr($newroot,-1) != '/' ) {
+ $newroot .= '/';
+ }
+ $newroot .= $root;
+ $template = $t->get_markup_template($s, $newroot);
+ } else {
+ $template = $t->get_markup_template($s, $root);
}
- return $template;
- }
+ return $template;
+ }
}
/**
diff --git a/include/text.php b/include/text.php
index 26cb61977..6ac04f435 100644
--- a/include/text.php
+++ b/include/text.php
@@ -825,6 +825,9 @@ function get_tags($s) {
// ignore anything in [color= ], because it may contain color codes which are mistaken for tags
$s = preg_replace('/\[color=(.*?)\]/sm','',$s);
+
+ // skip anchors in URL
+ $s = preg_replace('/\[url=(.*?)\]/sm','',$s);
// match any double quoted tags
@@ -983,7 +986,7 @@ function contact_block() {
// There is no setting to discover if you are bi-directionally connected
// Use the ability to post comments as an indication that this relationship is more
- // than wishful thinking; even though soapbox channels and feeds will disable it.
+ // than wishful thinking; even though soapbox channels and feeds will disable it.
if(! intval(get_abconfig(App::$profile['uid'],$rr['xchan_hash'],'their_perms','post_comments'))) {
$rr['oneway'] = true;
@@ -1109,19 +1112,19 @@ function linkify($s, $me = false) {
* @returns string
*/
function sslify($s) {
-
+
// Local photo cache
$str = array(
'body' => $s,
'uid' => local_channel()
);
call_hooks('cache_body_hook', $str);
-
+
$s = $str['body'];
if (strpos(z_root(),'https:') === false)
return $s;
-
+
// By default we'll only sslify img tags because media files will probably choke.
// You can set sslify_everything if you want - but it will likely white-screen if it hits your php memory limit.
// The downside is that http: media files will likely be blocked by your browser
@@ -1452,7 +1455,7 @@ function theme_attachments(&$item) {
foreach($arr as $r) {
$icon = getIconFromType($r['type']);
-
+
if($r['title'])
$label = urldecode(htmlspecialchars($r['title'], ENT_COMPAT, 'UTF-8'));
@@ -1729,17 +1732,24 @@ function prepare_binary($item) {
/**
- * @brief Given a text string, convert from bbcode to html and add smilie icons.
+ * @brief Given a text string, convert from content_type to HTML.
*
- * @param string $text
- * @param string $content_type (optional) default text/bbcode
- * @param boolean $cache (optional) default false
+ * Take a text in plain text, html, markdown, bbcode, PDL or PHP and prepare
+ * it to return HTML.
*
+ * In bbcode this function will add smilie icons.
+ *
+ * @param string $text
+ * @param string $content_type (optional)
+ * default 'text/bbcode', other values are 'text/plain', 'text/html',
+ * 'text/markdown', 'application/x-pdl', 'application/x-php'
+ * @param boolean|array $opts (optional)
+ * default false, otherwise configuration array for bbcode()
* @return string
+ * The parsed $text as prepared HTML.
*/
function prepare_text($text, $content_type = 'text/bbcode', $opts = false) {
-
switch($content_type) {
case 'text/plain':
$s = escape_tags($text);
@@ -1779,8 +1789,8 @@ function prepare_text($text, $content_type = 'text/bbcode', $opts = false) {
default:
require_once('include/bbcode.php');
- if(stristr($text,'[nosmile]'))
- $s = bbcode($text, [ 'cache' => $cache ]);
+ if(stristr($text, '[nosmile]'))
+ $s = bbcode($text, ((is_array($opts)) ? $opts : [] ));
else
$s = smilies(bbcode($text, ((is_array($opts)) ? $opts : [] )));
@@ -2140,7 +2150,7 @@ function legal_webbie($s) {
return '';
// WARNING: This regex may not work in a federated environment.
- // You will probably want something like
+ // You will probably want something like
// preg_replace('/([^a-z0-9\_])/','',strtolower($s));
$r = preg_replace('/([^a-z0-9\-\_])/','',strtolower($s));
@@ -2240,7 +2250,7 @@ function ids_to_querystr($arr,$idx = 'id',$quote = false) {
/**
* @brief array_elm_to_str($arr,$elm,$delim = ',') extract unique individual elements from an array of arrays and return them as a string separated by a delimiter
- * similar to ids_to_querystr, but allows a different delimiter instead of a db-quote option
+ * similar to ids_to_querystr, but allows a different delimiter instead of a db-quote option
* empty elements (evaluated after trim()) are ignored.
* @param $arr array
* @param $elm array key to extract from sub-array
@@ -2666,7 +2676,7 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $i
// get the channel name
// First extract the name or name fragment we are going to replace
- $name = substr($tag,(($exclusive) ? 2 : 1));
+ $name = substr($tag,(($exclusive) ? 2 : 1));
$newname = $name; // make a copy that we can mess with
$tagcid = 0;
@@ -2709,7 +2719,7 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $i
// select anybody by full hubloc_addr
if((! $r) && strpos($newname,'@')) {
- $r = q("SELECT * FROM xchan left join hubloc on xchan_hash = hubloc_hash
+ $r = q("SELECT * FROM xchan left join hubloc on xchan_hash = hubloc_hash
WHERE hubloc_addr = '%s' LIMIT 1",
dbesc($newname)
);
@@ -2730,7 +2740,7 @@ function handle_tag($a, &$body, &$access_tag, &$str_tags, $profile_uid, $tag, $i
// $r is set if we found something
$channel = App::get_channel();
-
+
if($r) {
$profile = $r[0]['xchan_url'];
$newname = $r[0]['xchan_name'];
@@ -2875,7 +2885,7 @@ function getIconFromType($type) {
'video/x-matroska' => 'fa-file-video-o'
);
- $catMap = [
+ $catMap = [
'application' => 'fa-file-code-o',
'multipart' => 'fa-folder',
'audio' => 'fa-file-audio-o',
@@ -2883,7 +2893,7 @@ function getIconFromType($type) {
'text' => 'fa-file-text-o',
'image' => 'fa=file-picture-o',
'message' => 'fa-file-text-o'
- ];
+ ];
$iconFromType = '';
@@ -2893,7 +2903,7 @@ function getIconFromType($type) {
}
else {
$parts = explode('/',$type);
- if($parts[0] && $catMap[$parts[0]]) {
+ if($parts[0] && $catMap[$parts[0]]) {
$iconFromType = $catMap[$parts[0]];
}
}
@@ -3149,7 +3159,7 @@ function flatten_array_recursive($arr) {
* @param string $lang Which language should be highlighted
* @return string
* Important: The returned text has the text pattern 'http' translated to '%eY9-!' which should be converted back
- * after further processing. This was done to prevent oembed links from occurring inside code blocks.
+ * after further processing. This was done to prevent oembed links from occurring inside code blocks.
* See include/bbcode.php
*/
function text_highlight($s, $lang) {
@@ -3383,7 +3393,7 @@ function unique_multidim_array($array, $key) {
$temp_array = array();
$i = 0;
$key_array = array();
-
+
foreach($array as $val) {
if (!in_array($val[$key], $key_array)) {
$key_array[$i] = $val[$key];
@@ -3411,7 +3421,7 @@ function get_forum_channels($uid) {
intval($uid)
);
- if($x2) {
+ if($x2) {
$xf = ids_to_querystr($x2,'xchan',true);
// private forums
@@ -3424,7 +3434,7 @@ function get_forum_channels($uid) {
}
}
- $sql_extra = (($xf) ? " and ( xchan_hash in (" . $xf . ") or xchan_pubforum = 1 ) " : " and xchan_pubforum = 1 ");
+ $sql_extra = (($xf) ? " and ( xchan_hash in (" . $xf . ") or xchan_pubforum = 1 ) " : " and xchan_pubforum = 1 ");
$r = q("select abook_id, xchan_hash, xchan_name, xchan_url, xchan_addr, xchan_photo_s from abook left join xchan on abook_xchan = xchan_hash where xchan_deleted = 0 and abook_channel = %d and abook_pending = 0 and abook_ignored = 0 and abook_blocked = 0 and abook_archived = 0 $sql_extra order by xchan_name",
intval($uid)
@@ -3460,14 +3470,14 @@ function print_array($arr, $level = 0) {
$o .= $tabs . '[' . $k . '] => ' . print_array($v, $level + 1) . "\n";
}
else {
- $o .= $tabs . '[' . $k . '] => ' . print_val($v) . ",\n";
+ $o .= $tabs . '[' . $k . '] => ' . print_val($v) . ",\n";
}
}
}
$o .= substr($tabs,0,-1) . ']' . (($level) ? ',' : ';' ). "\n";
return $o;
}
-
+
}
function print_val($v) {
@@ -3494,7 +3504,7 @@ function array_path_exists($str,$arr) {
}
else {
return false;
- }
+ }
}
return true;
}
diff --git a/tests/phpunit-pgsql.xml b/tests/phpunit-pgsql.xml
index 078056d56..8b11aae31 100644
--- a/tests/phpunit-pgsql.xml
+++ b/tests/phpunit-pgsql.xml
@@ -1,24 +1,26 @@
<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
- xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/6.0/phpunit.xsd"
+ xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/7.5/phpunit.xsd"
bootstrap="../boot.php"
forceCoversAnnotation="false"
beStrictAboutCoversAnnotation="true"
beStrictAboutOutputDuringTests="true"
beStrictAboutTodoAnnotatedTests="true"
verbose="true">
- <testsuite name="Hubzilla default Test Suite">
- <directory suffix="Test.php">./unit/</directory>
- </testsuite>
- <testsuite name="API Test Suite">
- <directory suffix="Test.php" prefix="API">./unit/</directory>
- </testsuite>
+ <testsuites>
+ <testsuite name="Hubzilla default Test Suite">
+ <directory suffix="Test.php">./unit/</directory>
+ </testsuite>
+ <testsuite name="API Test Suite">
+ <directory suffix="Test.php" prefix="API">./unit/</directory>
+ </testsuite>
+ </testsuites>
<groups>
<exclude>
<group>mysql</group>
</exclude>
</groups>
- <!--cover reporting-->
+ <!--coverage reporting-->
<filter>
<whitelist processUncoveredFilesFromWhitelist="true">
<directory suffix=".php">../Zotlabs/</directory>
@@ -26,21 +28,22 @@
</whitelist>
</filter>
<logging>
- <log type="junit" target="./results/junit.xml" logIncompleteSkipped="false"/>
- <log type="coverage-clover" target="./results/coverage-clover.xml"/>
+ <log type="junit" target="./results/junit.xml"/>
+ <!--<log type="coverage-clover" target="./results/coverage-clover.xml"/>-->
<log type="coverage-html" target="./results/coverage-report/" lowUpperBound="35"
highLowerBound="70"/>
- <log type="testdox-text" target="./results/testdox.txt"/>
+ <!--<log type="testdox-text" target="./results/testdox.txt"/>-->
+ <log type="testdox-html" target="./results/testdox.html"/>
</logging>
<php>
<!-- Default test database config, only used if no environment variables
with same names are set.
!!! Never run against a real database, it will truncate all tables -->
- <env name="hz_db_server" value="127.0.0.1"/>
+ <env name="hz_db_server" value="postgres"/>
<env name="hz_db_scheme" value="pgsql"/>
<env name="hz_db_port" value="5432"/>
- <env name="hz_db_user" value="travis_hz"/>
- <env name="hz_db_pass" value="hubzilla"/>
- <env name="hz_db_database" value="travis_hubzilla"/>
+ <env name="hz_db_user" value="ci-user"/>
+ <env name="hz_db_pass" value="ci-pass"/>
+ <env name="hz_db_database" value="ci-db"/>
</php>
</phpunit>
diff --git a/view/js/main.js b/view/js/main.js
index 017d39353..fca9d125d 100644
--- a/view/js/main.js
+++ b/view/js/main.js
@@ -468,6 +468,9 @@ function notificationsUpdate(cached_data) {
$.get(pingCmd,function(data) {
// Put the object into storage
+ if(! data)
+ return;
+
sessionStorage.setItem('notifications_cache', JSON.stringify(data));
var fnotifs = [];
@@ -766,7 +769,7 @@ function updateConvItems(mode,data) {
mediaPlaying = false;
});
- var bimgs = ((preloadImages) ? false : $(".wall-item-body img").not(function() { return this.complete; }));
+ var bimgs = ((preloadImages) ? false : $(".wall-item-body img, .wall-photo-item img").not(function() { return this.complete; }));
var bimgcount = bimgs.length;
if (bimgcount) {
@@ -842,10 +845,10 @@ function collapseHeight() {
});
var collapsedContentHeight = Math.ceil($("#region_2").height());
- contentHeightDiff = origContentHeight - collapsedContentHeight;
+ contentHeightDiff = liking ? 0 : origContentHeight - collapsedContentHeight;
console.log('collapseHeight() - contentHeightDiff: ' + contentHeightDiff + 'px');
- if(i){
+ if(i && !liking){
var sval = position - cDiff + ($(".divgrow-showmore").outerHeight() * i);
console.log('collapsed above viewport count: ' + i);
$(window).scrollTop(sval);
@@ -996,7 +999,7 @@ function liveUpdate(notify_id) {
$("#profile-jot-text-loading").hide();
// adjust scroll position if new content was added above viewport
- if(update_mode === 'update') {
+ if(update_mode === 'update' && !justifiedGalleryActive) {
$(window).scrollTop($(window).scrollTop() + $("#region_2").height() - orgHeight + contentHeightDiff);
}
diff --git a/view/tpl/group_edit.tpl b/view/tpl/group_edit.tpl
index 88f037abe..60038701e 100755
--- a/view/tpl/group_edit.tpl
+++ b/view/tpl/group_edit.tpl
@@ -13,6 +13,7 @@
<input type='hidden' name='form_security_token' value='{{$form_security_token_edit}}'>
{{include file="field_input.tpl" field=$gname}}
{{include file="field_checkbox.tpl" field=$public}}
+ {{$pgrp_extras}}
<a href="group/drop/{{$gid}}?t={{$form_security_token_drop}}" onclick="return confirmDelete();" class="btn btn-sm btn-danger">
{{$delete}}
</a>