tripal.module 54 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623
  1. <?php
  2. /**
  3. * @file
  4. * The core Tripal module
  5. */
  6. /**
  7. * @defgroup tripal Tripal Module
  8. * @ingroup tripal_modules
  9. * @{
  10. * The core Tripal module provides functionality useful for all other Tripal
  11. * modules and extension modules.
  12. * @}
  13. */
  14. /**
  15. * @defgroup tripal_api Tripal API
  16. * @ingroup tripal
  17. * @{
  18. * Tripal provides an application programming interface (API) to support
  19. * customizations and creation of new extensions.
  20. * @}
  21. */
  22. // Import the full Tripal API into scope.
  23. tripal_import_api();
  24. require_once "includes/tripal.field_storage.inc";
  25. require_once "includes/tripal.fields.inc";
  26. require_once "includes/tripal.entity.inc";
  27. require_once "includes/tripal.registration.inc";
  28. require_once "includes/TripalVocab.inc";
  29. require_once "includes/TripalVocabController.inc";
  30. require_once "includes/TripalVocabViewsController.inc";
  31. require_once "includes/TripalTerm.inc";
  32. require_once "includes/TripalTermController.inc";
  33. require_once "includes/TripalTermViewsController.inc";
  34. require_once "includes/TripalEntity.inc";
  35. require_once "includes/TripalEntityController.inc";
  36. require_once "includes/TripalEntityUIController.inc";
  37. require_once "includes/TripalEntityViewsController.inc";
  38. require_once "includes/TripalBundle.inc";
  39. require_once "includes/TripalBundleController.inc";
  40. require_once "includes/TripalBundleUIController.inc";
  41. require_once "includes/TripalBundleViewsController.inc";
  42. require_once "includes/TripalFields/TripalField.inc";
  43. require_once "includes/TripalFields/TripalFieldWidget.inc";
  44. require_once "includes/TripalFields/TripalFieldFormatter.inc";
  45. require_once "includes/TripalFieldQuery.inc";
  46. require_once "includes/TripalJob.inc";
  47. require_once "includes/TripalImporter.inc";
  48. require_once "includes/TripalEntityCollection.inc";
  49. require_once "includes/TripalFieldDownloaders/TripalFieldDownloader.inc";
  50. /**
  51. * Implements hook_views_api().
  52. */
  53. function tripal_views_api() {
  54. return array(
  55. 'api' => 3,
  56. );
  57. }
  58. /**
  59. * Implements hook_init().
  60. *
  61. * @ingroup tripal
  62. */
  63. function tripal_init() {
  64. global $base_url;
  65. // add some variables for all javasript to use for building URLs
  66. $clean_urls = variable_get('clean_url', 0);
  67. $tripal_path = url(drupal_get_path('module', 'tripal'));
  68. drupal_add_js("
  69. var baseurl = '$base_url';
  70. var isClean = $clean_urls;
  71. var tripal_path = '$tripal_path';",
  72. 'inline', 'header');
  73. // make sure the date time settings are the way Tripal will insert them
  74. // otherwise PostgreSQL version that may have a different datestyle setting
  75. // will fail when inserting or updating a date column in a table.
  76. db_query("SET DATESTYLE TO :style", array(':style' => 'MDY'));
  77. //Ask users to do the registration form
  78. if (user_access('administer tripal')) {
  79. if (empty(variable_get('tripal_site_registration', FALSE)) || !(variable_get('disable_tripal_reporting', FALSE))) {
  80. if (current_path() != 'admin/tripal/register' and current_path() != 'system/ajax') {
  81. drupal_set_message('Please register your Tripal Site. Registering provides important
  82. information that will help secure funding for continued improvements to Tripal. ' .
  83. l('Click to register now or opt out.', 'admin/tripal/register'), 'warning');
  84. }
  85. }
  86. }
  87. }
  88. function tripal_menu_alter(&$items) {
  89. }
  90. /**
  91. * Implements hook_menu().
  92. * Defines all menu items needed by Tripal Core
  93. *
  94. * @ingroup tripal
  95. */
  96. function tripal_menu() {
  97. $items = array();
  98. // Tripal setting groups
  99. $items['admin/tripal'] = array(
  100. 'title' => 'Tripal',
  101. 'description' => t("Manage the behavior or Tripal and its various modules."),
  102. 'weight' => -8,
  103. 'page callback' => 'system_admin_menu_block_page',
  104. 'access arguments' => array('administer tripal'),
  105. 'file' => 'system.admin.inc',
  106. 'file path' => drupal_get_path('module', 'system'),
  107. );
  108. // Tripal registration form.
  109. $items['admin/tripal/register'] = [
  110. 'title' => 'Registration',
  111. 'description' => t('Register your Tripal website. Registration of Tripal
  112. websites gives the developers important information that allow us
  113. to continue to secure funding for maintenance and expansion.'),
  114. 'page callback' => 'drupal_get_form',
  115. 'page arguments' => array('tripal_registration_form'),
  116. 'access arguments' => array('administer tripal'),
  117. 'type' => MENU_NORMAL_ITEM,
  118. 'weight' => 0,
  119. 'file' => 'includes/tripal.registration.inc',
  120. ];
  121. $items['admin/content/bio_data/add'] = [
  122. 'title' => 'Add Tripal Content',
  123. 'description' => t('Create new Tripal Content.'),
  124. 'page callback' => 'tripal_add_page',
  125. 'access arguments' => ['administer tripal'],
  126. 'file' => 'includes/TripalEntityUIController.inc',
  127. 'file path' => drupal_get_path('module', 'tripal'),
  128. 'type' => MENU_LOCAL_ACTION,
  129. ];
  130. $items['admin/content/bio_data/unpublish'] = [
  131. 'title' => 'Unpublish Orphaned Content',
  132. 'description' => t('Unpublish content that has no associated records in the data store.'),
  133. 'page callback' => 'drupal_get_form',
  134. 'page arguments' => ['tripal_unpublish_orphans_form'],
  135. 'access arguments' => ['administer tripal'],
  136. 'file' => 'includes/tripal.unpublish_orphans.inc',
  137. 'file path' => drupal_get_path('module', 'tripal'),
  138. 'type' => MENU_LOCAL_ACTION,
  139. 'weight' => 3
  140. ];
  141. /**
  142. * Tripal Extensions
  143. */
  144. $items['admin/tripal/storage'] = array(
  145. 'title' => 'Data Storage',
  146. 'description' => t("Tripal is designed to access biological
  147. data in any data storage back-end. A storage back-end must have a
  148. module that can be installed that interfaces with Tripal. By default
  149. the base Tripal package provides The Tripal Chado module for storing
  150. data in the GMOD Chado database schema. All available storage backends
  151. and their administrative tools are found here."),
  152. 'weight' => 8,
  153. 'access arguments' => array('administer tripal'),
  154. );
  155. $items['admin/tripal/extension'] = array(
  156. 'title' => 'Extensions',
  157. 'description' => t("Configuration and management pages for Tripal extension modules."),
  158. 'weight' => 8,
  159. 'access arguments' => array('administer tripal'),
  160. );
  161. /**
  162. * Jobs Management
  163. */
  164. $items['admin/tripal/tripal_jobs'] = array(
  165. 'title' => 'Jobs',
  166. 'description' => t('Provides tools for managing jobs submitted to Tripal. In some
  167. cases, long-running tasks are too slow to complete within a single
  168. browser session. The Tripal jobs system allows long-running tasks
  169. to be submitted to a queue that can be executed manually by the
  170. site admin or automatically using a module such as the ') .
  171. l('Tripal Daemon', 'https://www.drupal.org/project/tripal_daemon', array('attributes' => array('target' => '_blank'))) .
  172. ' extension module.',
  173. 'page callback' => 'tripal_jobs_admin_view',
  174. 'access arguments' => array('administer tripal'),
  175. 'type' => MENU_NORMAL_ITEM,
  176. 'weight' => 0,
  177. 'file' => 'includes/tripal.jobs.inc',
  178. );
  179. $items['admin/tripal/tripal_jobs/help'] = array(
  180. 'title' => 'Help',
  181. 'description' => t('Help for the tripal job management system'),
  182. 'page callback' => 'theme',
  183. 'page arguments' => array('tripal_job_help'),
  184. 'access arguments' => array('administer tripal'),
  185. 'type' => MENU_LOCAL_TASK,
  186. 'weight' => 10
  187. );
  188. $items['admin/tripal/tripal_jobs/cancel/%'] = array(
  189. 'title' => 'Jobs',
  190. 'description' => t('Cancel a pending job'),
  191. 'page callback' => 'tripal_cancel_job',
  192. 'page arguments' => array(4),
  193. 'access arguments' => array('administer tripal'),
  194. 'type' => MENU_CALLBACK,
  195. 'file' => 'api/tripal.jobs.api.inc',
  196. );
  197. $items['admin/tripal/tripal_jobs/status/%'] = array(
  198. 'page callback' => 'tripal_jobs_status_view',
  199. 'page arguments' => array(4),
  200. 'access arguments' => array('administer tripal'),
  201. 'type' => MENU_CALLBACK,
  202. 'file' => 'includes/tripal.jobs.inc',
  203. );
  204. $items['admin/tripal/tripal_jobs/rerun/%'] = array(
  205. 'title' => 'Jobs',
  206. 'description' => t('Re-run an existing job.'),
  207. 'page callback' => 'tripal_rerun_job',
  208. 'page arguments' => array(4),
  209. 'access arguments' => array('administer tripal'),
  210. 'type' => MENU_CALLBACK,
  211. 'file' => 'includes/tripal.jobs.inc',
  212. );
  213. $items['admin/tripal/tripal_jobs/view/%'] = array(
  214. 'title' => 'Jobs Details',
  215. 'description' => t('View job details.'),
  216. 'page callback' => 'tripal_jobs_view',
  217. 'page arguments' => array(4),
  218. 'access arguments' => array('administer tripal'),
  219. 'type' => MENU_CALLBACK,
  220. 'file' => 'includes/tripal.jobs.inc',
  221. );
  222. $items['admin/tripal/tripal_jobs/views/jobs/enable'] = array(
  223. 'title' => 'Enable Jobs Administrative View',
  224. 'page callback' => 'tripal_enable_view',
  225. 'page arguments' => array('tripal_admin_jobs', 'admin/tripal/tripal_jobs'),
  226. 'access arguments' => array('administer tripal'),
  227. 'type' => MENU_CALLBACK,
  228. 'file' => 'includes/tripal.jobs.inc',
  229. );
  230. $items['admin/tripal/tripal_jobs/execute/%'] = array(
  231. 'title' => 'Jobs',
  232. 'description' => t('Execute an existing job'),
  233. 'page callback' => 'tripal_execute_job',
  234. 'page arguments' => array(4),
  235. 'access arguments' => array('administer tripal'),
  236. 'type' => MENU_CALLBACK,
  237. );
  238. /*
  239. * AJAX Callbacks.
  240. */
  241. $items['bio_data/ajax/field_attach/%'] = array(
  242. 'page callback' => 'tripal_ajax_attach_field',
  243. 'page arguments' => array(3),
  244. 'access arguments' => array('access content'),
  245. 'type' => MENU_CALLBACK,
  246. 'file' => 'includes/tripal.entity.inc',
  247. 'file path' => drupal_get_path('module', 'tripal'),
  248. );
  249. /*
  250. * Dashboard Action Item callbacks.
  251. */
  252. $items['admin/disable/notification/%'] = array(
  253. 'page callback' => 'tripal_disable_admin_notification',
  254. 'page arguments' => array(3),
  255. 'access arguments' => array('access content'),
  256. 'type' => MENU_CALLBACK,
  257. 'file' => 'includes/tripal.admin_blocks.inc',
  258. 'file path' => drupal_get_path('module', 'tripal'),
  259. );
  260. $items['admin/import/field/%/%/%/%'] = array(
  261. 'page callback' => 'tripal_admin_notification_import_field',
  262. 'page arguments' => array(3, 4, 5, 6),
  263. 'access arguments' => array('access content'),
  264. 'type' => MENU_CALLBACK,
  265. 'file' => 'includes/tripal.admin_blocks.inc',
  266. 'file path' => drupal_get_path('module', 'tripal'),
  267. );
  268. /*
  269. * Term Lookup
  270. */
  271. $items['cv/lookup'] = array(
  272. 'title' => 'Controlled Vocabularies',
  273. 'description' => t("A tool to explore the controlled vocabularies that are used on this site."),
  274. 'access arguments' => array('access content'),
  275. 'page callback' => 'tripal_vocabulary_lookup_page',
  276. 'file' => 'includes/tripal.term_lookup.inc',
  277. 'file path' => drupal_get_path('module', 'tripal'),
  278. 'type' => MENU_NORMAL_ITEM,
  279. );
  280. $items['cv/lookup/%'] = array(
  281. 'title' => 'Vocabulary Details',
  282. 'description' => t("Provides a tool to discover controlled vocabularies"),
  283. 'access arguments' => array('access content'),
  284. 'page callback' => 'tripal_vocabulary_lookup_vocab_page',
  285. 'page arguments' => array(2),
  286. 'file' => 'includes/tripal.term_lookup.inc',
  287. 'file path' => drupal_get_path('module', 'tripal'),
  288. 'type' => MENU_CALLBACK,
  289. );
  290. $items['cv/lookup/%/%'] = array(
  291. 'title' => 'Vocabulary Term Lookup',
  292. 'description' => t("Provides a tool to discover controlled vocabularies terms used by this site."),
  293. 'access arguments' => array('access content'),
  294. 'page callback' => 'tripal_vocabulary_lookup_term_page',
  295. 'page arguments' => array(2, 3),
  296. 'file' => 'includes/tripal.term_lookup.inc',
  297. 'file path' => drupal_get_path('module', 'tripal'),
  298. 'type' => MENU_CALLBACK,
  299. );
  300. $items['cv/lookup/%/%/children'] = array(
  301. 'access arguments' => array('access content'),
  302. 'page callback' => 'tripal_vocabulary_lookup_term_children_ajax',
  303. 'page arguments' => array(2, 3),
  304. 'file' => 'includes/tripal.term_lookup.inc',
  305. 'file path' => drupal_get_path('module', 'tripal'),
  306. 'type' => MENU_CALLBACK,
  307. );
  308. // Adds a +Check for new fields link on the 'Tripal Content Types' page.
  309. $items['admin/structure/bio_data/manage/%/fields/check'] = array(
  310. 'title' => 'Check for new fields',
  311. 'description' => t('Check if new fields should be added to this content type.'),
  312. 'page callback' => 'tripal_check_new_fields',
  313. 'page arguments' => array(4),
  314. 'access arguments' => array('administer tripal'),
  315. 'file' => 'api/tripal.entities.api.inc',
  316. 'file path' => drupal_get_path('module', 'tripal'),
  317. 'type' => MENU_LOCAL_ACTION,
  318. );
  319. $items['tripal/upload'] = array(
  320. 'page callback' => 'tripal_file_upload',
  321. 'access arguments' => array('upload files'),
  322. 'file' => '/includes/tripal.upload.inc',
  323. 'type' => MENU_CALLBACK,
  324. );
  325. /*
  326. * Data Loaders (TripalImporter)
  327. */
  328. $items['admin/tripal/loaders'] = array(
  329. 'title' => 'Data Loaders',
  330. 'description' => t('Tools facilitating data import.'),
  331. 'access arguments' => array('administer tripal'),
  332. 'type' => MENU_NORMAL_ITEM,
  333. 'weight' => 6
  334. );
  335. // Add in the loaders
  336. $importers = tripal_get_importers();
  337. foreach ($importers as $class_name) {
  338. tripal_load_include_importer_class($class_name);
  339. if (class_exists($class_name)) {
  340. $machine_name = $class_name::$machine_name;
  341. $menu_path = 'admin/tripal/loaders/' . $machine_name;
  342. $callback = $class_name::$callback;
  343. $callback_path = $class_name::$callback_path;
  344. $callback_module = $class_name::$callback_module;
  345. $page_args = [];
  346. if ($class_name::$menu_path) {
  347. $menu_path = $class_name::$menu_path;
  348. }
  349. if (!$callback) {
  350. $callback = 'drupal_get_form';
  351. $page_args = ['tripal_get_importer_form', $class_name];
  352. }
  353. if (!$callback_path) {
  354. $callback_path = 'includes/tripal.importer.inc';
  355. }
  356. $file_path = drupal_get_path('module', 'tripal');
  357. if ($callback_path and $callback_module) {
  358. $file_path = drupal_get_path('module', $callback_module);
  359. }
  360. $items[$menu_path] = array(
  361. 'title' => $class_name::$name,
  362. 'description' => $class_name::$description,
  363. 'page callback' => $callback,
  364. 'page arguments' => $page_args,
  365. 'access arguments' => array('use ' . $machine_name . ' importer'),
  366. 'type' => MENU_NORMAL_ITEM,
  367. 'file' => $callback_path,
  368. 'file path' => $file_path,
  369. );
  370. }
  371. }
  372. /**
  373. * Data Collections
  374. */
  375. $items['user/%/data-collections/%/delete'] = array (
  376. 'title' => 'Delete a Collections',
  377. 'description' => 'Deletes a data collection.',
  378. 'page callback' => 'drupal_get_form',
  379. 'page arguments' => array('tripal_user_collections_delete_form', 1, 3),
  380. 'access callback' => 'tripal_accesss_user_collections',
  381. 'access arguments' => array(1),
  382. 'type' => MENU_CALLBACK,
  383. 'file' => 'includes/tripal.collections.inc',
  384. 'file path' => drupal_get_path('module', 'tripal'),
  385. );
  386. $items['user/%/data-collections/%/view'] = array (
  387. 'title' => 'View a Collections',
  388. 'description' => 'Views a data collection.',
  389. 'page callback' => 'tripal_user_collections_view_page',
  390. 'page arguments' => array(1, 3),
  391. 'access callback' => 'tripal_accesss_user_collections',
  392. 'access arguments' => array(1),
  393. 'type' => MENU_CALLBACK,
  394. 'file' => 'includes/tripal.collections.inc',
  395. 'file path' => drupal_get_path('module', 'tripal'),
  396. );
  397. $items['user/%/data-collections/generate/%'] = array (
  398. 'title' => 'Generate a file for download of a Collections',
  399. 'description' => 'Generates a data collection file for download.',
  400. 'page callback' => 'drupal_get_form',
  401. 'page arguments' => array('tripal_user_collections_generate_file_form', 1, 4),
  402. 'access callback' => 'tripal_accesss_user_collections',
  403. 'access arguments' => array(1),
  404. 'type' => MENU_CALLBACK,
  405. 'file' => 'includes/tripal.collections.inc',
  406. 'file path' => drupal_get_path('module', 'tripal'),
  407. );
  408. $items['admin/tripal/data-collections'] = array(
  409. 'title' => 'Data Collections',
  410. 'description' => t('Site-wide settings for data collections'),
  411. 'page callback' => 'drupal_get_form',
  412. 'page arguments' => array('tripal_admin_data_collection_form'),
  413. 'access arguments' => array('administer tripal'),
  414. 'type' => MENU_NORMAL_ITEM,
  415. 'weight' => 0,
  416. 'file' => 'includes/tripal.admin.inc',
  417. 'file path' => drupal_get_path('module', 'tripal'),
  418. );
  419. //
  420. // USER FILE MANAGEMENT
  421. //
  422. $items['admin/tripal/files'] = [
  423. 'title' => 'User File Management',
  424. 'description' => 'Set maximum upload sizes, quotas and view usage.',
  425. 'page callback' => 'drupal_get_form',
  426. 'page arguments' => ['tripal_admin_manage_files_form'],
  427. 'access arguments' => ['administer tripal'],
  428. 'type' => MENU_NORMAL_ITEM,
  429. 'file' => 'includes/tripal.admin_files.inc',
  430. 'file path' => drupal_get_path('module', 'tripal'),
  431. 'weight' => 30,
  432. ];
  433. $items['admin/tripal/files/quota'] = [
  434. 'title' => 'User Quotas',
  435. 'description' => 'Set default quota, expiration date, and custom quotas',
  436. 'page callback' => 'drupal_get_form',
  437. 'page arguments' => ['tripal_admin_manage_quota_form'],
  438. 'access arguments' => ['administer tripal'],
  439. 'type' => MENU_LOCAL_TASK,
  440. 'file' => 'includes/tripal.admin_files.inc',
  441. 'file path' => drupal_get_path('module', 'tripal'),
  442. 'weight' => 10,
  443. ];
  444. // Admin remove user quota
  445. $items['admin/tripal/files/quota/remove/%'] = [
  446. 'title' => 'Remove custom user quota',
  447. 'description' => "Revert's a user's quota and expiration of files to the site wide defaults.",
  448. 'page callback' => 'drupal_get_form',
  449. 'page arguments' => ['tripal_admin_remove_quota_form', 5],
  450. 'access arguments' => ['administer tripal'],
  451. 'type' => MENU_CALLBACK,
  452. 'file' => 'includes/tripal.admin_files.inc',
  453. 'file path' => drupal_get_path('module', 'tripal'),
  454. ];
  455. // Add user quota
  456. $items['admin/tripal/files/quota/add'] = [
  457. 'title' => 'Add Custom Quota',
  458. 'description' => 'Gives the user a new quota and expiration date',
  459. 'page callback' => 'drupal_get_form',
  460. 'page arguments' => ['tripal_admin_add_custom_form'],
  461. 'access arguments' => ['administer tripal'],
  462. // TODO: Ask Stephen is this is fine as a link at the top of the form
  463. // as well as a link in the table
  464. 'type' => MENU_CALLBACK,
  465. 'file' => 'includes/tripal.admin_files.inc',
  466. 'file path' => drupal_get_path('module', 'tripal'),
  467. ];
  468. // Autocomplete path for the users on the site
  469. $items['admin/tripal/files/quota/user/autocomplete'] = [
  470. 'title' => 'Autocomplete for existing users',
  471. 'description' => 'Provide a list of existing users on the site.',
  472. 'page callback' => 'tripal_users_autocomplete',
  473. 'access arguments' => ['administer tripal'],
  474. 'type' => MENU_CALLBACK,
  475. 'file' => 'includes/tripal.admin_files.inc',
  476. 'file path' => drupal_get_path('module', 'tripal'),
  477. ];
  478. // Edit user quota
  479. $items['admin/tripal/files/quota/edit/%'] = [
  480. 'title' => 'Edit Custom Quota',
  481. 'description' => 'Edit an existing user\'s quota and/or expiration date.',
  482. 'page callback' => 'drupal_get_form',
  483. 'page arguments' => ['tripal_admin_edit_quota_form', 5],
  484. 'access arguments' => ['administer tripal'],
  485. 'type' => MENU_CALLBACK,
  486. 'file' => 'includes/tripal.admin_files.inc',
  487. 'file path' => drupal_get_path('module', 'tripal'),
  488. ];
  489. $items['admin/tripal/files/usage'] = [
  490. 'title' => 'File Usage',
  491. 'description' => 'Set default quota, expiration date, and custom quotas',
  492. 'page callback' => 'drupal_get_form',
  493. 'page arguments' => ['tripal_admin_file_usage_page'],
  494. 'access arguments' => ['administer tripal'],
  495. 'type' => MENU_LOCAL_TASK,
  496. 'file' => 'includes/tripal.admin_files.inc',
  497. 'file path' => drupal_get_path('module', 'tripal'),
  498. 'weight' => 15
  499. ];
  500. //
  501. // USER FILES
  502. //
  503. // User view quota (Tab)
  504. $items['user/%/files'] = [
  505. 'title' => 'Files',
  506. 'description' => 'Monitors what files that have been uploaded by user through the tripal module',
  507. 'page callback' => 'tripal_user_files_page',
  508. 'page arguments' => [1],
  509. 'access callback' => 'tripal_access_user_files',
  510. 'access arguments' => ['view', 1],
  511. 'type' => MENU_LOCAL_TASK,
  512. 'file' => 'includes/tripal.user.inc',
  513. 'file path' => drupal_get_path('module', 'tripal'),
  514. 'weight' => 10,
  515. ];
  516. $items['user/%/files/%'] = [
  517. 'title' => 'File Details',
  518. 'description' => "View details about the file",
  519. 'page callback' => 'tripal_view_file',
  520. 'page arguments' => [1, 3],
  521. 'access callback' => 'tripal_access_user_files',
  522. 'access arguments' => ['renew', 1, 3],
  523. 'type' => MENU_CALLBACK,
  524. 'file' => 'includes/tripal.user.inc',
  525. 'file path' => drupal_get_path('module', 'tripal'),
  526. ];
  527. // User file renew.
  528. $items['user/%/files/%/renew'] = [
  529. 'title' => 'Renew File',
  530. 'description' => "Renew a user's file",
  531. 'page callback' => 'tripal_renew_file',
  532. 'page arguments' => [3],
  533. 'access callback' => 'tripal_access_user_files',
  534. 'access arguments' => ['renew', 1, 3],
  535. 'type' => MENU_CALLBACK,
  536. 'file' => 'includes/tripal.user.inc',
  537. 'file path' => drupal_get_path('module', 'tripal'),
  538. ];
  539. // User file download.
  540. $items['user/%/files/%/download'] = [
  541. 'title' => 'Download File',
  542. 'description' => "Download a user's file based off of the link clicked in the table",
  543. 'page callback' => 'tripal_download_file',
  544. 'page arguments' => [3],
  545. 'access arguments' => ['download', 1, 3],
  546. 'access callback' => 'tripal_access_user_files',
  547. 'type' => MENU_CALLBACK,
  548. 'file' => 'includes/tripal.user.inc',
  549. 'file path' => drupal_get_path('module', 'tripal'),
  550. ];
  551. // User file delete.
  552. $items['user/%/files/%/delete'] = [
  553. 'title' => 'Delete File',
  554. 'description' => "Delete a user's file based on either user action or expired file",
  555. 'page callback' => 'drupal_get_form',
  556. 'page arguments' => ['tripal_delete_file_form', 1, 3],
  557. 'access callback' => 'tripal_access_user_files',
  558. 'access arguments' => ['delete', 1, 3],
  559. 'type' => MENU_CALLBACK,
  560. 'file' => 'includes/tripal.user.inc',
  561. 'file path' => drupal_get_path('module', 'tripal'),
  562. ];
  563. return $items;
  564. }
  565. /**
  566. * Checks if the current user has permissions to perform an action on a file.
  567. *
  568. * @param $op
  569. * The operation to perform. These include 'view', 'download', 'renew' and
  570. * 'delete'
  571. * @param $uid
  572. * The user ID of the user's account that owns the file.
  573. * @param $fid
  574. * The file ID.
  575. */
  576. function tripal_access_user_files($op, $uid, $fid = NULL) {
  577. global $user;
  578. // The site admin can do anything.
  579. if (in_array('administrator', $user->roles)) {
  580. return TRUE;
  581. }
  582. // Only the user that owns the files can see them.
  583. if ($uid != $user->uid) {
  584. return FALSE;
  585. }
  586. // If no file ID is provided and the user wants to view then
  587. // this is the case where the user wants to see all the files.
  588. if (!$fid and $op == 'view') {
  589. return TRUE;
  590. }
  591. $file = file_load($fid);
  592. switch ($op) {
  593. case 'view':
  594. case 'download':
  595. case 'renew':
  596. case 'delete':
  597. if ($user->uid == $file->uid) {
  598. return TRUE;
  599. }
  600. break;
  601. }
  602. return FALSE;
  603. }
  604. /**
  605. * An access function for data collections.
  606. *
  607. * @return boolean
  608. */
  609. function tripal_accesss_user_collections($uid) {
  610. if (!tripal_access_user_data($uid)) {
  611. return FALSE;
  612. }
  613. $collections_enabled = variable_get('tripal_data_collections_enabled', 1);
  614. if (!$collections_enabled) {
  615. return FALSE;
  616. }
  617. return TRUE;
  618. }
  619. /**
  620. * Autocomplete function for listing existing users on the site.
  621. *
  622. * @return json array of users that match the query in the textfield
  623. **/
  624. function tripal_users_autocomplete($string) {
  625. $matches = [];
  626. $result = db_select('users', 'u')
  627. ->fields('u', ['name'])
  628. ->condition('name', '%' . db_like($string) . '%', 'LIKE')
  629. ->execute();
  630. foreach ($result as $row) {
  631. $matches[$row->name] = check_plain($row->name);
  632. }
  633. drupal_json_output($matches);
  634. }
  635. /**
  636. * Access callback for accessing a user's Tripal-added private data.
  637. *
  638. * The User account being accessed must match the ID of the current user. This
  639. * function can be used to check access for any type of user-specfic data
  640. * added by any Tripal module.
  641. *
  642. * @param $uid
  643. * The UID of the user's account to access.
  644. * @return boolean
  645. */
  646. function tripal_access_user_data($uid) {
  647. global $user;
  648. if ($uid == $user->uid) {
  649. return TRUE;
  650. }
  651. return FALSE;
  652. }
  653. /**
  654. * Implements hook_permission().
  655. */
  656. function tripal_permission() {
  657. $permissions = array(
  658. 'administer tripal' => array(
  659. 'title' => t('Administer Tripal'),
  660. 'description' => t('Allow the user to access administrative pages of Tripal. This includes management of jobs, the storage systems, extensions and the controlled vocabularies.'),
  661. 'restrict access' => TRUE,
  662. ),
  663. 'access tripal content overview' => array(
  664. 'title' => t('Access the Tripal content overview page'),
  665. 'description' => t('Get an overview of all Tripal content'),
  666. 'restrict access' => TRUE,
  667. ),
  668. 'manage tripal content types' => array(
  669. 'title' => t('Manage Tripal content types'),
  670. 'description' => t('Allows the user to create, update and delete Tripal content types.'),
  671. 'restrict access' => TRUE,
  672. ),
  673. 'publish tripal content' => array(
  674. 'title' => t('Publish Tripal content types'),
  675. 'description' => t('Allows the user to publish Tripal content for online access.'),
  676. 'restrict access' => TRUE,
  677. ),
  678. 'upload files' => array(
  679. 'title' => t('Upload Files'),
  680. 'description' => t('Allows the user to upload files using Tripal\'s HTML5 loader.'),
  681. ),
  682. 'view dev helps' => array(
  683. 'title' => t('View Developer Hints'),
  684. 'description' => t('Tripal will provide blue shaded boxes that provide
  685. instructions for how to customize or setup specific pages on a
  686. site. This permission should be enabled for developers. But can
  687. be disabled once developers are accustomed to these hints.'),
  688. 'restrict access' => TRUE,
  689. ),
  690. );
  691. // Add permissions for each content type.
  692. $bundles = tripal_get_content_types();
  693. foreach ($bundles as $bundle) {
  694. $permissions['view ' . $bundle->name] = array(
  695. 'title' => t('%label: View Content', array('%label' => $bundle->label)),
  696. 'description' => t('Allow the user to view %label content', array('%label' => $bundle->label)),
  697. );
  698. $permissions['create ' . $bundle->name] = array(
  699. 'title' => t('%label: Create Content', array('%label' => $bundle->label)),
  700. 'description' => t('Allow the user to create %label content', array('%label' => $bundle->label)),
  701. 'restrict access' => TRUE,
  702. );
  703. $permissions['edit ' . $bundle->name] = array(
  704. 'title' => t('%label: Edit Content', array('%label' => $bundle->label)),
  705. 'description' => t('Allow the user to edit %label content', array('%label' => $bundle->label)),
  706. 'restrict access' => TRUE,
  707. );
  708. $permissions['unpublish ' . $bundle->name] = array(
  709. 'title' => t('%label: Unpublish Content', array('%label' => $bundle->label)),
  710. 'description' => t('Allow the user to unpublish %label content. Unpublishing of content removes it from visibility on the site but does not delete the record in the underlying database.', array('%label' => $bundle->label)),
  711. );
  712. $permissions['delete ' . $bundle->name] = array(
  713. 'title' => t('%label: Delete Content', array('%label' => $bundle->label)),
  714. 'description' => t('Allow the user to delete %label content. When content is deleted it is first unpublished and then deleted from the database.', array('%label' => $bundle->label)),
  715. 'restrict access' => TRUE,
  716. );
  717. }
  718. // Add permissions for each Importer
  719. $importers = tripal_get_importers();
  720. foreach ($importers as $class_name) {
  721. tripal_load_include_importer_class($class_name);
  722. if (class_exists($class_name)) {
  723. $machine_name = $class_name::$machine_name;
  724. $name = $class_name::$name;
  725. $permissions['use ' . $machine_name . ' importer'] = array(
  726. 'title' => t('Importer: Use the %label', array('%label' => $name)),
  727. 'description' => t('Allow the user to import data using the %label. Note: you may also need to give the "Upload Files" permission for importers to work.', array('%label' => $name)),
  728. 'restrict access' => TRUE,
  729. );
  730. }
  731. }
  732. return $permissions;
  733. }
  734. /**
  735. * Implements hook_theme().
  736. * Registers template files/functions used by this module.
  737. *
  738. * @ingroup tripal
  739. */
  740. function tripal_theme($existing, $type, $theme, $path) {
  741. $themes = array(
  742. // Admin messages theme
  743. 'tripal_admin_message' => array(
  744. 'function' => 'theme_tripal_admin_message',
  745. 'variables' => array('message' => NULL),
  746. ),
  747. 'tripal_entity' => array(
  748. 'render element' => 'elements',
  749. 'template' => 'tripal_entity',
  750. 'path' => "$path/theme/templates"
  751. ),
  752. 'tripal_add_list' => array(
  753. 'variables' => array('content' => NULL),
  754. ),
  755. // Themeing for all fields.
  756. 'tripal_field_default' => array(
  757. 'render element' => 'element',
  758. 'file' => 'includes/tripal.fields.inc',
  759. ),
  760. // Themed forms
  761. 'tripal_views_handler_area_collections_fields_fset' => array(
  762. 'render element' => 'form',
  763. 'file' => 'views_handlers/tripal_views_handler_area_collections.inc',
  764. ),
  765. );
  766. return $themes;
  767. }
  768. /**
  769. * Implements hook_coder_ignore().
  770. * Defines the path to the file (tripal.coder_ignores.txt) where ignore rules for coder are stored
  771. */
  772. function tripal_coder_ignore() {
  773. return array(
  774. 'path' => drupal_get_path('module', 'tripal'),
  775. 'line prefix' => drupal_get_path('module', 'tripal'),
  776. );
  777. }
  778. /**
  779. * Implements hook_libraries_info().
  780. */
  781. function tripal_libraries_info() {
  782. $libraries = array();
  783. $libraries['d3'] = array(
  784. 'name' => 'D3.js',
  785. 'vendor url' => 'http://d3js.org/',
  786. 'download url' => 'https://github.com/mbostock/d3',
  787. 'version arguments' => array(
  788. 'file' => 'd3.js',
  789. 'pattern' => '/\s*version: "(\d+\.\d+\.\d+)"/',
  790. ),
  791. 'files' => array(
  792. 'js' => array(
  793. 'd3.min.js',
  794. ),
  795. ),
  796. );
  797. return $libraries;
  798. }
  799. /**
  800. * Implements hook_admin_paths().
  801. * Define administrative paths.
  802. */
  803. function tripal_admin_paths() {
  804. $paths = array();
  805. if (variable_get('node_admin_theme')) {
  806. $paths = array(
  807. 'bio_data/*/edit' => TRUE,
  808. 'bio_data/*/delete' => TRUE,
  809. 'bio_data/*/unpublish' => TRUE,
  810. 'bio_data/add' => TRUE,
  811. 'bio_data/add/*' => TRUE,
  812. );
  813. }
  814. $paths['cv/lookup/*/*'] = TRUE;
  815. return $paths;
  816. }
  817. /**
  818. * Implements hook_menu_local_tasks_alter().
  819. *
  820. * Used to add action links to pages.
  821. */
  822. function tripal_menu_local_tasks_alter(&$data, $router_item, $root_path) {
  823. // Add an "Add Tripal Content" action link to the Admin >> Content >>
  824. // Biological Content page.
  825. if ($root_path == 'admin/content/bio_data') {
  826. $item = menu_get_item('bio_data/add');
  827. if ($item['access']) {
  828. $data['actions']['output'][] = array(
  829. '#theme' => 'menu_local_action',
  830. '#link' => $item,
  831. );
  832. }
  833. }
  834. }
  835. /**
  836. * Implements hook_shortcut_default_set().
  837. * Modify the shortcut menu to include Biological content links.
  838. *
  839. * @param object $account
  840. * The user account whose default shortcut set will be returned. If not provided, the
  841. * function will return the currently logged-in user's default shortcut set.
  842. *
  843. * @return
  844. * An object representing the default shortcut set.
  845. */
  846. function tripal_shortcut_default_set($account) {
  847. $sets = shortcut_sets();
  848. $found = FALSE;
  849. foreach ($sets as $set) {
  850. if ($set->title == 'TripalDefault') {
  851. $found = TRUE;
  852. }
  853. }
  854. if (!$found) {
  855. $t = get_t();
  856. // Create an initial default shortcut set.
  857. $shortcut_set = new stdClass();
  858. $shortcut_set->title = $t('TripalDefault');
  859. $shortcut_set->links = array(
  860. array(
  861. 'link_path' => 'node/add',
  862. 'link_title' => $t('Add content'),
  863. 'weight' => -35,
  864. ),
  865. array(
  866. 'link_path' => 'bio_data/add',
  867. 'link_title' => 'Add Tripal Content',
  868. 'weight' => -30,
  869. ),
  870. array(
  871. 'link_path' => 'admin/content',
  872. 'link_title' => $t('Find content'),
  873. 'weight' => -25,
  874. ),
  875. array(
  876. 'link_path' => 'admin/content/bio_data',
  877. 'link_title' => 'Find Tripal Content',
  878. 'weight' => -20,
  879. ),
  880. );
  881. shortcut_set_save($shortcut_set);
  882. }
  883. $sets = shortcut_sets();
  884. foreach ($sets as $set) {
  885. if ($set->title == 'TripalDefault') {
  886. return $set->set_name;
  887. }
  888. }
  889. }
  890. /**
  891. * Menu argument loader; Load a tripal data type by string.
  892. *
  893. * This function is not meant to be used as an API function. It is only meant
  894. * for use in the menu to resolve the %tripal_bundle wildcard.
  895. *
  896. * @param $type
  897. * The machine-readable name of a tripal data type to load.
  898. * @return
  899. * A tripal data type array or FALSE if $type does not exist.
  900. */
  901. function TripalBundle_load($bundle_type, $reset = FALSE) {
  902. // Get the type of entity by the ID.
  903. $bundle = db_select('tripal_bundle', 'tdt')
  904. ->fields('tdt')
  905. ->condition('name', $bundle_type)
  906. ->execute()
  907. ->fetchObject();
  908. if ($bundle) {
  909. $entity = entity_load('TripalBundle', array($bundle->id), array(), $reset);
  910. return reset($entity);
  911. }
  912. return FALSE;
  913. }
  914. /**
  915. * Allows the menu system to use a wildcard to fetch the entity.
  916. *
  917. * Make sure that the wildcard you choose in the tripal_entity entity
  918. * definition fits the function name here.
  919. *
  920. * This function is not meant to be used as an API function. It is only meant
  921. * for use in the menu to resolve the %tripal_entity wildcard.
  922. *
  923. * @param $id
  924. * Integer specifying the tripal_entity id.
  925. * @param $reset
  926. * A boolean indicating that the internal cache should be reset.
  927. * @return
  928. * A fully-loaded $tripal_entity object or FALSE if it cannot be loaded.
  929. *
  930. * @see tripal_entity_load_multiple()
  931. */
  932. function TripalEntity_load($id, $reset = FALSE) {
  933. // $entity = entity_load('TripalEntity', array($id), array(), $reset);
  934. $entity = tripal_load_entity('TripalEntity', array($id), $reset);
  935. return reset($entity);
  936. }
  937. /**
  938. * Imports all of the Tripal API into scope.
  939. *
  940. * Typically this function call is not necessary as all of the API is
  941. * automaticaly included by the tripal module. However this function can
  942. * be useful in the .install files during a site upgrade when the tripal
  943. * module is not enabld.
  944. *
  945. * Example usage:
  946. * @code
  947. * module_load_include('module', 'tripal', 'tripal');
  948. * tripal_import_api();
  949. * @endcode
  950. *
  951. */
  952. function tripal_import_api() {
  953. module_load_include('inc', 'tripal', 'api/tripal.d3js.api');
  954. module_load_include('inc', 'tripal', 'api/tripal.fields.api');
  955. module_load_include('inc', 'tripal', 'api/tripal.importer.api');
  956. module_load_include('inc', 'tripal', 'api/tripal.terms.api');
  957. module_load_include('inc', 'tripal', 'api/tripal.entities.api');
  958. module_load_include('inc', 'tripal', 'api/tripal.files.api');
  959. module_load_include('inc', 'tripal', 'api/tripal.jobs.api');
  960. module_load_include('inc', 'tripal', 'api/tripal.notice.api');
  961. module_load_include('inc', 'tripal', 'api/tripal.variables.api');
  962. module_load_include('inc', 'tripal', 'api/tripal.upload.api');
  963. module_load_include('inc', 'tripal', 'api/tripal.collections.api');
  964. module_load_include('inc', 'tripal', 'api/tripal.quotas.api');
  965. module_load_include('inc', 'tripal', 'api/tripal.DEPRECATED.api');
  966. }
  967. /**
  968. *
  969. * Implements hook_form_FORM_ID_alter().
  970. *
  971. * The field_ui_field_edit_form is used for customizing the settings of
  972. * a field attached to an entity.
  973. *
  974. * This alter function disables some of the form widgets when the storage
  975. * backend indicates they are not appropriate.
  976. */
  977. function tripal_form_field_ui_field_edit_form_alter(&$form, &$form_state, $form_id) {
  978. // If this is the field_ui_field_edit_form (i.e. the form that appears
  979. // when editing a field that is attached to an entity). Then we want
  980. // to add term settings for any field attached to a TripalEntity
  981. // content type.
  982. if ($form['#instance']['entity_type'] == 'TripalEntity') {
  983. // Add the form elements for setting the vocabulary terms.
  984. tripal_field_instance_settings_form_alter($form, $form_state);
  985. // Make sure we preserve the auto_attach settings.
  986. $auto_attach = TRUE;
  987. if (array_key_exists('auto_attach', $form['#instance']['settings'])) {
  988. $auto_attach = $form['#instance']['settings']['auto_attach'];
  989. }
  990. $form['instance']['settings']['auto_attach'] = array(
  991. '#type' => 'value',
  992. '#value' => $auto_attach,
  993. );
  994. }
  995. }
  996. /**
  997. * Implements hook_form_alter().
  998. */
  999. function tripal_form_alter(&$form, $form_state, $form_id) {
  1000. // Remove fields that have no form. It's just a bit too confusing to have
  1001. // widgets appear in the form but without any form elements inside them.
  1002. if ($form_id == 'tripal_entity_form') {
  1003. $children = element_children($form);
  1004. foreach ($children as $child) {
  1005. // Count the number of form elements.
  1006. if (array_key_exists('und', $form[$child])) {
  1007. $total_widgets = 0;
  1008. // Some fields with cardinality of one that aren't TripalFields
  1009. // may not have an array, so we need to catch those.
  1010. if (array_key_exists('#type', $form[$child]['und'])) {
  1011. $total_widgets++;
  1012. }
  1013. foreach ($form[$child]['und'] as $delta => $element) {
  1014. if (is_numeric($delta)) {
  1015. $total_widgets += count(element_children($element));
  1016. // Ignore the weight column
  1017. if (array_key_exists('_weight', $element)) {
  1018. $total_widgets--;
  1019. }
  1020. // Ignore a hidden value column
  1021. if (array_key_exists('value', $element) and $element['value']['#type'] == 'value') {
  1022. $total_widgets--;
  1023. }
  1024. // Some form elements don't have a 'value' and they don't have any
  1025. // widgets (i.e image field and description field. We don't
  1026. // want to loose those, so add one to the widget count.
  1027. if (!array_key_exists('value', $element)) {
  1028. $total_widgets++;
  1029. }
  1030. }
  1031. }
  1032. // If we have no widgets then here's not a form for this field so just
  1033. // remove it.
  1034. if ($total_widgets == 0) {
  1035. unset($form[$child]);
  1036. }
  1037. }
  1038. }
  1039. }
  1040. }
  1041. function tripal_check_new_fields($bundle_name) {
  1042. $bundle = tripal_load_bundle_entity(array('name' => $bundle_name));
  1043. $term = tripal_load_term_entity(array('term_id' => $bundle->term_id));
  1044. $added = tripal_create_bundle_fields($bundle, $term);
  1045. if (count($added) == 0) {
  1046. drupal_set_message('No new fields were added');
  1047. }
  1048. foreach ($added as $field_name) {
  1049. drupal_set_message('Added field: ' . $field_name);
  1050. }
  1051. drupal_goto("admin/structure/bio_data/manage/$bundle_name/fields");
  1052. }
  1053. /**
  1054. * Implements hook_block_info().
  1055. */
  1056. function tripal_block_info() {
  1057. $blocks = array();
  1058. $admin_theme = 'seven';
  1059. $blocks['notifications_block'] = array(
  1060. 'info' => t('Dashboard Notifications'),
  1061. 'visibility' => BLOCK_VISIBILITY_LISTED,
  1062. 'pages' => 'admin/dashboard',
  1063. 'status' => TRUE,
  1064. 'theme' => $admin_theme,
  1065. 'region' => 'dashboard_main',
  1066. 'properties' => array(
  1067. 'administrative' => TRUE,
  1068. ),
  1069. );
  1070. $blocks['content_type_barchart'] = array(
  1071. 'info' => t('Published Tripal Content'),
  1072. 'visibility' => BLOCK_VISIBILITY_LISTED,
  1073. 'pages' => 'admin/dashboard',
  1074. 'status' => TRUE,
  1075. 'theme' => $admin_theme,
  1076. 'region' => 'dashboard_main',
  1077. 'properties' => array(
  1078. 'administrative' => TRUE,
  1079. ),
  1080. );
  1081. $blocks['powered_by_tripal'] = array(
  1082. 'info' => t('Powered by Tripal'),
  1083. 'cache' => DRUPAL_NO_CACHE,
  1084. );
  1085. return $blocks;
  1086. }
  1087. /**
  1088. * Implements hook_block_view().
  1089. */
  1090. function tripal_block_view($delta = ''){
  1091. global $base_path;
  1092. $block = array();
  1093. // The $delta parameter tells us which block is being requested.
  1094. switch ($delta) {
  1095. case 'powered_by_tripal':
  1096. $size = variable_get('powered_by_tripal_size', 'small');
  1097. $type = variable_get('powered_by_tripal_type', 'bw');
  1098. $image = 'powered_by_tripal_bw_small.png';
  1099. if ($size == 'small' and $type == 'col') {
  1100. $image = 'powered_by_tripal_small.png';
  1101. }
  1102. if ($size == 'large' and $type == 'bw') {
  1103. $image = 'powered_by_tripal_bw.png';
  1104. }
  1105. if ($size == 'large' and $type == 'col') {
  1106. $image = 'powered_by_tripal.png';
  1107. }
  1108. $block['title'] = '';
  1109. $block['content'] = array(
  1110. '#markup' => '<a href="http://tripal.info"><img border="0" src="' . $base_path . drupal_get_path('module', 'tripal') . '/theme/images/' . $image . '"></a>',
  1111. );
  1112. break;
  1113. case 'content_type_barchart':
  1114. // The number of content types
  1115. $entity_types = db_select('tripal_bundle', 'tb')
  1116. ->fields('tb')
  1117. ->execute()
  1118. ->fetchAll();
  1119. $entity_count_listing = array();
  1120. // The number of entities per content type.
  1121. foreach($entity_types as $entity_types => $entity_type){
  1122. $result = db_select('chado_' . $entity_type->name, 'et')
  1123. ->fields('et')
  1124. ->execute();
  1125. $number_of_entities = $result->rowCount();
  1126. $entity_count_listing[$entity_types] = array(
  1127. 'name' => $entity_type->label,
  1128. 'count' => $number_of_entities,
  1129. );
  1130. }
  1131. tripal_add_d3js();
  1132. drupal_add_js(drupal_get_path ('module', 'tripal') . '/theme/js/tripal.dashboard.js');
  1133. drupal_add_css(drupal_get_path ('module', 'tripal') . '/theme/css/tripal.dashboard.css');
  1134. drupal_add_library('system', 'drupal.collapse');
  1135. drupal_add_js("var entityCountListing = " . json_encode($entity_count_listing) . ";", array('type' => 'inline'));
  1136. $output = "<div id=\"tripal-entity-types\" class=\"tripal-entity-types-pane\">
  1137. <p>A list of the published Tripal content types and the number of each.</p>
  1138. <div id=\"tripal-entity-type-chart\"></div>
  1139. </div>";
  1140. $block['title'] = '';
  1141. $block['content'] = array(
  1142. '#markup' => $output,
  1143. );
  1144. break;
  1145. case 'notifications_block':
  1146. // Create your block content here
  1147. $block['content'] = '';
  1148. // Prepare table header
  1149. $header = array(
  1150. 'title' => array('data' => t('Title')),
  1151. 'details' => array('data' => t('Details')),
  1152. 'type' => array('data' => t('Type'), 'field' => 'tan.type'),
  1153. 'actions' => array('data' => t('Actions'))
  1154. );
  1155. $query = db_select('tripal_admin_notfications', 'tan')
  1156. ->extend('TableSort');
  1157. $results = $query->fields('tan')
  1158. ->condition('enabled', 1, '=')
  1159. ->orderByHeader($header)
  1160. ->execute()->fetchAll();
  1161. $rows = array();
  1162. foreach($results as $result){
  1163. $data['operation'] = ' | ';
  1164. $data['operation'] .= l(t('Dismiss Notification'), 'admin/disable/notification/' . $result->note_id);
  1165. $actions = unserialize($result->actions);
  1166. foreach($actions as $action){
  1167. $label = key($actions);
  1168. $link = $action;
  1169. }
  1170. $rows[] = array(
  1171. 'Title' => $result->title,
  1172. 'Details' => $result->details,
  1173. 'Type' => $result->type,
  1174. 'Actions' => l(t($label), $link) . $data['operation'],
  1175. );
  1176. }
  1177. if(!empty($rows)) {
  1178. //Number of records shown in per page
  1179. $per_page = 10;
  1180. $current_page = pager_default_initialize(count($rows), $per_page);
  1181. $chunks = array_chunk($rows, $per_page, TRUE);
  1182. // Output of table with the paging
  1183. $table = theme('table',
  1184. array(
  1185. "header" => $header,
  1186. "rows" => $chunks[ $current_page ],
  1187. "attributes" => array(),
  1188. "sticky" => TRUE,
  1189. "caption" => "",
  1190. "colgroups" => array(),
  1191. "empty" => t("No notifications.")
  1192. )
  1193. );
  1194. $table .= theme('pager', array('quantity', count($rows)));
  1195. $fieldset_table = array(
  1196. '#title' => t('Notifications'),
  1197. '#collapsed' => FALSE,
  1198. '#collapsible' => TRUE,
  1199. '#attributes' => array('class' => array('collapsible')),
  1200. '#children' => $table,
  1201. );
  1202. //return pager with limited number of records.
  1203. $block['content'] = theme('fieldset', array('element' => $fieldset_table));
  1204. }
  1205. else {
  1206. $block['content'] = 'There are no notifications at this time.';
  1207. }
  1208. $block['title'] = 'Tripal Administrative Notifications';
  1209. break;
  1210. }
  1211. return $block;
  1212. }
  1213. /**
  1214. * Implements hook_block_save().
  1215. */
  1216. function tripal_block_save($delta = '', $edit = array()) {
  1217. switch ($delta) {
  1218. case 'powered_by_tripal':
  1219. if (!empty($edit['logo_size'])) {
  1220. variable_set('powered_by_tripal_size', $edit['logo_size']);
  1221. }
  1222. if (!empty($edit['logo_type'])) {
  1223. variable_set('powered_by_tripal_type', $edit['logo_type']);
  1224. }
  1225. }
  1226. }
  1227. /**
  1228. * Implements hook_block_configure().
  1229. */
  1230. function tripal_block_configure($delta = '') {
  1231. $form = array();
  1232. switch ($delta) {
  1233. case 'powered_by_tripal':
  1234. $form['logo_size'] = array(
  1235. '#type' => 'radios',
  1236. '#title' => t('Logo Size'),
  1237. '#default_value' => variable_get('powered_by_tripal_size', 'small'),
  1238. '#options' => array(
  1239. 'large' => t('Large'),
  1240. 'small' => t('Small')
  1241. ),
  1242. '#description' => t('Select if you would like a small or large "Powered by Tripal" logo.'),
  1243. );
  1244. $form['logo_type'] = array(
  1245. '#type' => 'radios',
  1246. '#title' => t('Logo Type'),
  1247. '#default_value' => variable_get('powered_by_tripal_type', 'bw'),
  1248. '#options' => array(
  1249. 'bw' => t('Gray scale'),
  1250. 'col' => t('Colored')
  1251. ),
  1252. '#description' => t('Select if you would like a black and white or colored "Powered by Tripal" logo.'),
  1253. );
  1254. }
  1255. return $form;
  1256. }
  1257. /**
  1258. * Implements hook_cron().
  1259. */
  1260. function tripal_cron() {
  1261. // Add jobs to the Tripal queue for commong tasks.
  1262. $args = [];
  1263. $includes = [];
  1264. if (variable_get('tripal_admin_notification_creation_during_cron', TRUE)) {
  1265. $modules = module_implements('tripal_cron_notification');
  1266. foreach ($modules as $module) {
  1267. $function = $module . '_tripal_cron_notification';
  1268. tripal_add_job("Cron: Checking for '$module' notifications.", 'tripal',
  1269. $function, $args, 1, 1, $includes, TRUE);
  1270. }
  1271. }
  1272. // Check for expired collections.
  1273. tripal_add_job('Cron: Checking expired collections', 'tripal',
  1274. 'tripal_expire_collections', $args, 1, 1, $includes, TRUE);
  1275. tripal_add_job('Cron: Checking expired files', 'tripal',
  1276. 'tripal_expire_files', $args, 1, 1, $includes, TRUE);
  1277. // Update the registration information every month.
  1278. if (variable_get('tripal_site_registration', FALSE)) {
  1279. $last_submit = variable_get('tripal_site_registration_last_update');
  1280. if ($last_submit) {
  1281. if ($last_submit <= strtotime('-1 month')) {
  1282. $registration = variable_get('tripal_site_registration', FALSE);
  1283. $success = tripal_registration_remote_submit($registration);
  1284. watchdog('Tripal Cron', 'Tripal registration has been successfull submitted to the remote service.', [], WATCHDOG_INFO);
  1285. }
  1286. }
  1287. }
  1288. }
  1289. /**
  1290. * Implements hook_element_info().
  1291. *
  1292. * Used for creating new form API elements.
  1293. */
  1294. function tripal_element_info() {
  1295. // Element for uploading large files. This form element
  1296. // accepts the following keys when using in a form:
  1297. // - #title: The title that will appear above the element.
  1298. // - #description: The description that will appear below the element.
  1299. // - #usage_type: Required. The type of file. This will be stored in
  1300. // the 'type' column of the file_usage table.
  1301. // - #usage_id: Required. A unique numeric ID representing an entity, node
  1302. // or some other record identifier. This can be any identifier that
  1303. // makes sense to the module that implements a form that uses this
  1304. // element.
  1305. // -#usage_module: The module that will be using the file. This will be
  1306. // stored in the 'module' column of the file_usage table.
  1307. // -#allowed_types: An array of file extensions that are allowed for
  1308. // to be uploaded.
  1309. // -#cardinality: A numeric value indicating the number of files the
  1310. // user can upload. Set to 0 for unlimited.
  1311. $elements['html5_file'] = array(
  1312. '#input' => 'TRUE',
  1313. '#process' => array('tripal_html5_file_process'),
  1314. '#element_validate' => array('tripal_html5_file_validate'),
  1315. '#value_callback' => 'tripal_html5_file_value',
  1316. );
  1317. return $elements;
  1318. }
  1319. /**
  1320. * The process function for the html5_file form element.
  1321. */
  1322. function tripal_html5_file_process($element, $form_state, $complete_form) {
  1323. $module = array_key_exists('#usage_module', $element) ? $element['#usage_module'] : 'tripal';
  1324. $type = $element['#usage_id'] . '-' . $element['#usage_type'] . '-' . $module;
  1325. $type_var_name = 'uploader_' . $element['#usage_id'] . '_' . $element['#usage_type'] . '_' . $module;
  1326. $name = $element['#name'];
  1327. $name = preg_replace('/[^\w]/', '_', $name);
  1328. $allowed_types = array_key_exists('#allowed_types', $element) ? $element['#allowed_types'] : array();
  1329. $cardinality = array_key_exists('#cardinality', $element) ? $element['#cardinality'] : 1;
  1330. $paired = array_key_exists('#paired', $element) ? $element['#paired'] : FALSE;
  1331. if ($paired) {
  1332. $headers = array(
  1333. array('data' => 'File #1'),
  1334. array('data' => 'Size', 'width' => '10%'),
  1335. array('data' => 'Upload Progress', 'width' => '20%'),
  1336. array('data' => 'Action', 'width' => '10%'),
  1337. array('data' => 'File #2'),
  1338. array('data' => 'Size', 'width' => '10%'),
  1339. array('data' => 'Upload Progress', 'width' => '20%'),
  1340. array('data' => 'Action', 'width' => '10%')
  1341. );
  1342. }
  1343. else {
  1344. $headers = array(
  1345. array('data' => 'File'),
  1346. array('data' => 'Size', 'width' => '10%'),
  1347. array('data' => 'Upload Progress', 'width' => '20%'),
  1348. array('data' => 'Action', 'width' => '10%'),
  1349. );
  1350. }
  1351. $rows = array();
  1352. $table_vars = array(
  1353. 'header' => $headers,
  1354. 'rows' => $rows,
  1355. 'attributes' => array(
  1356. 'class' => array('tripal-html5-file-upload-table'),
  1357. 'id' => 'tripal-html5-file-upload-table-' . $type
  1358. ),
  1359. 'sticky' => TRUE,
  1360. 'colgroups' => array(),
  1361. 'empty' => t('There are currently no files.'),
  1362. );
  1363. $element['html5_file_table_key'] = array(
  1364. '#type' => 'hidden',
  1365. '#value' => $type,
  1366. '#attributes' => array(
  1367. 'class' => array('tripal-html5-file-upload-table-key')
  1368. )
  1369. );
  1370. $element['html5_file_table'] = array(
  1371. '#type' => 'item',
  1372. '#title' => $element['#title'] ? $element['#title'] : 'File Upload',
  1373. '#description' => $element['#description'],
  1374. '#markup' => theme('table', $table_vars)
  1375. );
  1376. $element[$name] = array(
  1377. '#type' => 'hidden',
  1378. '#attributes' => array('id' => 'tripal-html5-upload-fid-' . $type),
  1379. '#default_value' => $element['#value'],
  1380. );
  1381. $element['html5_file_submit'] = array(
  1382. '#type' => 'submit',
  1383. '#value' => 'Upload File',
  1384. '#name' => 'tripal_html5_file_upload_submit-' . $type,
  1385. // We don't want this button to submit as the file upload
  1386. // is handled by the JavaScript code.
  1387. '#attributes' => array(
  1388. 'id' => 'tripal-html5-file-upload-submit-' . $type,
  1389. 'onclick' => 'return (false);'
  1390. )
  1391. );
  1392. if (!$paired) {
  1393. $categories = array($element['#usage_id'] . '-' . $element['#usage_type']);
  1394. }
  1395. else {
  1396. $categories = array(
  1397. $element['#usage_id'] . '-' . $element['#usage_type'] . '-f',
  1398. $element['#usage_id'] . '-' . $element['#usage_type'] . '-r',
  1399. );
  1400. }
  1401. $uploader_settings = array(
  1402. 'table_id' => '#tripal-html5-file-upload-table-' . $type,
  1403. 'submit_id' => '#tripal-html5-file-upload-submit-' . $type,
  1404. 'category' => $categories,
  1405. 'cardinality' => $cardinality,
  1406. 'target_id' => 'tripal-html5-upload-fid-' . $type,
  1407. 'module' => $module,
  1408. 'allowed_types' => $allowed_types,
  1409. );
  1410. drupal_add_js(array($type_var_name => $uploader_settings), 'setting');
  1411. drupal_add_js(drupal_get_path ('module', 'tripal') . '/theme/js/TripalUploader.js');
  1412. drupal_add_js(drupal_get_path ('module', 'tripal') . '/theme/js/TripalUploadFile.js');
  1413. drupal_add_js(drupal_get_path ('module', 'tripal') . '/theme/js/tripal.file.js');
  1414. return $element;
  1415. }
  1416. /**
  1417. * Implements the validate hook for the html5_file form element.
  1418. */
  1419. function tripal_html5_file_validate($element, &$form_state) {
  1420. $is_required = $element['#required'];
  1421. $name = $element['#name'];
  1422. $name = preg_replace('/[^\w]/', '_', $name);
  1423. $fid = NULL;
  1424. if (is_array($element['#value']) and array_key_exists($name, $element['#value'])) {
  1425. $fid = $element['#value'][$name];
  1426. }
  1427. // TODO: the fid should just be the $element['#value'] why isn't this
  1428. // working given the tripal_html5_file_value function below.
  1429. if ($is_required and !$fid) {
  1430. form_error($element, t('A file must be provided.'));
  1431. }
  1432. }
  1433. /**
  1434. * Implements hook_value() for the html5_file form element.
  1435. */
  1436. function tripal_html5_file_value($element, $input = FALSE, &$form_state) {
  1437. if ($input) {
  1438. if (is_array($input)) {
  1439. $name = $element['#name'];
  1440. $name = preg_replace('/[^\w]/', '_', $name);
  1441. return $input[$name];
  1442. }
  1443. else {
  1444. return $input;
  1445. }
  1446. }
  1447. }
  1448. /**
  1449. * Implements hook_field_display_alter().
  1450. *
  1451. * @param $display
  1452. * @param $context
  1453. */
  1454. function tripal_field_display_TripalEntity_alter(&$display, $context){
  1455. }
  1456. /**
  1457. * Implements hook_field_group_table_rows_alter().
  1458. *
  1459. * This hook is used for hiding empty rows in a Field Group Table field group.
  1460. *
  1461. * @param $element
  1462. * The field group object.
  1463. * @param $children
  1464. * An array of field names that are contained in the field group.
  1465. */
  1466. function tripal_field_group_table_rows_alter(&$element, &$children) {
  1467. // Iterate through the children of this table field group.
  1468. foreach ($children as $index => $child) {
  1469. if (is_array($element[$child])) {
  1470. $bundle = $element[$child]['#bundle'];
  1471. $bundle_info = tripal_load_bundle_entity(array('name' => $bundle));
  1472. $processed = FALSE;
  1473. if (array_key_exists('#processed', $element[$child]['#object']->$child)) {
  1474. $processed = $element[$child]['#object']->$child['#processed'];
  1475. }
  1476. // If the hide empty variable is turned on and ajax load is turned off
  1477. // then remove fields from the field group.
  1478. $hide_variable = tripal_get_bundle_variable('hide_empty_field', $bundle_info->id);
  1479. if ($hide_variable == TRUE and $processed == TRUE) {
  1480. $items = $element[$child]['#items'];
  1481. $field = field_info_field($child);
  1482. if ($field and tripal_field_is_empty($field, $items)) {
  1483. unset($children[$index]);
  1484. unset($element[$child]);
  1485. }
  1486. }
  1487. }
  1488. }
  1489. }