PageRenderTime 56ms CodeModel.GetById 21ms RepoModel.GetById 1ms app.codeStats 0ms

/ojs/ojs-2.3.0/classes/oai/ojs/OAIDAO.inc.php

https://github.com/mcrider/pkpUpgradeTestSuite
PHP | 499 lines | 301 code | 75 blank | 123 comment | 33 complexity | cbfee93fa1d27865ad1606b81011d62f MD5 | raw file
Possible License(s): GPL-2.0, LGPL-2.1
  1. <?php
  2. /**
  3. * @file classes/oai/ojs/OAIDAO.inc.php
  4. *
  5. * Copyright (c) 2003-2009 John Willinsky
  6. * Distributed under the GNU GPL v2. For full terms see the file docs/COPYING.
  7. *
  8. * @class OAIDAO
  9. * @ingroup oai_ojs
  10. * @see OAI
  11. *
  12. * @brief DAO operations for the OJS OAI interface.
  13. */
  14. // $Id: OAIDAO.inc.php,v 1.42 2009/05/06 22:31:14 asmecher Exp $
  15. import('oai.OAI');
  16. import('issue.Issue');
  17. class OAIDAO extends DAO {
  18. /** @var $oai JournalOAI parent OAI object */
  19. var $oai;
  20. /** Helper DAOs */
  21. var $journalDao;
  22. var $sectionDao;
  23. var $publishedArticleDao;
  24. var $articleGalleyDao;
  25. var $issueDao;
  26. var $authorDao;
  27. var $suppFileDao;
  28. var $journalSettingsDao;
  29. var $journalCache;
  30. var $sectionCache;
  31. /**
  32. * Constructor.
  33. */
  34. function OAIDAO() {
  35. parent::DAO();
  36. $this->journalDao =& DAORegistry::getDAO('JournalDAO');
  37. $this->sectionDao =& DAORegistry::getDAO('SectionDAO');
  38. $this->publishedArticleDao =& DAORegistry::getDAO('PublishedArticleDAO');
  39. $this->articleGalleyDao =& DAORegistry::getDAO('ArticleGalleyDAO');
  40. $this->issueDao =& DAORegistry::getDAO('IssueDAO');
  41. $this->authorDao =& DAORegistry::getDAO('AuthorDAO');
  42. $this->suppFileDao =& DAORegistry::getDAO('SuppFileDAO');
  43. $this->journalSettingsDao =& DAORegistry::getDAO('JournalSettingsDAO');
  44. $this->journalCache = array();
  45. $this->sectionCache = array();
  46. }
  47. /**
  48. * Set parent OAI object.
  49. * @param JournalOAI
  50. */
  51. function setOAI(&$oai) {
  52. $this->oai = $oai;
  53. }
  54. //
  55. // Records
  56. //
  57. /**
  58. * Return the *nix timestamp of the earliest published article.
  59. * @param $journalId int optional
  60. * @return int
  61. */
  62. function getEarliestDatestamp($journalId = null) {
  63. $result =& $this->retrieve(
  64. 'SELECT MIN(pa.date_published)
  65. FROM published_articles pa, issues i
  66. WHERE pa.issue_id = i.issue_id AND i.published = 1'
  67. . (isset($journalId) ? ' AND i.journal_id = ?' : ''),
  68. isset($journalId) ? $journalId : false
  69. );
  70. if (isset($result->fields[0])) {
  71. $timestamp = strtotime($this->datetimeFromDB($result->fields[0]));
  72. }
  73. if (!isset($timestamp) || $timestamp == -1) {
  74. $timestamp = 0;
  75. }
  76. $result->Close();
  77. unset($result);
  78. return $timestamp;
  79. }
  80. /**
  81. * Check if an article ID specifies a published article.
  82. * @param $articleId int
  83. * @param $journalId int optional
  84. * @return boolean
  85. */
  86. function recordExists($articleId, $journalId = null) {
  87. $result =& $this->retrieve(
  88. 'SELECT COUNT(*)
  89. FROM published_articles pa, issues i
  90. WHERE pa.issue_id = i.issue_id AND i.published = 1 AND pa.article_id = ?'
  91. . (isset($journalId) ? ' AND i.journal_id = ?' : ''),
  92. isset($journalId) ? array($articleId, $journalId) : $articleId
  93. );
  94. $returner = $result->fields[0] == 1;
  95. $result->Close();
  96. unset($result);
  97. return $returner;
  98. }
  99. /**
  100. * Return OAI record for specified article.
  101. * @param $articleId int
  102. * @param $journalId int optional
  103. * @return OAIRecord
  104. */
  105. function &getRecord($articleId, $journalId = null) {
  106. $result =& $this->retrieve(
  107. 'SELECT pa.*,
  108. a.article_id,
  109. i.issue_id,
  110. j.journal_id,
  111. s.section_id
  112. FROM published_articles pa,
  113. issues i,
  114. journals j,
  115. articles a,
  116. sections s
  117. WHERE pa.article_id = a.article_id
  118. AND s.section_id = a.section_id
  119. AND j.journal_id = a.journal_id
  120. AND pa.issue_id = i.issue_id
  121. AND i.published = 1
  122. AND pa.article_id = ?'
  123. . (isset($journalId) ? ' AND a.journal_id = ?' : ''),
  124. isset($journalId) ? array($articleId, $journalId) : $articleId
  125. );
  126. $returner = null;
  127. if ($result->RecordCount() != 0) {
  128. $row =& $result->GetRowAssoc(false);
  129. $returner =& $this->_returnRecordFromRow($row);
  130. }
  131. $result->Close();
  132. unset($result);
  133. return $returner;
  134. }
  135. /**
  136. * Return set of OAI records matching specified parameters.
  137. * @param $journalId int
  138. * @param $sectionId int
  139. * @parma $from int timestamp
  140. * @parma $until int timestamp
  141. * @param $offset int
  142. * @param $limit int
  143. * @param $total int
  144. * @return array OAIRecord
  145. */
  146. function &getRecords($journalId, $sectionId, $from, $until, $offset, $limit, &$total) {
  147. $records = array();
  148. $params = array();
  149. if (isset($journalId)) {
  150. array_push($params, $journalId);
  151. }
  152. if (isset($sectionId)) {
  153. array_push($params, $sectionId);
  154. }
  155. $result =& $this->retrieve(
  156. 'SELECT pa.*,
  157. a.article_id,
  158. j.journal_id,
  159. s.section_id,
  160. i.issue_id
  161. FROM published_articles pa,
  162. issues i,
  163. journals j,
  164. articles a,
  165. sections s
  166. WHERE pa.article_id = a.article_id
  167. AND s.section_id = a.section_id
  168. AND j.journal_id = a.journal_id
  169. AND pa.issue_id = i.issue_id
  170. AND i.published = 1'
  171. . (isset($journalId) ? ' AND a.journal_id = ?' : '')
  172. . (isset($sectionId) ? ' AND a.section_id = ?' : '')
  173. . (isset($from) ? ' AND pa.date_published >= ' . $this->datetimeToDB($from) : '')
  174. . (isset($until) ? ' AND pa.date_published <= ' . $this->datetimeToDB($until) : '')
  175. . ' ORDER BY journal_id',
  176. $params
  177. );
  178. $total = $result->RecordCount();
  179. $result->Move($offset);
  180. for ($count = 0; $count < $limit && !$result->EOF; $count++) {
  181. $row =& $result->GetRowAssoc(false);
  182. $records[] =& $this->_returnRecordFromRow($row);
  183. $result->moveNext();
  184. }
  185. $result->Close();
  186. unset($result);
  187. return $records;
  188. }
  189. /**
  190. * Return set of OAI identifiers matching specified parameters.
  191. * @param $journalId int
  192. * @param $sectionId int
  193. * @parma $from int timestamp
  194. * @parma $until int timestamp
  195. * @param $offset int
  196. * @param $limit int
  197. * @param $total int
  198. * @return array OAIIdentifier
  199. */
  200. function &getIdentifiers($journalId, $sectionId, $from, $until, $offset, $limit, &$total) {
  201. $records = array();
  202. $params = array();
  203. if (isset($journalId)) {
  204. array_push($params, $journalId);
  205. }
  206. if (isset($sectionId)) {
  207. array_push($params, $sectionId);
  208. }
  209. $result =& $this->retrieve(
  210. 'SELECT pa.article_id,
  211. pa.date_published,
  212. j.journal_id,
  213. s.section_id
  214. FROM published_articles pa,
  215. issues i,
  216. journals j,
  217. articles a,
  218. sections s
  219. WHERE pa.article_id = a.article_id
  220. AND s.section_id = a.section_id
  221. AND j.journal_id = a.journal_id
  222. AND pa.issue_id = i.issue_id AND i.published = 1'
  223. . (isset($journalId) ? ' AND a.journal_id = ?' : '')
  224. . (isset($sectionId) ? ' AND a.section_id = ?' : '')
  225. . (isset($from) ? ' AND pa.date_published >= ' . $this->datetimeToDB($from) : '')
  226. . (isset($until) ? ' AND pa.date_published <= ' . $this->datetimeToDB($until) : '')
  227. . ' ORDER BY journal_id',
  228. $params
  229. );
  230. $total = $result->RecordCount();
  231. $result->Move($offset);
  232. for ($count = 0; $count < $limit && !$result->EOF; $count++) {
  233. $row =& $result->GetRowAssoc(false);
  234. $records[] =& $this->_returnIdentifierFromRow($row);
  235. $result->moveNext();
  236. }
  237. $result->Close();
  238. unset($result);
  239. return $records;
  240. }
  241. /**
  242. * Cached function to get a journal
  243. * @param $journalId int
  244. * @return object
  245. */
  246. function &getJournal($journalId) {
  247. if (!isset($this->journalCache[$journalId])) {
  248. $this->journalCache[$journalId] =& $this->journalDao->getJournal($journalId);
  249. }
  250. return $this->journalCache[$journalId];
  251. }
  252. /**
  253. * Cached function to get an issue
  254. * @param $issueId int
  255. * @return object
  256. */
  257. function &getIssue($issueId) {
  258. if (!isset($this->issueCache[$issueId])) {
  259. $this->issueCache[$issueId] =& $this->issueDao->getIssueById($issueId);
  260. }
  261. return $this->issueCache[$issueId];
  262. }
  263. /**
  264. * Cached function to get a journal section
  265. * @param $sectionId int
  266. * @return object
  267. */
  268. function &getSection($sectionId) {
  269. if (!isset($this->sectionCache[$sectionId])) {
  270. $this->sectionCache[$sectionId] =& $this->sectionDao->getSection($sectionId);
  271. }
  272. return $this->sectionCache[$sectionId];
  273. }
  274. /**
  275. * Return OAIRecord object from database row.
  276. * @param $row array
  277. * @return OAIRecord
  278. */
  279. function &_returnRecordFromRow(&$row) {
  280. $record = new OAIRecord();
  281. $articleId = $row['article_id'];
  282. $publishedArticle =& $this->publishedArticleDao->getPublishedArticleByArticleId($articleId);
  283. $journal =& $this->getJournal($row['journal_id']);
  284. $section =& $this->getSection($row['section_id']);
  285. $issue =& $this->getIssue($row['issue_id']);
  286. $galleys =& $this->articleGalleyDao->getGalleysByArticle($articleId);
  287. $record->setData('article', $publishedArticle);
  288. $record->setData('journal', $journal);
  289. $record->setData('section', $section);
  290. $record->setData('issue', $issue);
  291. $record->setData('galleys', $galleys);
  292. $record->identifier = $this->oai->articleIdToIdentifier($row['article_id']);
  293. $record->datestamp = OAIUtils::UTCDate(strtotime($this->datetimeFromDB($row['date_published'])));
  294. $record->sets = array($journal->getPath() . ':' . $section->getLocalizedAbbrev());
  295. return $record;
  296. }
  297. /**
  298. * Return OAIIdentifier object from database row.
  299. * @param $row array
  300. * @return OAIIdentifier
  301. */
  302. function &_returnIdentifierFromRow(&$row) {
  303. $journal =& $this->getJournal($row['journal_id']);
  304. $section =& $this->getSection($row['section_id']);
  305. $record = new OAIRecord();
  306. $record->identifier = $this->oai->articleIdToIdentifier($row['article_id']);
  307. $record->datestamp = OAIUtils::UTCDate(strtotime($this->datetimeFromDB($row['date_published'])));
  308. $record->sets = array($journal->getPath() . ':' . $section->getLocalizedAbbrev());
  309. return $record;
  310. }
  311. //
  312. // Resumption tokens
  313. //
  314. /**
  315. * Clear stale resumption tokens.
  316. */
  317. function clearTokens() {
  318. $this->update(
  319. 'DELETE FROM oai_resumption_tokens WHERE expire < ?', time()
  320. );
  321. }
  322. /**
  323. * Retrieve a resumption token.
  324. * @return OAIResumptionToken
  325. */
  326. function &getToken($tokenId) {
  327. $result =& $this->retrieve(
  328. 'SELECT * FROM oai_resumption_tokens WHERE token = ?', $tokenId
  329. );
  330. if ($result->RecordCount() == 0) {
  331. $token = null;
  332. } else {
  333. $row =& $result->getRowAssoc(false);
  334. $token = new OAIResumptionToken($row['token'], $row['record_offset'], unserialize($row['params']), $row['expire']);
  335. }
  336. $result->Close();
  337. unset($result);
  338. return $token;
  339. }
  340. /**
  341. * Insert an OAI resumption token, generating a new ID.
  342. * @param $token OAIResumptionToken
  343. * @return OAIResumptionToken
  344. */
  345. function &insertToken(&$token) {
  346. do {
  347. // Generate unique token ID
  348. $token->id = md5(uniqid(mt_rand(), true));
  349. $result =& $this->retrieve(
  350. 'SELECT COUNT(*) FROM oai_resumption_tokens WHERE token = ?',
  351. $token->id
  352. );
  353. $val = $result->fields[0];
  354. $result->Close();
  355. unset($result);
  356. } while($val != 0);
  357. $this->update(
  358. 'INSERT INTO oai_resumption_tokens (token, record_offset, params, expire)
  359. VALUES
  360. (?, ?, ?, ?)',
  361. array($token->id, $token->offset, serialize($token->params), $token->expire)
  362. );
  363. return $token;
  364. }
  365. //
  366. // Sets
  367. //
  368. /**
  369. * Return hierarchy of OAI sets (journals plus journal sections).
  370. * @param $journalId int
  371. * @param $offset int
  372. * @param $total int
  373. * @return array OAISet
  374. */
  375. function &getJournalSets($journalId, $offset, &$total) {
  376. if (isset($journalId)) {
  377. $journals = array($this->journalDao->getJournal($journalId));
  378. } else {
  379. $journals =& $this->journalDao->getJournals();
  380. $journals =& $journals->toArray();
  381. }
  382. // FIXME Set descriptions
  383. $sets = array();
  384. foreach ($journals as $journal) {
  385. $title = $journal->getLocalizedTitle();
  386. $abbrev = $journal->getPath();
  387. array_push($sets, new OAISet($abbrev, $title, ''));
  388. $sections =& $this->sectionDao->getJournalSections($journal->getJournalId());
  389. foreach ($sections->toArray() as $section) {
  390. array_push($sets, new OAISet($abbrev . ':' . $section->getLocalizedAbbrev(), $section->getLocalizedTitle(), ''));
  391. }
  392. }
  393. if ($offset != 0) {
  394. $sets = array_slice($sets, $offset);
  395. }
  396. return $sets;
  397. }
  398. /**
  399. * Return the journal ID and section ID corresponding to a journal/section pairing.
  400. * @param $journalSpec string
  401. * @param $sectionSpec string
  402. * @param $restrictJournalId int
  403. * @return array (int, int)
  404. */
  405. function getSetJournalSectionId($journalSpec, $sectionSpec, $restrictJournalId = null) {
  406. $journalId = null;
  407. $journal =& $this->journalDao->getJournalByPath($journalSpec);
  408. if (!isset($journal) || (isset($restrictJournalId) && $journal->getJournalId() != $restrictJournalId)) {
  409. return array(0, 0);
  410. }
  411. $journalId = $journal->getJournalId();
  412. $sectionId = null;
  413. if (isset($sectionSpec)) {
  414. $section =& $this->sectionDao->getSectionByAbbrev($sectionSpec, $journal->getJournalId());
  415. if (isset($section)) {
  416. $sectionId = $section->getSectionId();
  417. } else {
  418. $sectionId = 0;
  419. }
  420. }
  421. return array($journalId, $sectionId);
  422. }
  423. }
  424. ?>