1<?php 2// (c) Copyright by authors of the Tiki Wiki CMS Groupware Project 3// 4// All Rights Reserved. See copyright.txt for details and a complete list of authors. 5// Licensed under the GNU LESSER GENERAL PUBLIC LICENSE. See license.txt for details. 6// $Id$ 7 8class Tracker_Field_Articles extends Tracker_Field_Abstract 9{ 10 private $articleSource; 11 12 public static function getTypes() 13 { 14 $db = TikiDb::get(); 15 $topics = $db->table('tiki_topics')->fetchMap('topicId', 'name', [], -1, -1, 'name_asc'); 16 $types = $db->table('tiki_article_types')->fetchColumn('type', []); 17 $types = array_combine($types, $types); 18 19 $options = [ 20 'articles' => [ 21 'name' => tr('Articles'), 22 'description' => tr('Attach articles to the tracker item.'), 23 'prefs' => ['trackerfield_articles', 'feature_articles'], 24 'tags' => ['advanced'], 25 'help' => 'Articles Tracker Field', 26 'default' => 'n', 27 'params' => [ 28 'topicId' => [ 29 'name' => tr('Topic'), 30 'description' => tr('Default article topic'), 31 'filter' => 'int', 32 'profile_reference' => 'article_topic', 33 'options' => $topics, 34 ], 35 'type' => [ 36 'name' => tr('Article Type'), 37 'description' => tr('Default article type'), 38 'filter' => 'text', 39 'profile_reference' => 'article_type', 40 'options' => $types, 41 ], 42 ], 43 ], 44 ]; 45 return $options; 46 } 47 48 function getFieldData(array $requestData = []) 49 { 50 global $prefs; 51 $ins_id = $this->getInsertId(); 52 if (isset($requestData[$ins_id])) { 53 if (is_string($requestData[$ins_id])) { 54 $articleIds = explode(',', $requestData[$ins_id]); 55 } else { 56 $articleIds = $requestData[$ins_id]; 57 } 58 59 $articleIds = array_filter(array_map('intval', $articleIds)); 60 $value = implode(',', $articleIds); 61 } else { 62 $value = $this->getValue(); 63 64 // Obtain the information from the database for display 65 $articleIds = array_filter(explode(',', $value)); 66 } 67 68 return [ 69 'value' => $value, 70 'articleIds' => $articleIds, 71 ]; 72 } 73 74 function addValue($articleId) { 75 $existing = explode(',', $this->getValue()); 76 if (! in_array($articleId, $existing)) { 77 $existing[] = $articleId; 78 } 79 return implode(',', $existing); 80 } 81 82 function removeValue($articleId) { 83 $existing = explode(',', $this->getValue()); 84 $existing = array_filter($existing, function($v) use ($articleId) { 85 return $v != $articleId; 86 }); 87 return implode(',', $existing); 88 } 89 90 function renderInput($context = []) 91 { 92 global $prefs; 93 // if the article is being indexed with the trackeritem as part of the autogenerated rss feature, the field should become read-only 94 if ($prefs['tracker_article_indexing'] == 'y' && $prefs['tracker_article_trackerId'] == $this->getConfiguration('trackerId')) { 95 $readonly = true; 96 } else { 97 $readonly = false; 98 } 99 $articleIds = $this->getConfiguration('articleIds'); 100 101 return $this->renderTemplate('trackerinput/articles.tpl', $context, [ 102 'filter' => ['type' => 'article'], 103 'labels' => array_combine( 104 $articleIds, 105 array_map(function ($id) { 106 return TikiLib::lib('object')->get_title('article', $id); 107 }, $articleIds) 108 ), 109 'readonly' => $readonly, 110 ]); 111 } 112 113 function renderOutput($context = []) 114 { 115 return $this->renderTemplate('trackeroutput/articles.tpl', $context, [ 116 ]); 117 } 118 119 function handleSave($value, $oldValue) 120 { 121 $new = array_diff(explode(',', $value), explode(',', $oldValue)); 122 $remove = array_diff(explode(',', $oldValue), explode(',', $value)); 123 124 $itemId = $this->getItemId(); 125 126 $relationlib = TikiLib::lib('relation'); 127 $relations = $relationlib->get_relations_from('trackeritem', $itemId, 'tiki.article.attach'); 128 foreach ($relations as $existing) { 129 if ($existing['type'] != 'article') { 130 continue; 131 } 132 133 if (in_array($existing['itemId'], $remove)) { 134 $relationlib->remove_relation($existing['relationId']); 135 } 136 } 137 138 foreach ($new as $articleId) { 139 $relationlib->add_relation('tiki.article.attach', 'trackeritem', $itemId, 'article', $articleId); 140 } 141 142 return [ 143 'value' => $value, 144 ]; 145 } 146 147 /** 148 * This returns the document part for the article field in the trackeritem. 149 * Note that this indexing only works as part of the rss aggregator feature. 150 * 151 * @param Search_Type_Factory_Interface $typeFactory 152 * @return array 153 */ 154 function getDocumentPart(Search_Type_Factory_Interface $typeFactory) 155 { 156 global $prefs; 157 //if article indexing is set to off for tracker, just return an empty array here. 158 if ($prefs['tracker_article_indexing'] != 'y' || $prefs['tracker_article_trackerId'] != $this->getItemData()['trackerId']) { 159 return []; 160 } 161 $value = $this->getValue(); 162 $baseKey = $this->getBaseKey(); 163 164 if (! $value) { 165 return []; 166 } 167 168 if (empty($this->articleSource)) { 169 $this->articleSource = new Search_ContentSource_ArticleSource(); 170 } 171 172 $articleInfo = $this->articleSource->getDocument($value, $typeFactory); 173 $data = []; 174 //append the article field to the base key. ie. tracker_field_articleField_title, tracker_field_articleField_author, etc 175 foreach ($articleInfo as $key => $v) { 176 $data[$baseKey . "_" . $key] = $v; 177 } 178 $data[$baseKey] = $typeFactory->identifier($value); 179 return $data; 180 } 181 182 function getProvidedFields() 183 { 184 $baseKey = $this->getBaseKey(); 185 186 if (empty($this->articleSource)) { 187 $this->articleSource = new Search_ContentSource_ArticleSource(); 188 } 189 190 $articleInfo = $this->articleSource->getProvidedFields(); 191 $data = []; 192 foreach ($articleInfo as $k => $v) { 193 $data[$k] = $baseKey . '_' . $v; 194 } 195 $data[] = $baseKey; 196 197 return $data; 198 } 199 200 function getGlobalFields() 201 { 202 $baseKey = $this->getBaseKey(); 203 return [$baseKey => true]; 204 } 205} 206