]> git.mxchange.org Git - friendica.git/blob - include/text.php
Merge pull request #7598 from annando/fix-picture-detection
[friendica.git] / include / text.php
1 <?php
2 /**
3  * @file include/text.php
4  */
5
6 use Friendica\App;
7 use Friendica\Content\Text\BBCode;
8 use Friendica\Core\Protocol;
9 use Friendica\Model\Contact;
10 use Friendica\Model\FileTag;
11 use Friendica\Model\Group;
12 use Friendica\Util\Strings;
13
14 /**
15  * Turn user/group ACLs stored as angle bracketed text into arrays
16  *
17  * @param string $s
18  * @return array
19  */
20 function expand_acl($s) {
21         // turn string array of angle-bracketed elements into numeric array
22         // e.g. "<1><2><3>" => array(1,2,3);
23         preg_match_all('/<(' . Group::FOLLOWERS . '|'. Group::MUTUALS . '|[0-9]+)>/', $s, $matches, PREG_PATTERN_ORDER);
24
25         return $matches[1];
26 }
27
28
29 /**
30  * Wrap ACL elements in angle brackets for storage
31  * @param string $item
32  */
33 function sanitise_acl(&$item) {
34         if (intval($item)) {
35                 $item = '<' . intval(Strings::escapeTags(trim($item))) . '>';
36         } elseif (in_array($item, [Group::FOLLOWERS, Group::MUTUALS])) {
37                 $item = '<' . $item . '>';
38         } else {
39                 unset($item);
40         }
41 }
42
43
44 /**
45  * Convert an ACL array to a storable string
46  *
47  * Normally ACL permissions will be an array.
48  * We'll also allow a comma-separated string.
49  *
50  * @param string|array $p
51  * @return string
52  */
53 function perms2str($p) {
54         $ret = '';
55         if (is_array($p)) {
56                 $tmp = $p;
57         } else {
58                 $tmp = explode(',', $p);
59         }
60
61         if (is_array($tmp)) {
62                 array_walk($tmp, 'sanitise_acl');
63                 $ret = implode('', $tmp);
64         }
65         return $ret;
66 }
67
68 /**
69  *  for html,xml parsing - let's say you've got
70  *  an attribute foobar="class1 class2 class3"
71  *  and you want to find out if it contains 'class3'.
72  *  you can't use a normal sub string search because you
73  *  might match 'notclass3' and a regex to do the job is
74  *  possible but a bit complicated.
75  *  pass the attribute string as $attr and the attribute you
76  *  are looking for as $s - returns true if found, otherwise false
77  *
78  * @param string $attr attribute value
79  * @param string $s string to search
80  * @return boolean True if found, False otherwise
81  */
82 function attribute_contains($attr, $s) {
83         $a = explode(' ', $attr);
84         return (count($a) && in_array($s,$a));
85 }
86
87 /**
88  * Compare activity uri. Knows about activity namespace.
89  *
90  * @param string $haystack
91  * @param string $needle
92  * @return boolean
93  */
94 function activity_match($haystack,$needle) {
95         return (($haystack === $needle) || ((basename($needle) === $haystack) && strstr($needle, NAMESPACE_ACTIVITY_SCHEMA)));
96 }
97
98 /**
99  * quick and dirty quoted_printable encoding
100  *
101  * @param string $s
102  * @return string
103  */
104 function qp($s) {
105         return str_replace("%", "=", rawurlencode($s));
106 }
107
108 /**
109  * @brief Find any non-embedded images in private items and add redir links to them
110  *
111  * @param App $a
112  * @param array &$item The field array of an item row
113  */
114 function redir_private_images($a, &$item)
115 {
116         $matches = [];
117         $cnt = preg_match_all('|\[img\](http[^\[]*?/photo/[a-fA-F0-9]+?(-[0-9]\.[\w]+?)?)\[\/img\]|', $item['body'], $matches, PREG_SET_ORDER);
118         if ($cnt) {
119                 foreach ($matches as $mtch) {
120                         if (strpos($mtch[1], '/redir') !== false) {
121                                 continue;
122                         }
123
124                         if ((local_user() == $item['uid']) && ($item['private'] == 1) && ($item['contact-id'] != $a->contact['id']) && ($item['network'] == Protocol::DFRN)) {
125                                 $img_url = 'redir?f=1&quiet=1&url=' . urlencode($mtch[1]) . '&conurl=' . urlencode($item['author-link']);
126                                 $item['body'] = str_replace($mtch[0], '[img]' . $img_url . '[/img]', $item['body']);
127                         }
128                 }
129         }
130 }
131
132 /**
133  * @brief Given a text string, convert from bbcode to html and add smilie icons.
134  *
135  * @param string $text String with bbcode.
136  * @return string Formatted HTML
137  * @throws \Friendica\Network\HTTPException\InternalServerErrorException
138  */
139 function prepare_text($text)
140 {
141         $s = BBCode::convert($text);
142         return trim($s);
143 }
144
145 /**
146  * return array with details for categories and folders for an item
147  *
148  * @param array $item
149  * @return array
150  *
151   * [
152  *      [ // categories array
153  *          {
154  *               'name': 'category name',
155  *               'removeurl': 'url to remove this category',
156  *               'first': 'is the first in this array? true/false',
157  *               'last': 'is the last in this array? true/false',
158  *           } ,
159  *           ....
160  *       ],
161  *       [ //folders array
162  *                      {
163  *               'name': 'folder name',
164  *               'removeurl': 'url to remove this folder',
165  *               'first': 'is the first in this array? true/false',
166  *               'last': 'is the last in this array? true/false',
167  *           } ,
168  *           ....
169  *       ]
170  *  ]
171  */
172 function get_cats_and_terms($item)
173 {
174         $categories = [];
175         $folders = [];
176         $first = true;
177
178         foreach (FileTag::fileToArray($item['file'] ?? '', 'category') as $savedFolderName) {
179                 $categories[] = [
180                         'name' => $savedFolderName,
181                         'url' => "#",
182                         'removeurl' => ((local_user() == $item['uid']) ? 'filerm/' . $item['id'] . '?f=&cat=' . rawurlencode($savedFolderName) : ""),
183                         'first' => $first,
184                         'last' => false
185                 ];
186                 $first = false;
187         }
188
189         if (count($categories)) {
190                 $categories[count($categories) - 1]['last'] = true;
191         }
192
193         if (local_user() == $item['uid']) {
194                 foreach (FileTag::fileToArray($item['file'] ?? '') as $savedFolderName) {
195                         $folders[] = [
196                                 'name' => $savedFolderName,
197                                 'url' => "#",
198                                 'removeurl' => ((local_user() == $item['uid']) ? 'filerm/' . $item['id'] . '?f=&term=' . rawurlencode($savedFolderName) : ""),
199                                 'first' => $first,
200                                 'last' => false
201                         ];
202                         $first = false;
203                 }
204         }
205
206         if (count($folders)) {
207                 $folders[count($folders) - 1]['last'] = true;
208         }
209
210         return [$categories, $folders];
211 }
212
213 /**
214  * return number of bytes in size (K, M, G)
215  * @param string $size_str
216  * @return int
217  */
218 function return_bytes($size_str) {
219         switch (substr ($size_str, -1)) {
220                 case 'M': case 'm': return (int)$size_str * 1048576;
221                 case 'K': case 'k': return (int)$size_str * 1024;
222                 case 'G': case 'g': return (int)$size_str * 1073741824;
223                 default: return $size_str;
224         }
225 }
226
227 function bb_translate_video($s) {
228
229         $matches = null;
230         $r = preg_match_all("/\[video\](.*?)\[\/video\]/ism",$s,$matches,PREG_SET_ORDER);
231         if ($r) {
232                 foreach ($matches as $mtch) {
233                         if ((stristr($mtch[1], 'youtube')) || (stristr($mtch[1], 'youtu.be'))) {
234                                 $s = str_replace($mtch[0], '[youtube]' . $mtch[1] . '[/youtube]', $s);
235                         } elseif (stristr($mtch[1], 'vimeo')) {
236                                 $s = str_replace($mtch[0], '[vimeo]' . $mtch[1] . '[/vimeo]', $s);
237                         }
238                 }
239         }
240         return $s;
241 }
242
243 function undo_post_tagging($s) {
244         $matches = null;
245         $cnt = preg_match_all('/([!#@])\[url=(.*?)\](.*?)\[\/url\]/ism', $s, $matches, PREG_SET_ORDER);
246         if ($cnt) {
247                 foreach ($matches as $mtch) {
248                         if (in_array($mtch[1], ['!', '@'])) {
249                                 $contact = Contact::getDetailsByURL($mtch[2]);
250                                 $mtch[3] = empty($contact['addr']) ? $mtch[2] : $contact['addr'];
251                         }
252                         $s = str_replace($mtch[0], $mtch[1] . $mtch[3],$s);
253                 }
254         }
255         return $s;
256 }
257
258 /// @TODO Rewrite this
259 function is_a_date_arg($s) {
260         $i = intval($s);
261
262         if ($i > 1900) {
263                 $y = date('Y');
264
265                 if ($i <= $y + 1 && strpos($s, '-') == 4) {
266                         $m = intval(substr($s, 5));
267
268                         if ($m > 0 && $m <= 12) {
269                                 return true;
270                         }
271                 }
272         }
273
274         return false;
275 }