dolibarr 21.0.0-alpha
fediverse.php
1<?php
2/* Copyright (C) 2003 Eric Seigne <erics@rycks.com>
3 * Copyright (C) 2003,2005 Rodolphe Quiedeville <rodolphe@quiedeville.org>
4 * Copyright (C) 2004-2011 Laurent Destailleur <eldy@users.sourceforge.net>
5 * Copyright (C) 2004 Sebastien Di Cintio <sdicintio@ressource-toi.org>
6 * Copyright (C) 2004 Benoit Mortier <benoit.mortier@opensides.be>
7 * Copyright (C) 2005-2011 Regis Houssin <regis.houssin@inodbox.com>
8 * Copyright (C) 2011 Juanjo Menent <jmenent@2byte.es>
9 * Copyright (C) 2020 Tobias Sekan <tobias.sekan@startmail.com>
10 * Copyright (C) 2024 MDW <mdeweerd@users.noreply.github.com>
11 * Copyright (C) 2024 Frédéric France <frederic.france@free.fr>
12 *
13 * This program is free software; you can redistribute it and/or modify
14 * it under the terms of the GNU General Public License as published by
15 * the Free Software Foundation; either version 3 of the License, or
16 * (at your option) any later version.
17 *
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
22 *
23 * You should have received a copy of the GNU General Public License
24 * along with this program. If not, see <https://www.gnu.org/licenses/>.
25 */
26
33//load Dolibarr environment
34require '../main.inc.php';
35require_once DOL_DOCUMENT_ROOT.'/core/lib/admin.lib.php';
36require_once DOL_DOCUMENT_ROOT.'/core/lib/socialnetwork.lib.php';
37require_once DOL_DOCUMENT_ROOT.'/core/modules/modSocialNetworks.class.php';
38require_once DOL_DOCUMENT_ROOT.'/core/class/infobox.class.php';
39require_once DOL_DOCUMENT_ROOT.'/core/class/fediverseparser.class.php';
40require_once DOL_DOCUMENT_ROOT.'/core/boxes/box_fediverse.php';
41
42
43
44//load translation files requires by the page
45$langs->loadLangs(array('admin', 'users', 'dict'));
46
47$action = GETPOST('action', 'aZ09');
48
49// Security check
50if (!$user->admin) {
52}
53if (!isModEnabled('socialnetworks')) {
54 accessforbidden('Module Social Networks is not enabled');
55}
56
57
58/*
59 * Actions
60 */
61
62if ($action == 'add') {
63 $error = 0;
64
65 if (empty(GETPOST('socialnetwork_name')) || empty(GETPOST('socialnetwork_url'))) {
66 $error++;
67 }
68
69 $socialNetworkName = GETPOST('socialnetwork_name', 'alpha');
70 $socialNetworkUrl = GETPOST('socialnetwork_url', 'alpha');
71
72 // other params if exist
73 $paramNames = GETPOST('param_name', 'array');
74 $paramValues = GETPOST('param_value', 'array');
75
76 $additionalParams = [];
77 if (!empty($paramNames) && is_array($paramNames)) {
78 foreach ($paramNames as $index => $paramName) {
79 if (!empty($paramName) && isset($paramValues[$index])) {
80 $additionalParams[$paramName] = $paramValues[$index];
81 }
82 }
83 }
84 if (!$error) {
85 $db->begin();
86
87 $socialNetworkData = array(
88 'title' => $socialNetworkName,
89 'url' => $socialNetworkUrl
90 );
91
92 $socialNetworkData = array_merge($socialNetworkData, $additionalParams);
93
94 $boxlabel = '(SocialNetwoksInformations)';
95
96 $sql = "INSERT INTO ".MAIN_DB_PREFIX."boxes_def (file, note)";
97 $sql .= " VALUES ('box_fediverse.php', '".$db->escape($socialNetworkName)."')";
98
99 if (!$db->query($sql)) {
100 dol_print_error($db);
101 $error++;
102 } else {
103 $jsonData = json_encode($socialNetworkData);
104 $result = dolibarr_set_const($db, "SOCIAL_NETWORKS_DATA_".$socialNetworkName, $jsonData, 'chaine', 0, '', $conf->entity);
105 }
106 }
107 if ($result) {
108 $db->commit();
109 header("Location: ".$_SERVER["PHP_SELF"]);
110 exit;
111 } else {
112 $db->rollback();
113 dol_print_error($db);
114 }
115}
116
117if ($action == 'confirm_delete' && GETPOST('confirm') == 'yes') {
118 $error = 0;
119 $key = GETPOST('key', 'alpha');
120 $name = '';
121 $sqlgetName = "SELECT note FROM ".MAIN_DB_PREFIX."boxes_def WHERE rowid=".((int) $key);
122
123 $resqName = $db->query($sqlgetName);
124 if ($resqName) {
125 $objName = $db->fetch_object($resqName);
126 $name = $objName->note;
127 }
128
129 $db->begin();
130
131 $sql = "DELETE FROM ".MAIN_DB_PREFIX."boxes";
132 $sql .= " WHERE entity = ".$conf->entity;
133 $sql .= " AND box_id = ".((int) $key);
134 $resql1 = $db->query($sql);
135
136 $sql = "DELETE FROM ".MAIN_DB_PREFIX."boxes_def";
137 $sql .= " WHERE rowid = ".((int) $key);
138 $resql2 = $db->query($sql);
139
140 if (!$resql1 || !$resql2) {
141 $db->rollback();
142 dol_print_error($db, "sql=".$sql);
143 exit;
144 } else {
145 $result = dolibarr_del_const($db, "SOCIAL_NETWORKS_DATA_".$name, $conf->entity);
146 if ($result) {
147 $db->commit();
148 header("Location: ".$_SERVER["PHP_SELF"]);
149 exit;
150 } else {
151 $db->rollback();
152 dol_print_error($db);
153 }
154 }
155}
156
157if ($action == 'updatesocialnetwork') {
158 $error = 0;
159 $id = GETPOST('key', 'alpha');
160 $name = GETPOST('socialnetwork_name');
161 $url = GETPOST('socialnetwork_url');
162 $paramsKey = GETPOST('paramsKey', 'array');
163 $paramsVal = GETPOST('paramsVal', 'array');
164
165 $result = dolibarr_get_const($db, "SOCIAL_NETWORKS_DATA_".$name, $conf);
166 $socialNetworkData = json_decode($result, true);
167
168 foreach ($paramsKey as $index => $key) {
169 if (empty($key) || empty($paramsVal[$index])) {
170 $error++;
171 }
172 }
173 // delete others params
174 foreach ($socialNetworkData as $key => $value) {
175 if ($key != 'title' && $key != 'url') {
176 unset($socialNetworkData[$key]);
177 }
178 }
179
180 // new keys and new values in array
181 $mergedParams = array();
182 foreach ($paramsKey as $index => $key) {
183 if (isset($paramsVal[$index])) {
184 $mergedParams[$key] = $paramsVal[$index];
185 }
186 }
187
188 // Add new key, value if changed
189 foreach ($mergedParams as $newKey => $newValue) {
190 if (!isset($socialNetworkData[$newKey]) || $socialNetworkData[$newKey] !== $newValue) {
191 $socialNetworkData[$newKey] = $newValue;
192 }
193 }
194 if (!$error) {
195 $newData = json_encode($socialNetworkData);
196 $result = dolibarr_set_const($db, "SOCIAL_NETWORKS_DATA_".$name, $newData, 'chaine', 0, '', $conf->entity);
197 if ($result) {
198 $db->commit();
199 header("Location: ".$_SERVER["PHP_SELF"]);
200 exit;
201 } else {
202 $db->rollback();
203 dol_print_error($db);
204 }
205 } else {
206 setEventMessages($langs->trans("ErrorInputRequired"), null, 'errors');
207 header("Location: ".$_SERVER["PHP_SELF"].'?action=editsocialnetwork&token='.newToken().'&key='.$id);
208 exit;
209 }
210}
211
212
213
214/*
215 * View
216 */
217
218$form = new Form($db);
219
220llxHeader('', $langs->trans("FediverseSetup"), '', '', 0, 0, '', '', '', 'mod-admin page-dict');
221
222$head = socialnetwork_prepare_head();
223
224$linkback = '<a href="'.DOL_URL_ROOT.'/admin/modules.php?restore_lastsearch_values=1">'.$langs->trans("BackToModuleList").'</a>';
225print dol_get_fiche_head($head, 'divers', $langs->trans('MenuDict'), -1, 'user', 0, $linkback, '', 0, '', 0);
226
227$title = $langs->trans("ConfigImportSocialNetwork");
228
229print_barre_liste($title, '', $_SERVER["PHP_SELF"], '', '', '', '', -1, '', 'tools', 0, '', '', -1, 0, 0, 0, '');
230
231
232print '<form action="'.$_SERVER["PHP_SELF"].'" method="post">';
233print '<input type="hidden" name="token" value="'.newToken().'">';
234
235print '<div class="div-table-responsive-no-min">';
236print '<table class="noborder centpercent">';
237
238print '<tr class="liste_titre">';
239print '<td colspan="2">'.$langs->trans("NewSocialNetwork").'</td>';
240print '<td>'.$langs->trans("Example").'</td>';
241print '</tr>';
242
243print '<tr class="oddeven">';
244print '<td>'.$langs->trans("Title").'</td>';
245print '<td><input type="text" class="flat minwidth300" name="socialnetwork_name"></td>';
246print '<td>Mastodon</td>';
247print '</tr>';
248
249print '<tr class="oddeven">';
250print '<td>'.$langs->trans('SocialNetworkUrl').'</td>';
251print '<td><input type="text" class="flat minwidth300" name="socialnetwork_url"></td>';
252print '<td>https://mastodon.social/api/v1/accounts/id_user</td>';
253print '</tr>';
254
255print '<tr class="oddeven"><td>';
256print $form->textwithpicto($langs->trans("Others"), $langs->trans("AddMoreParams"));
257print '</td><td><button type="button" id="addParamButton">'.img_picto($langs->trans("AddMoreParams"), 'add', 'pictofixedwidth').'</button></td>';
258print '<td>Token : ****<br>Cookie : ****</td>';
259print '</tr>';
260
261print '<tr class="oddeven">';
262print '<td colspan="2">';
263print '<div id="additionalParams"></div>';
264print '</td>';
265print '<td></td>';
266print '</tr>';
267
268
269print '</table>';
270
271print '</div>';
272
273print $form->buttonsSaveCancel("Add", '');
274print '<input type="hidden" name="action" value="add">';
275print '<script type="text/javascript">
276 document.getElementById("addParamButton").addEventListener("click", function() {
277 var container = document.getElementById("additionalParams");
278 var index = container.children.length;
279 var div = document.createElement("div");
280 div.className = "pair-group";
281 div.innerHTML = "<input type=\'text\' class=\'flat minwidth300\' name=\'param_name[]\' placeholder=\''.$langs->trans("ParamName").'\' class=\'flat\' /> <input type=\'text\' class=\'flat minwidth300\' name=\'param_value[]\' placeholder=\''.$langs->trans("ParamValue").'\' class=\'flat\' />";
282 container.appendChild(div);
283 });
284</script>';
285print '</form>';
286
287print '<br><br>';
288print '<span class="opacitymedium">'.$langs->trans('SocialNetworksNote').'</span>';
289print ' - ';
290print '<a href="'.DOL_URL_ROOT.'/admin/boxes.php?backtopage='.urlencode($_SERVER["PHP_SELF"]).'">'.$langs->trans('JumpToBoxes').'</a>';
291print '<br><br>';
292
293
294if ($action == 'deletesocialnetwork') {
295 $formconfirm = $form->formconfirm(
296 $_SERVER["PHP_SELF"].'?key='.urlencode(GETPOST('key', 'alpha')),
297 $langs->trans('Delete'),
298 $langs->trans('ConfirmDeleteSocialNetwork', GETPOST('key', 'alpha')),
299 'confirm_delete',
300 '',
301 0,
302 1
303 );
304 print $formconfirm;
305}
306$sql = "SELECT rowid, file, note FROM ".MAIN_DB_PREFIX."boxes_def";
307$sql .= " WHERE file = 'box_fediverse.php'";
308$sql .= " ORDER BY note";
309
310dol_syslog("select socialnetworks boxes", LOG_DEBUG);
311$resql = $db->query($sql);
312if ($resql) {
313 $boxlist = InfoBox::listBoxes($db, 'activated', -1, null);
314 $num = $db->num_rows($resql);
315 $i = 0;
316 while ($i < $num) {
317 $obj = $db->fetch_object($resql);
318
319 $jsonData = getDolGlobalString("SOCIAL_NETWORKS_DATA_".$obj->note);
320
321 $socialNetworkData = json_decode($jsonData, true);
322
323 $socialNetworkTitle = $socialNetworkData['title'];
324 $socialNetworkUrl = $socialNetworkData['url'];
325 $socialNetworkId = $obj->rowid;
326
327 $fediverseparser = new SocialNetworkManager($socialNetworkTitle);
328 $path_fediverse = DOL_DATA_ROOT.'/fediverse/temp/'.$socialNetworkTitle;
329
330 //check if other params exist
331 $authParams = [];
332 foreach ($socialNetworkData as $key => $value) {
333 if ($key !== 'title' && $key !== 'url') {
334 $authParams[$key] = $value;
335 }
336 }
337
338 $result = $fediverseparser->fetchPosts($socialNetworkUrl, 5, 300, $path_fediverse, $authParams);
339
340 print "<br>";
341 print '<form action="'.$_SERVER["PHP_SELF"].'" method="post">'."\n";
342 print '<input type="hidden" name="token" value="'.newToken().'">'."\n";
343
344 print '<table class="noborder centpercent">'."\n";
345
346 print '<tr class="liste_titre">';
347 print "<td>".$langs->trans("SocialNetworks")." ".($i+1)."</td>";
348 print '<td class="right">';
349 print '<a class="viewfielda reposition marginleftonly marginrighttonly showInputBtn" href="'.$_SERVER["PHP_SELF"].'?action=editsocialnetwork&token='.newToken().'&key='.urlencode($socialNetworkId).'">'.img_edit().'</a>';
350 print '<a class="deletefielda reposition marginleftonly right" href="'.$_SERVER["PHP_SELF"].'?action=deletesocialnetwork&token='.newToken().'&key='.urlencode($socialNetworkId).'">'.img_delete().'</a>';
351 print '<input type="hidden" name="id" value="'.$socialNetworkId.'">';
352 print '</td>';
353 print '</tr>'."\n";
354
355 print '<tr class="oddeven">';
356 print '<td>'.$langs->trans("Title")."</td>";
357 print '<td><input type="text" class="flat minwidth300" name="socialnetwork_name" value="'.dol_escape_htmltag($socialNetworkTitle).'" '.($action != "editsocialnetwork" ? 'disabled' : '').'></td>';
358 print '</tr>'."\n";
359
360 print '<tr class="oddeven">';
361 print "<td>".$langs->trans("URL")."</td>";
362 print '<td><input type="text" class="flat minwidth300" name="socialnetwork_url" value="'.dol_escape_htmltag($socialNetworkUrl).'" '.($action != "editsocialnetwork" ? 'disabled' : '').'></td>';
363 print '</tr>'."\n";
364
365 print '<tr class="oddeven">';
366 print "<td>".$langs->trans("Status")."</td>";
367 print "<td>";
368 if ($result > 0 && empty($fediverseparser->error)) {
369 print '<span class="ok">'.img_picto($langs->trans("Online"), 'tick', 'class="pictofixedwidth"').$langs->trans("Online").'</div>';
370 } else {
371 print '<span class="error">'.$langs->trans("Offline");
372 $langs->load("errors");
373 if ($fediverseparser->error) {
374 print ' - '.$langs->trans($fediverseparser->error);
375 }
376 print '</div>';
377 }
378 print "</td>";
379 print '</tr>'."\n";
380
381 // Active
382 $active = _isInBoxListFediverse((int) $socialNetworkId, $boxlist) ? 'yes' : 'no';
383
384 print '<tr class="oddeven">';
385 print '<td>'.$langs->trans('WidgetAvailable').'</td>';
386 print '<td>'.yn($active);
387 print ' &nbsp; - &nbsp; <a href="'.DOL_URL_ROOT.'/admin/boxes.php?backtopage='.urlencode($_SERVER["PHP_SELF"]).'">';
388 print $langs->trans("JumpToBoxes");
389 print '</a>';
390 print '</td>';
391 print '</tr>'."\n";
392
393 if ($action == 'editsocialnetwork' && $socialNetworkId == GETPOST('key')) {
394 foreach ($socialNetworkData as $k => $val) {
395 if ($k != 'title' && $k != 'url') {
396 print '<tr class="oddeven">';
397 print '<td><input type="text" class="flat minwidth200" name="paramsKey[]" value="'.dol_escape_htmltag($k).'"</td>';
398 if ($k == 'password') {
399 print '<td><input type="password" class="flat minwidth300" name="paramsVal[]" value="'.dol_escape_htmltag($val).'" />';
400 } else {
401 print '<td><input type="text" class="flat minwidth300" name="paramsVal[]" value="'.dol_escape_htmltag($val).'" />';
402 }
403 print '</td>';
404 print '</tr>'."\n";
405 }
406 }
407
408 print '<tr class="oddeven">';
409 print '<td><input type="hidden" name="action" value="updatesocialnetwork" /></td>';
410 print '<td><input class="button " type="submit" name="update" value="'.$langs->trans('Modify').'" /></td>';
411 print '</tr>'."\n";
412 }
413
414 print '</table>'."\n";
415
416 print "</form>\n";
417
418 $i++;
419 }
420} else {
421 dol_print_error($db);
422}
423
424print dol_get_fiche_end();
425
426llxFooter();
427$db->close();
428
436function _isInBoxListFediverse(int $id, array $boxlist)
437{
438 foreach ($boxlist as $box) {
439 if ($box->boxcode === "lastfediverseinfos") {
440 return true;
441 }
442 }
443 return false;
444}
$id
Definition account.php:39
dolibarr_set_const($db, $name, $value, $type='chaine', $visible=0, $note='', $entity=1)
Insert a parameter (key,value) into database (delete old key then insert it again).
dolibarr_del_const($db, $name, $entity=1)
Delete a constant.
dolibarr_get_const($db, $name, $entity=1)
Get the value of a setup constant from database.
if(!defined('NOREQUIRESOC')) if(!defined( 'NOREQUIRETRAN')) if(!defined('NOTOKENRENEWAL')) if(!defined( 'NOREQUIREMENU')) if(!defined('NOREQUIREHTML')) if(!defined( 'NOREQUIREAJAX')) llxHeader($head='', $title='', $help_url='', $target='', $disablejs=0, $disablehead=0, $arrayofjs='', $arrayofcss='', $morequerystring='', $morecssonbody='', $replacemainareaby='', $disablenofollow=0, $disablenoindex=0)
Empty header.
Definition wrapper.php:70
Class to manage generation of HTML components Only common components must be here.
static listBoxes($dbs, $mode, $zone, $user=null, $excludelist=array(), $includehidden=1)
Return array of boxes qualified for area and user.
Class to manage Social network posts.
llxFooter()
Footer empty.
Definition document.php:107
img_delete($titlealt='default', $other='class="pictodelete"', $morecss='')
Show delete logo.
dol_get_fiche_head($links=array(), $active='', $title='', $notab=0, $picto='', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limittoshow=0, $moretabssuffix='', $dragdropfile=0)
Show tabs of a record.
dol_get_fiche_end($notab=0)
Return tab footer of a card.
newToken()
Return the value of token currently saved into session with name 'newtoken'.
print_barre_liste($title, $page, $file, $options='', $sortfield='', $sortorder='', $morehtmlcenter='', $num=-1, $totalnboflines='', $picto='generic', $pictoisfullpath=0, $morehtmlright='', $morecss='', $limit=-1, $hideselectlimit=0, $hidenavigation=0, $pagenavastextinput=0, $morehtmlrightbeforearrow='')
Print a title with navigation controls for pagination.
GETPOST($paramname, $check='alphanohtml', $method=0, $filter=null, $options=null, $noreplace=0)
Return value of a param into GET or POST supervariable.
setEventMessages($mesg, $mesgs, $style='mesgs', $messagekey='', $noduplicate=0)
Set event messages in dol_events session object.
dol_print_error($db=null, $error='', $errors=null)
Displays error message system with all the information to facilitate the diagnosis and the escalation...
getDolGlobalString($key, $default='')
Return a Dolibarr global constant string value.
img_edit($titlealt='default', $float=0, $other='')
Show logo edit/modify fiche.
dol_syslog($message, $level=LOG_INFO, $ident=0, $suffixinfilename='', $restricttologhandler='', $logcontext=null)
Write log message into outputs.
accessforbidden($message='', $printheader=1, $printfooter=1, $showonlymessage=0, $params=null)
Show a message to say access is forbidden and stop program.