HistoryService.php 39 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536
  1. <?php
  2. require_once 'formatters/LengthFormatter.php';
  3. class Application_Service_HistoryService
  4. {
  5. private $con;
  6. private $timezone;
  7. const TEMPLATE_TYPE_ITEM = "item";
  8. const TEMPLATE_TYPE_FILE = "file";
  9. public function __construct()
  10. {
  11. $this->con = isset($con) ? $con : Propel::getConnection(CcPlayoutHistoryPeer::DATABASE_NAME);
  12. $this->timezone = Application_Model_Preference::GetTimezone();
  13. }
  14. public function getSupportedTemplateTypes()
  15. {
  16. return array(self::TEMPLATE_TYPE_ITEM, self::TEMPLATE_TYPE_FILE);
  17. }
  18. //opts is from datatables.
  19. public function getPlayedItemData($startDT, $endDT, $opts, $instanceId=null)
  20. {
  21. $mainSqlQuery = "";
  22. $paramMap = array();
  23. $sqlTypes = $this->getSqlTypes();
  24. $start = $startDT->format("Y-m-d H:i:s");
  25. $end = $endDT->format("Y-m-d H:i:s");
  26. $template = $this->getConfiguredItemTemplate();
  27. $fields = $template["fields"];
  28. $required = $this->mandatoryItemFields();
  29. $fields_filemd = array();
  30. $filemd_keys = array();
  31. $fields_general = array();
  32. $general_keys = array();
  33. foreach ($fields as $index=>$field) {
  34. if (in_array($field["name"], $required)) {
  35. continue;
  36. }
  37. if ($field["isFileMd"]) {
  38. $fields_filemd[] = $field;
  39. $filemd_keys[] = $field["name"];
  40. }
  41. else {
  42. $fields_general[] = $field;
  43. $general_keys[] = $field["name"];
  44. }
  45. }
  46. //-----------------------------------------------------------------------
  47. //Using the instance_id to filter the data.
  48. $historyRange = "(".
  49. "SELECT history.starts, history.ends, history.id AS history_id, history.instance_id".
  50. " FROM cc_playout_history as history";
  51. if (isset($instanceId)) {
  52. $historyRange.= " WHERE history.instance_id = :instance";
  53. $paramMap["instance"] = $instanceId;
  54. }
  55. else {
  56. $historyRange.= " WHERE history.starts >= :starts and history.starts < :ends";
  57. $paramMap["starts"] = $start;
  58. $paramMap["ends"] = $end;
  59. }
  60. $historyRange.= ") AS history_range";
  61. $manualMeta = "(".
  62. "SELECT %KEY%.value AS %KEY%, %KEY%.history_id".
  63. " FROM (".
  64. " SELECT * from cc_playout_history_metadata AS phm WHERE phm.key = :meta_%KEY%".
  65. " ) AS %KEY%".
  66. " ) AS %KEY%_filter";
  67. $mainSelect = array(
  68. "history_range.starts",
  69. "history_range.ends",
  70. "history_range.history_id",
  71. "history_range.instance_id"
  72. );
  73. $mdFilters = array();
  74. $numFileMdFields = count($fields_filemd);
  75. if ($numFileMdFields > 0) {
  76. //these 3 selects are only needed if $fields_filemd has some fields.
  77. $fileSelect = array("history_file.history_id");
  78. $nonNullFileSelect = array("file.id as file_id");
  79. $nullFileSelect = array("null_file.history_id");
  80. $fileMdFilters = array();
  81. //populate the different dynamic selects with file info.
  82. for ($i = 0; $i < $numFileMdFields; $i++) {
  83. $field = $fields_filemd[$i];
  84. $key = $field["name"];
  85. $type = $sqlTypes[$field["type"]];
  86. $fileSelect[] = "file_md.{$key}::{$type}";
  87. $nonNullFileSelect[] = "file.{$key}::{$type}";
  88. $nullFileSelect[] = "{$key}_filter.{$key}::{$type}";
  89. $mainSelect[] = "file_info.{$key}::{$type}";
  90. $fileMdFilters[] = str_replace("%KEY%", $key, $manualMeta);
  91. $paramMap["meta_{$key}"] = $key;
  92. }
  93. //the files associated with scheduled playback in Airtime.
  94. $historyFile = "(".
  95. "SELECT history.id AS history_id, history.file_id".
  96. " FROM cc_playout_history AS history".
  97. " WHERE history.file_id IS NOT NULL".
  98. ") AS history_file";
  99. $fileMd = "(".
  100. "SELECT %NON_NULL_FILE_SELECT%".
  101. " FROM cc_files AS file".
  102. ") AS file_md";
  103. $fileMd = str_replace("%NON_NULL_FILE_SELECT%", join(", ", $nonNullFileSelect), $fileMd);
  104. //null files are from manually added data (filling in webstream info etc)
  105. $nullFile = "(".
  106. "SELECT history.id AS history_id".
  107. " FROM cc_playout_history AS history".
  108. " WHERE history.file_id IS NULL".
  109. ") AS null_file";
  110. //----------------------------------
  111. //building the file inner query
  112. $fileSqlQuery =
  113. "SELECT ".join(", ", $fileSelect).
  114. " FROM {$historyFile}".
  115. " LEFT JOIN {$fileMd} USING (file_id)".
  116. " UNION".
  117. " SELECT ".join(", ", $nullFileSelect).
  118. " FROM {$nullFile}";
  119. foreach ($fileMdFilters as $filter) {
  120. $fileSqlQuery.=
  121. " LEFT JOIN {$filter} USING(history_id)";
  122. }
  123. }
  124. for ($i = 0, $len = count($fields_general); $i < $len; $i++) {
  125. $field = $fields_general[$i];
  126. $key = $field["name"];
  127. $type = $sqlTypes[$field["type"]];
  128. $mdFilters[] = str_replace("%KEY%", $key, $manualMeta);
  129. $paramMap["meta_{$key}"] = $key;
  130. $mainSelect[] = "{$key}_filter.{$key}::{$type}";
  131. }
  132. $mainSqlQuery.=
  133. "SELECT ".join(", ", $mainSelect).
  134. " FROM {$historyRange}";
  135. if (isset($fileSqlQuery)) {
  136. $mainSqlQuery.=
  137. " LEFT JOIN ( {$fileSqlQuery} ) as file_info USING(history_id)";
  138. }
  139. foreach ($mdFilters as $filter) {
  140. $mainSqlQuery.=
  141. " LEFT JOIN {$filter} USING(history_id)";
  142. }
  143. //----------------------------------------------------------------------
  144. //need to count the total rows to tell Datatables.
  145. $stmt = $this->con->prepare($mainSqlQuery);
  146. foreach ($paramMap as $param => $v) {
  147. $stmt->bindValue($param, $v);
  148. }
  149. if ($stmt->execute()) {
  150. $totalRows = $stmt->rowCount();
  151. }
  152. else {
  153. $msg = implode(',', $stmt->errorInfo());
  154. throw new Exception("Error: $msg");
  155. }
  156. //------------------------------------------------------------------------
  157. //Using Datatables parameters to sort the data.
  158. if (empty($opts["iSortingCols"])) {
  159. $orderBys = array();
  160. } else {
  161. $numOrderColumns = $opts["iSortingCols"];
  162. $orderBys = array();
  163. for ($i = 0; $i < $numOrderColumns; $i++) {
  164. $colNum = $opts["iSortCol_".$i];
  165. $key = $opts["mDataProp_".$colNum];
  166. $sortDir = $opts["sSortDir_".$i];
  167. if (in_array($key, $required)) {
  168. $orderBys[] = "history_range.{$key} {$sortDir}";
  169. }
  170. else if (in_array($key, $filemd_keys)) {
  171. $orderBys[] = "file_info.{$key} {$sortDir}";
  172. }
  173. else if (in_array($key, $general_keys)) {
  174. $orderBys[] = "{$key}_filter.{$key} {$sortDir}";
  175. }
  176. else {
  177. //throw new Exception("Error: $key is not part of the template.");
  178. }
  179. }
  180. }
  181. if (count($orderBys) > 0) {
  182. $orders = join(", ", $orderBys);
  183. $mainSqlQuery.=
  184. " ORDER BY {$orders}";
  185. }
  186. //---------------------------------------------------------------
  187. //using Datatables parameters to add limits/offsets
  188. $displayLength = empty($opts["iDisplayLength"]) ? -1 : intval($opts["iDisplayLength"]);
  189. //limit the results returned.
  190. if ($displayLength !== -1) {
  191. $mainSqlQuery.=
  192. " OFFSET :offset LIMIT :limit";
  193. $paramMap["offset"] = intval($opts["iDisplayStart"]);
  194. $paramMap["limit"] = $displayLength;
  195. }
  196. $stmt = $this->con->prepare($mainSqlQuery);
  197. foreach ($paramMap as $param => $v) {
  198. $stmt->bindValue($param, $v);
  199. }
  200. $rows = array();
  201. if ($stmt->execute()) {
  202. $rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
  203. }
  204. else {
  205. $msg = implode(',', $stmt->errorInfo());
  206. throw new Exception("Error: $msg");
  207. }
  208. //-----------------------------------------------------------------------
  209. //processing results.
  210. $timezoneUTC = new DateTimeZone("UTC");
  211. $timezoneLocal = new DateTimeZone($this->timezone);
  212. $boolCast = array();
  213. foreach ($fields as $index=>$field) {
  214. if ($field["type"] == TEMPLATE_BOOLEAN) {
  215. $boolCast[] = $field;
  216. }
  217. }
  218. foreach ($rows as $index => &$result) {
  219. foreach ($boolCast as $field) {
  220. $result[$field['label']] = (bool) $result[$field['name']];
  221. }
  222. //need to display the results in the station's timezone.
  223. $dateTime = new DateTime($result["starts"], $timezoneUTC);
  224. $dateTime->setTimezone($timezoneLocal);
  225. $result["starts"] = $dateTime->format("Y-m-d H:i:s");
  226. //if ends is null we don't want it to default to "now"
  227. if (isset($result["ends"])) {
  228. $dateTime = new DateTime($result["ends"], $timezoneUTC);
  229. $dateTime->setTimezone($timezoneLocal);
  230. $result["ends"] = $dateTime->format("Y-m-d H:i:s");
  231. }
  232. if (isset($result[MDATA_KEY_DURATION])) {
  233. $formatter = new LengthFormatter($result[MDATA_KEY_DURATION]);
  234. $result[MDATA_KEY_DURATION] = $formatter->format();
  235. }
  236. //need to add a checkbox..
  237. $result["checkbox"] = "";
  238. //$unicodeChar = '\u2612';
  239. //$result["new"] = json_decode('"'.$unicodeChar.'"');
  240. //$result["new"] = "U+2612";
  241. }
  242. return array(
  243. "sEcho" => empty($opts["sEcho"]) ? null : intval($opts["sEcho"]),
  244. //"iTotalDisplayRecords" => intval($totalDisplayRows),
  245. "iTotalDisplayRecords" => intval($totalRows),
  246. "iTotalRecords" => intval($totalRows),
  247. "history" => $rows
  248. );
  249. }
  250. public function getFileSummaryData($startDT, $endDT, $opts)
  251. {
  252. $select = array (
  253. "summary.played",
  254. "summary.file_id",
  255. "summary.".MDATA_KEY_TITLE,
  256. "summary.".MDATA_KEY_CREATOR
  257. );
  258. $mainSqlQuery = "";
  259. $paramMap = array();
  260. $start = $startDT->format("Y-m-d H:i:s");
  261. $end = $endDT->format("Y-m-d H:i:s");
  262. $paramMap["starts"] = $start;
  263. $paramMap["ends"] = $end;
  264. $template = $this->getConfiguredFileTemplate();
  265. $fields = $template["fields"];
  266. $required = $this->mandatoryFileFields();
  267. foreach ($fields as $index=>$field) {
  268. $key = $field["name"];
  269. if (in_array($field["name"], $required)) {
  270. continue;
  271. }
  272. $select[] = "summary.{$key}";
  273. }
  274. $fileSummaryTable = "((
  275. SELECT COUNT(history.file_id) as played, history.file_id as file_id
  276. FROM cc_playout_history AS history
  277. WHERE history.starts >= :starts AND history.starts < :ends
  278. AND history.file_id IS NOT NULL
  279. GROUP BY history.file_id
  280. ) AS playout
  281. LEFT JOIN cc_files AS file ON (file.id = playout.file_id)) AS summary";
  282. $mainSqlQuery.=
  283. "SELECT ".join(", ", $select).
  284. " FROM {$fileSummaryTable}";
  285. //-------------------------------------------------------------------------
  286. //need to count the total rows to tell Datatables.
  287. $stmt = $this->con->prepare($mainSqlQuery);
  288. foreach ($paramMap as $param => $v) {
  289. $stmt->bindValue($param, $v);
  290. }
  291. if ($stmt->execute()) {
  292. $totalRows = $stmt->rowCount();
  293. }
  294. else {
  295. $msg = implode(',', $stmt->errorInfo());
  296. throw new Exception("Error: $msg");
  297. }
  298. //------------------------------------------------------------------------
  299. //Using Datatables parameters to sort the data.
  300. $numOrderColumns = $opts["iSortingCols"];
  301. $orderBys = array();
  302. for ($i = 0; $i < $numOrderColumns; $i++) {
  303. $colNum = $opts["iSortCol_".$i];
  304. $key = $opts["mDataProp_".$colNum];
  305. $sortDir = $opts["sSortDir_".$i];
  306. $orderBys[] = "summary.{$key} {$sortDir}";
  307. }
  308. if ($numOrderColumns > 0) {
  309. $orders = join(", ", $orderBys);
  310. $mainSqlQuery.=
  311. " ORDER BY {$orders}";
  312. }
  313. //------------------------------------------------------------
  314. //using datatables params to add limits/offsets
  315. $displayLength = intval($opts["iDisplayLength"]);
  316. if ($displayLength !== -1) {
  317. $mainSqlQuery.=
  318. " OFFSET :offset LIMIT :limit";
  319. $paramMap["offset"] = $opts["iDisplayStart"];
  320. $paramMap["limit"] = $displayLength;
  321. }
  322. $stmt = $this->con->prepare($mainSqlQuery);
  323. foreach ($paramMap as $param => $v) {
  324. $stmt->bindValue($param, $v);
  325. }
  326. $rows = array();
  327. if ($stmt->execute()) {
  328. $rows = $stmt->fetchAll(PDO::FETCH_ASSOC);
  329. }
  330. else {
  331. $msg = implode(',', $stmt->errorInfo());
  332. throw new Exception("Error: $msg");
  333. }
  334. //-----------------------------------------------------------------
  335. //processing the results
  336. foreach ($rows as &$row) {
  337. if (isset($row[MDATA_KEY_DURATION])) {
  338. $formatter = new LengthFormatter($row[MDATA_KEY_DURATION]);
  339. $row[MDATA_KEY_DURATION] = $formatter->format();
  340. }
  341. }
  342. return array(
  343. "sEcho" => intval($opts["sEcho"]),
  344. //"iTotalDisplayRecords" => intval($totalDisplayRows),
  345. "iTotalDisplayRecords" => intval($totalRows),
  346. "iTotalRecords" => intval($totalRows),
  347. "history" => $rows
  348. );
  349. }
  350. public function getShowList($startDT, $endDT, $userId = null)
  351. {
  352. if (empty($userId)) {
  353. $user = Application_Model_User::getCurrentUser();
  354. } else {
  355. $user = new Application_Model_User($userId);
  356. }
  357. $shows = Application_Model_Show::getShows($startDT, $endDT);
  358. Logging::info($startDT->format("Y-m-d H:i:s"));
  359. Logging::info($endDT->format("Y-m-d H:i:s"));
  360. Logging::info($shows);
  361. //need to filter the list to only their shows
  362. if ((!empty($user)) && ($user->isHost())) {
  363. $showIds = array();
  364. foreach ($shows as $show) {
  365. $showIds[] = $show["show_id"];
  366. }
  367. $showIds = array_unique($showIds);
  368. Logging::info($showIds);
  369. $hostRecords = CcShowHostsQuery::create()
  370. ->filterByDbHost($user->getId())
  371. ->filterByDbShow($showIds)
  372. ->find($this->con);
  373. $filteredShowIds = array();
  374. foreach($hostRecords as $record) {
  375. $filteredShowIds[] = $record->getDbShow();
  376. }
  377. Logging::info($filteredShowIds);
  378. $filteredShows = array();
  379. foreach($shows as $show) {
  380. if (in_array($show["show_id"], $filteredShowIds)) {
  381. $filteredShows[] = $show;
  382. }
  383. }
  384. }
  385. else {
  386. $filteredShows = $shows;
  387. }
  388. $timezoneUTC = new DateTimeZone("UTC");
  389. $timezoneLocal = new DateTimeZone($this->timezone);
  390. foreach ($filteredShows as &$result) {
  391. //need to display the results in the station's timezone.
  392. $dateTime = new DateTime($result["starts"], $timezoneUTC);
  393. $dateTime->setTimezone($timezoneLocal);
  394. $result["starts"] = $dateTime->format("Y-m-d H:i:s");
  395. $dateTime = new DateTime($result["ends"], $timezoneUTC);
  396. $dateTime->setTimezone($timezoneLocal);
  397. $result["ends"] = $dateTime->format("Y-m-d H:i:s");
  398. }
  399. return $filteredShows;
  400. }
  401. public function insertWebstreamMetadata($schedId, $startDT, $data) {
  402. $this->con->beginTransaction();
  403. try {
  404. $item = CcScheduleQuery::create()->findPK($schedId, $this->con);
  405. //TODO figure out how to combine these all into 1 query.
  406. $showInstance = $item->getCcShowInstances($this->con);
  407. $show = $showInstance->getCcShow($this->con);
  408. $webstream = $item->getCcWebstream($this->con);
  409. $metadata = array();
  410. $metadata["showname"] = $show->getDbName();
  411. $metadata[MDATA_KEY_TITLE] = $data->title;
  412. $metadata[MDATA_KEY_CREATOR] = $webstream->getDbName();
  413. $history = new CcPlayoutHistory();
  414. $history->setDbStarts($startDT);
  415. $history->setDbEnds(null);
  416. $history->setDbInstanceId($item->getDbInstanceId());
  417. foreach ($metadata as $key => $val) {
  418. $meta = new CcPlayoutHistoryMetaData();
  419. $meta->setDbKey($key);
  420. $meta->setDbValue($val);
  421. $history->addCcPlayoutHistoryMetaData($meta);
  422. }
  423. $history->save($this->con);
  424. $this->con->commit();
  425. }
  426. catch (Exception $e) {
  427. $this->con->rollback();
  428. throw $e;
  429. }
  430. }
  431. public function insertPlayedItem($schedId) {
  432. $this->con->beginTransaction();
  433. try {
  434. $item = CcScheduleQuery::create()->findPK($schedId, $this->con);
  435. if (is_null($item)) {
  436. throw new Exception("Invalid schedule id: ".$schedId);
  437. }
  438. //TODO figure out how to combine these all into 1 query.
  439. $showInstance = $item->getCcShowInstances($this->con);
  440. $show = $showInstance->getCcShow($this->con);
  441. $fileId = $item->getDbFileId();
  442. //don't add webstreams
  443. if (isset($fileId)) {
  444. $metadata = array();
  445. $metadata["showname"] = $show->getDbName();
  446. $instanceEnd = $showInstance->getDbEnds(null);
  447. $itemEnd = $item->getDbEnds(null);
  448. $recordStart = $item->getDbStarts(null);
  449. $recordEnd = ($instanceEnd < $itemEnd) ? $instanceEnd : $itemEnd;
  450. //first check if this is a duplicate
  451. // (caused by restarting liquidsoap)
  452. $prevRecord = CcPlayoutHistoryQuery::create()
  453. ->filterByDbStarts($recordStart)
  454. ->filterByDbEnds($recordEnd)
  455. ->filterByDbFileId($fileId)
  456. ->findOne($this->con);
  457. if (empty($prevRecord)) {
  458. $history = new CcPlayoutHistory();
  459. $history->setDbFileId($fileId);
  460. $history->setDbStarts($recordStart);
  461. $history->setDbEnds($recordEnd);
  462. $history->setDbInstanceId($item->getDbInstanceId());
  463. foreach ($metadata as $key => $val) {
  464. $meta = new CcPlayoutHistoryMetaData();
  465. $meta->setDbKey($key);
  466. $meta->setDbValue($val);
  467. $history->addCcPlayoutHistoryMetaData($meta);
  468. }
  469. $history->save($this->con);
  470. $this->con->commit();
  471. }
  472. }
  473. }
  474. catch (Exception $e) {
  475. $this->con->rollback();
  476. throw $e;
  477. }
  478. }
  479. /* id is an id in cc_playout_history */
  480. public function makeHistoryItemForm($id, $populate=false) {
  481. try {
  482. $form = new Application_Form_EditHistoryItem();
  483. $template = $this->getConfiguredItemTemplate();
  484. $required = $this->mandatoryItemFields();
  485. $form->createFromTemplate($template["fields"], $required);
  486. if ($populate) {
  487. $formValues = array();
  488. $historyRecord = CcPlayoutHistoryQuery::create()->findPk($id, $this->con);
  489. $file = $historyRecord->getCcFiles($this->con);
  490. $instance = $historyRecord->getCcShowInstances($this->con);
  491. if (isset($instance)) {
  492. $show = $instance->getCcShow($this->con);
  493. $selOpts = array();
  494. $instance_id = $instance->getDbId();
  495. $selOpts[$instance_id] = $show->getDbName();
  496. $form->populateShowInstances($selOpts, $instance_id);
  497. }
  498. if (isset($file)) {
  499. $f = Application_Model_StoredFile::createWithFile($file, $this->con);
  500. $filemd = $f->getDbColMetadata();
  501. }
  502. $metadata = array();
  503. $mds = $historyRecord->getCcPlayoutHistoryMetaDatas();
  504. foreach ($mds as $md) {
  505. $metadata[$md->getDbKey()] = $md->getDbValue();
  506. }
  507. $prefix = Application_Form_EditHistoryItem::ID_PREFIX;
  508. $formValues["{$prefix}id"] = $id;
  509. foreach($template["fields"] as $index => $field) {
  510. $key = $field["name"];
  511. $value = "";
  512. if (in_array($key, $required)) {
  513. $method = "getDb".ucfirst($key);
  514. $value = $historyRecord->$method();
  515. }
  516. else if (isset($filemd) && $field["isFileMd"]) {
  517. $value = $filemd[$key];
  518. }
  519. else if (isset($metadata[$key])) {
  520. $value = $metadata[$key];
  521. }
  522. //need to convert to the station's local time first.
  523. if ($field["type"] == TEMPLATE_DATETIME && !is_null($value)) {
  524. $timezoneUTC = new DateTimeZone("UTC");
  525. $timezoneLocal = new DateTimeZone($this->timezone);
  526. $dateTime = new DateTime($value, $timezoneUTC);
  527. $dateTime->setTimezone($timezoneLocal);
  528. $value = $dateTime->format("Y-m-d H:i:s");
  529. }
  530. $formValues["$prefix{$key}"] = $value;
  531. }
  532. $form->populate($formValues);
  533. }
  534. return $form;
  535. }
  536. catch (Exception $e) {
  537. Logging::info($e);
  538. throw $e;
  539. }
  540. }
  541. /* id is an id in cc_files */
  542. public function makeHistoryFileForm($id) {
  543. try {
  544. $form = new Application_Form_EditHistoryFile();
  545. $template = $this->getConfiguredFileTemplate();
  546. $required = $this->mandatoryFileFields();
  547. $form->createFromTemplate($template["fields"], $required);
  548. $file = Application_Model_StoredFile::RecallById($id, $this->con);
  549. $md = $file->getDbColMetadata();
  550. $prefix = Application_Form_EditHistoryFile::ID_PREFIX;
  551. $formValues = array();
  552. $formValues["{$prefix}id"] = $id;
  553. foreach($template["fields"] as $index => $field) {
  554. $key = $field["name"];
  555. if (in_array($key, $required)) {
  556. continue;
  557. }
  558. $value = $md[$key];
  559. $formValues["$prefix{$key}"] = $value;
  560. }
  561. $form->populate($formValues);
  562. return $form;
  563. }
  564. catch (Exception $e) {
  565. Logging::info($e);
  566. throw $e;
  567. }
  568. }
  569. public function populateTemplateFile($values, $id) {
  570. $this->con->beginTransaction();
  571. try {
  572. $file = Application_Model_StoredFile::RecallById($id, $this->con);
  573. $prefix = Application_Form_EditHistoryFile::ID_PREFIX;
  574. $prefix_len = strlen($prefix);
  575. $templateValues = $values[$prefix."template"];
  576. $md = array();
  577. foreach ($templateValues as $index => $value) {
  578. $key = substr($index, $prefix_len);
  579. $md[$key] = $value;
  580. }
  581. $file->setDbColMetadata($md);
  582. $this->con->commit();
  583. }
  584. catch (Exception $e) {
  585. $this->con->rollback();
  586. throw $e;
  587. }
  588. }
  589. public function populateTemplateItem($values, $id=null, $instance_id=null) {
  590. $this->con->beginTransaction();
  591. try {
  592. $template = $this->getConfiguredItemTemplate();
  593. $prefix = Application_Form_EditHistoryItem::ID_PREFIX;
  594. if (isset($id)) {
  595. $historyRecord = CcPlayoutHistoryQuery::create()->findPk($id, $this->con);
  596. }
  597. else {
  598. $historyRecord = new CcPlayoutHistory();
  599. }
  600. if (isset($instance_id)) {
  601. $historyRecord->setDbInstanceId($instance_id);
  602. }
  603. $timezoneUTC = new DateTimeZone("UTC");
  604. $timezoneLocal = new DateTimeZone($this->timezone);
  605. $dateTime = new DateTime($values[$prefix."starts"], $timezoneLocal);
  606. $dateTime->setTimezone($timezoneUTC);
  607. $historyRecord->setDbStarts($dateTime->format("Y-m-d H:i:s"));
  608. $dateTime = new DateTime($values[$prefix."ends"], $timezoneLocal);
  609. $dateTime->setTimezone($timezoneUTC);
  610. $historyRecord->setDbEnds($dateTime->format("Y-m-d H:i:s"));
  611. $templateValues = $values[$prefix."template"];
  612. $file = $historyRecord->getCcFiles();
  613. $md = array();
  614. $metadata = array();
  615. $fields = $template["fields"];
  616. $required = $this->mandatoryItemFields();
  617. $phpCasts = $this->getPhpCasts();
  618. for ($i = 0, $len = count($fields); $i < $len; $i++) {
  619. $field = $fields[$i];
  620. $key = $field["name"];
  621. //required is delt with before this loop.
  622. if (in_array($key, $required)) {
  623. continue;
  624. }
  625. $isFileMd = $field["isFileMd"];
  626. $entry = $phpCasts[$field["type"]]($templateValues[$prefix.$key]);
  627. if ($isFileMd && isset($file)) {
  628. Logging::info("adding metadata associated to a file for {$key} = {$entry}");
  629. $md[$key] = $entry;
  630. }
  631. else {
  632. Logging::info("adding metadata for {$key} = {$entry}");
  633. $metadata[$key] = $entry;
  634. }
  635. }
  636. if (count($md) > 0) {
  637. $f = Application_Model_StoredFile::createWithFile($file, $this->con);
  638. $f->setDbColMetadata($md);
  639. }
  640. //Use this array to update existing values.
  641. $mds = $historyRecord->getCcPlayoutHistoryMetaDatas();
  642. foreach ($mds as $md) {
  643. $prevmd[$md->getDbKey()] = $md;
  644. }
  645. foreach ($metadata as $key => $val) {
  646. if (isset($prevmd[$key])) {
  647. $meta = $prevmd[$key];
  648. $meta->setDbValue($val);
  649. }
  650. else {
  651. $meta = new CcPlayoutHistoryMetaData();
  652. $meta->setDbKey($key);
  653. $meta->setDbValue($val);
  654. $historyRecord->addCcPlayoutHistoryMetaData($meta);
  655. }
  656. }
  657. $historyRecord->save($this->con);
  658. $this->con->commit();
  659. }
  660. catch (Exception $e) {
  661. $this->con->rollback();
  662. throw $e;
  663. }
  664. }
  665. //start,end timestamp strings in local timezone.
  666. public function populateShowInstances($start, $end) {
  667. $timezoneLocal = new DateTimeZone($this->timezone);
  668. $startDT = new DateTime($start, $timezoneLocal);
  669. $endDT = new DateTime($end, $timezoneLocal);
  670. $shows = $this->getShowList($startDT, $endDT);
  671. $select = array();
  672. foreach ($shows as &$show) {
  673. $select[$show["instance_id"]] = $show["name"];
  674. }
  675. return $select;
  676. }
  677. private function validateHistoryItem($instanceId, $form) {
  678. /*
  679. $userService = new Application_Service_UserService();
  680. $currentUser = $userService->getCurrentUser();
  681. if (!$currentUser->isAdminOrPM()) {
  682. if (empty($instance_id) ) {
  683. }
  684. }
  685. */
  686. $valid = true;
  687. $recordStartsEl = $form->getElement("his_item_starts");
  688. $recordStarts = $recordStartsEl->getValue();
  689. $recordEndsEl = $form->getElement("his_item_starts");
  690. $recordEnds = $recordEndsEl->getValue();
  691. $timezoneLocal = new DateTimeZone($this->timezone);
  692. $startDT = new DateTime($recordStarts, $timezoneLocal);
  693. $endDT = new DateTime($recordEnds, $timezoneLocal);
  694. if ($recordStarts > $recordEnds) {
  695. $valid = false;
  696. $recordEndsEl->addErrorMessage("End time must be after start time");
  697. }
  698. if (isset($instanceId)) {
  699. $instance = CcShowInstancesQuery::create()->findPk($instanceId, $this->con);
  700. $inStartsDT = $instance->getDbStarts(null);
  701. $inEndsDT = $instance->getDbEnds(null);
  702. if ($startDT < $inStartsDT) {
  703. $valid = false;
  704. $form->addErrorMessage("History item begins before show.");
  705. }
  706. else if ($startDT > $inEndsDT) {
  707. $valid = false;
  708. $form->addErrorMessage("History item begins after show.");
  709. }
  710. }
  711. return $valid;
  712. }
  713. public function createPlayedItem($data) {
  714. try {
  715. $form = $this->makeHistoryItemForm(null);
  716. $history_id = $form->getElement("his_item_id");
  717. $instanceId = isset($data["instance_id"]) ? $data["instance_id"] : null;
  718. $json = array();
  719. if ($form->isValid($data) && $this->validateHistoryItem($instanceId, $form)) {
  720. $history_id->setIgnore(true);
  721. $values = $form->getValues();
  722. $this->populateTemplateItem($values, null, $instanceId);
  723. }
  724. else {
  725. $json["form"] = $form;
  726. }
  727. return $json;
  728. }
  729. catch (Exception $e) {
  730. throw $e;
  731. }
  732. }
  733. /* id is an id in cc_playout_history */
  734. public function editPlayedItem($data) {
  735. try {
  736. $id = $data["his_item_id"];
  737. $instanceId = isset($data["instance_id"]) ? $data["instance_id"] : null;
  738. $form = $this->makeHistoryItemForm($id);
  739. $history_id = $form->getElement("his_item_id");
  740. $history_id->setRequired(true);
  741. $json = array();
  742. if ($form->isValid($data) && $this->validateHistoryItem($instanceId, $form)) {
  743. $history_id->setIgnore(true);
  744. $values = $form->getValues();
  745. $this->populateTemplateItem($values, $id, $instanceId);
  746. }
  747. else {
  748. $json["form"] = $form;
  749. }
  750. return $json;
  751. }
  752. catch (Exception $e) {
  753. throw $e;
  754. }
  755. }
  756. /* id is an id in cc_files */
  757. public function editPlayedFile($data) {
  758. try {
  759. $id = $data["his_file_id"];
  760. $form = $form = $this->makeHistoryFileForm($id);
  761. $history_id = $form->getElement("his_file_id");
  762. $history_id->setRequired(true);
  763. $json = array();
  764. if ($form->isValid($data)) {
  765. $history_id->setIgnore(true);
  766. $values = $form->getValues();
  767. $this->populateTemplateFile($values, $id);
  768. }
  769. else {
  770. $json["error"] = $msgs;
  771. }
  772. return $json;
  773. $this->con->commit();
  774. }
  775. catch (Exception $e) {
  776. $this->con->rollback();
  777. Logging::info($e);
  778. throw $e;
  779. }
  780. return $json;
  781. }
  782. /* id is an id in cc_playout_history */
  783. public function deletePlayedItem($id) {
  784. $this->con->beginTransaction();
  785. try {
  786. $record = CcPlayoutHistoryQuery::create()->findPk($id, $this->con);
  787. $record->delete($this->con);
  788. $this->con->commit();
  789. }
  790. catch (Exception $e) {
  791. $this->con->rollback();
  792. Logging::info($e);
  793. throw $e;
  794. }
  795. }
  796. /* id is an id in cc_playout_history */
  797. public function deletePlayedItems($ids) {
  798. $this->con->beginTransaction();
  799. try {
  800. $records = CcPlayoutHistoryQuery::create()->findPks($ids, $this->con);
  801. $records->delete($this->con);
  802. $this->con->commit();
  803. }
  804. catch (Exception $e) {
  805. $this->con->rollback();
  806. Logging::info($e);
  807. throw $e;
  808. }
  809. }
  810. //---------------- Following code is for History Templates --------------------------//
  811. public function getFieldTypes() {
  812. $fields = array(
  813. //TEMPLATE_DATE,
  814. //TEMPLATE_TIME,
  815. //TEMPLATE_DATETIME,
  816. TEMPLATE_STRING,
  817. TEMPLATE_BOOLEAN,
  818. TEMPLATE_INT,
  819. TEMPLATE_FLOAT,
  820. );
  821. return $fields;
  822. }
  823. private function getPhpCasts() {
  824. $fields = array(
  825. TEMPLATE_DATE => "strval",
  826. TEMPLATE_TIME => "strval",
  827. TEMPLATE_DATETIME => "strval",
  828. TEMPLATE_STRING => "strval",
  829. TEMPLATE_BOOLEAN => "intval", //boolval only exists in php 5.5+
  830. TEMPLATE_INT => "intval",
  831. TEMPLATE_FLOAT => "floatval",
  832. );
  833. return $fields;
  834. }
  835. private function getSqlTypes() {
  836. $fields = array(
  837. TEMPLATE_DATE => "date",
  838. TEMPLATE_TIME => "time",
  839. TEMPLATE_DATETIME => "datetime",
  840. TEMPLATE_STRING => "text",
  841. TEMPLATE_BOOLEAN => "boolean",
  842. TEMPLATE_INT => "integer",
  843. TEMPLATE_FLOAT => "float",
  844. );
  845. return $fields;
  846. }
  847. public function getFileMetadataTypes() {
  848. $fileMD = array(
  849. array("name"=> MDATA_KEY_TITLE, "label"=> _("Title"), "type"=> TEMPLATE_STRING),
  850. array("name"=> MDATA_KEY_CREATOR, "label"=> _("Creator"), "type"=> TEMPLATE_STRING),
  851. array("name"=> MDATA_KEY_SOURCE, "label"=> _("Album"), "type"=> TEMPLATE_STRING),
  852. array("name"=> MDATA_KEY_DURATION, "label"=> _("Length"), "type"=> TEMPLATE_STRING),
  853. array("name"=> MDATA_KEY_GENRE, "label"=> _("Genre"), "type"=> TEMPLATE_STRING),
  854. array("name"=> MDATA_KEY_MOOD, "label"=> _("Mood"), "type"=> TEMPLATE_STRING),
  855. array("name"=> MDATA_KEY_LABEL, "label"=> _("Label"), "type"=> TEMPLATE_STRING),
  856. array("name"=> MDATA_KEY_COMPOSER, "label"=> _("Composer"), "type"=> TEMPLATE_STRING),
  857. array("name"=> MDATA_KEY_ISRC, "label"=> _("ISRC"), "type"=> TEMPLATE_STRING),
  858. array("name"=> MDATA_KEY_COPYRIGHT, "label"=> _("Copyright"), "type"=> TEMPLATE_STRING),
  859. array("name"=> MDATA_KEY_YEAR, "label"=> _("Year"), "type"=> TEMPLATE_INT),
  860. array("name"=> MDATA_KEY_TRACKNUMBER, "label"=> _("Track"), "type"=> TEMPLATE_INT),
  861. array("name"=> MDATA_KEY_CONDUCTOR, "label"=> _("Conductor"), "type"=> TEMPLATE_STRING),
  862. array("name"=> MDATA_KEY_LANGUAGE, "label"=> _("Language"), "type"=> TEMPLATE_STRING),
  863. );
  864. return $fileMD;
  865. }
  866. public function mandatoryItemFields() {
  867. $fields = array("starts", "ends");
  868. return $fields;
  869. }
  870. public function mandatoryFileFields() {
  871. $fields = array("played");
  872. return $fields;
  873. }
  874. private function defaultItemTemplate() {
  875. $template = array();
  876. $fields = array();
  877. $fields[] = array("name" => "starts", "label"=> _("Start Time"),"type" => TEMPLATE_DATETIME, "isFileMd" => false);
  878. $fields[] = array("name" => "ends", "label"=> _("End Time"), "type" => TEMPLATE_DATETIME, "isFileMd" => false);
  879. $fields[] = array("name" => MDATA_KEY_TITLE, "label"=> _("Title"), "type" => TEMPLATE_STRING, "isFileMd" => true); //these fields can be populated from an associated file.
  880. $fields[] = array("name" => MDATA_KEY_CREATOR, "label"=> _("Creator"), "type" => TEMPLATE_STRING, "isFileMd" => true);
  881. $template["name"] = "Log Sheet ".date("Y-m-d H:i:s")." Template";
  882. $template["fields"] = $fields;
  883. return $template;
  884. }
  885. /*
  886. * Default File Summary Template. Taken from The Czech radio requirements (customer requested this in the past).
  887. */
  888. private function defaultFileTemplate() {
  889. $template = array();
  890. $fields = array();
  891. $fields[] = array("name" => MDATA_KEY_TITLE, "label"=> _("Title"), "type" => TEMPLATE_STRING, "isFileMd" => true);
  892. $fields[] = array("name" => MDATA_KEY_CREATOR, "label"=> _("Creator"), "type" => TEMPLATE_STRING, "isFileMd" => true);
  893. $fields[] = array("name" => "played", "label"=> _("Played"), "type" => TEMPLATE_INT, "isFileMd" => false);
  894. $fields[] = array("name" => MDATA_KEY_DURATION, "label"=> _("Length"), "type" => TEMPLATE_STRING, "isFileMd" => true);
  895. $fields[] = array("name" => MDATA_KEY_COMPOSER, "label"=> _("Composer"), "type" => TEMPLATE_STRING, "isFileMd" => true);
  896. $fields[] = array("name" => MDATA_KEY_COPYRIGHT, "label"=> _("Copyright"), "type" => TEMPLATE_STRING, "isFileMd" => true);
  897. $template["name"] = "File Summary ".date("Y-m-d H:i:s")." Template";
  898. $template["fields"] = $fields;
  899. return $template;
  900. }
  901. public function loadTemplate($id) {
  902. try {
  903. if (!is_numeric($id)) {
  904. throw new Exception("Error: $id is not numeric.");
  905. }
  906. $template = CcPlayoutHistoryTemplateQuery::create()->findPk($id, $this->con);
  907. if (empty($template)) {
  908. throw new Exception("Error: Template $id does not exist.");
  909. }
  910. $c = new Criteria();
  911. $c->addAscendingOrderByColumn(CcPlayoutHistoryTemplateFieldPeer::POSITION);
  912. $config = $template->getCcPlayoutHistoryTemplateFields($c, $this->con);
  913. $fields = array();
  914. foreach ($config as $item) {
  915. $fields[] = array(
  916. "name" => $item->getDbName(),
  917. "label" => $item->getDbLabel(),
  918. "type" => $item->getDbType(),
  919. "isFileMd" => $item->getDbIsFileMD(),
  920. "id" => $item->getDbId()
  921. );
  922. }
  923. $data = array();
  924. $data["id"] = $template->getDbId();
  925. $data["name"] = $template->getDbName();
  926. $data["fields"] = $fields;
  927. $data["type"] = $template->getDbType();
  928. return $data;
  929. }
  930. catch (Exception $e) {
  931. throw $e;
  932. }
  933. }
  934. public function getItemTemplate($id) {
  935. if (is_numeric($id)) {
  936. Logging::info("template id is: $id");
  937. $template = $this->loadTemplate($id);
  938. }
  939. else {
  940. Logging::info("Using default template");
  941. $template = $this->defaultItemTemplate();
  942. }
  943. return $template;
  944. }
  945. public function getTemplates($type) {
  946. $list = array();
  947. try {
  948. $query = CcPlayoutHistoryTemplateQuery::create()
  949. ->setFormatter(ModelCriteria::FORMAT_ON_DEMAND);
  950. if (isset($type)) {
  951. $templates = $query->findByDbType($type);
  952. }
  953. else {
  954. $templates = $query->find();
  955. }
  956. foreach ($templates as $template) {
  957. $list[$template->getDbId()] = $template->getDbName();
  958. }
  959. return $list;
  960. }
  961. catch (Exception $e) {
  962. throw $e;
  963. }
  964. }
  965. public function getListItemTemplates() {
  966. return $this->getTemplates(self::TEMPLATE_TYPE_ITEM);
  967. }
  968. public function getFileTemplates() {
  969. return $this->getTemplates(self::TEMPLATE_TYPE_FILE);
  970. }
  971. private function datatablesColumns($fields) {
  972. $columns = array();
  973. foreach ($fields as $field) {
  974. $label = $field["label"];
  975. $key = $field["name"];
  976. $columns[] = array(
  977. "sTitle"=> $label,
  978. "mDataProp"=> $key,
  979. "sClass"=> "his_{$key}",
  980. "sDataType"=> $field["type"]
  981. );
  982. }
  983. return $columns;
  984. }
  985. public function getDatatablesLogSheetColumns() {
  986. //need to prepend a checkbox column.
  987. $checkbox = array(
  988. "sTitle"=> "",
  989. "mDataProp"=> "checkbox",
  990. "sClass"=> "his_checkbox",
  991. "bSortable"=> false
  992. );
  993. try {
  994. $template = $this->getConfiguredItemTemplate();
  995. $fields = $template["fields"];
  996. $columns = $this->datatablesColumns($fields);
  997. array_unshift($columns, $checkbox);
  998. return $columns;
  999. }
  1000. catch (Exception $e) {
  1001. throw $e;
  1002. }
  1003. }
  1004. public function getDatatablesFileSummaryColumns() {
  1005. try {
  1006. $template = $this->getConfiguredFileTemplate();
  1007. return $this->datatablesColumns($template["fields"]);
  1008. }
  1009. catch (Exception $e) {
  1010. throw $e;
  1011. }
  1012. }
  1013. public function getConfiguredItemTemplate() {
  1014. try {
  1015. $id = Application_Model_Preference::GetHistoryItemTemplate();
  1016. if (is_numeric($id)) {
  1017. $template = $this->loadTemplate($id);
  1018. }
  1019. else {
  1020. $template = $this->defaultItemTemplate();
  1021. }
  1022. return $template;
  1023. }
  1024. catch (Exception $e) {
  1025. throw $e;
  1026. }
  1027. }
  1028. public function setConfiguredItemTemplate($id) {
  1029. try {
  1030. Application_Model_Preference::SetHistoryItemTemplate($id);
  1031. }
  1032. catch (Exception $e) {
  1033. throw $e;
  1034. }
  1035. }
  1036. public function getConfiguredFileTemplate() {
  1037. try {
  1038. $id = Application_Model_Preference::GetHistoryFileTemplate();
  1039. if (is_numeric($id)) {
  1040. $template = $this->loadTemplate($id);
  1041. }
  1042. else {
  1043. $template = $this->defaultFileTemplate();
  1044. }
  1045. return $template;
  1046. }
  1047. catch (Exception $e) {
  1048. throw $e;
  1049. }
  1050. }
  1051. public function setConfiguredFileTemplate($id) {
  1052. try {
  1053. Application_Model_Preference::SetHistoryFileTemplate($id);
  1054. }
  1055. catch (Exception $e) {
  1056. throw $e;
  1057. }
  1058. }
  1059. public function setConfiguredTemplate($id) {
  1060. try {
  1061. $template = $this->loadTemplate($id);
  1062. $type = $template["type"];
  1063. $setTemplate = "setConfigured".ucfirst($type)."Template";
  1064. $this->$setTemplate($id);
  1065. }
  1066. catch (Exception $e) {
  1067. throw $e;
  1068. }
  1069. }
  1070. public function getConfiguredTemplateIds() {
  1071. try {
  1072. $id = Application_Model_Preference::GetHistoryItemTemplate();
  1073. $id2 = Application_Model_Preference::GetHistoryFileTemplate();
  1074. $configured = array();
  1075. if (is_numeric($id)) {
  1076. $configured[] = $id;
  1077. }
  1078. if (is_numeric($id2)) {
  1079. $configured[] = $id2;
  1080. }
  1081. return $configured;
  1082. }
  1083. catch (Exception $e) {
  1084. throw $e;
  1085. }
  1086. }
  1087. public function createTemplate($config) {
  1088. $this->con->beginTransaction();
  1089. try {
  1090. $type = $config["type"];
  1091. $method = "default".ucfirst($type)."Template";
  1092. $default = $this->$method();
  1093. $name = isset($config["name"]) ? $config["name"] : $default["name"];
  1094. $fields = isset($config["fields"]) ? $config["fields"] : $default["fields"];
  1095. $doSetDefault = isset($config['setDefault']) ? $config['setDefault'] : false;
  1096. $template = new CcPlayoutHistoryTemplate();
  1097. $template->setDbName($name);
  1098. $template->setDbType($type);
  1099. foreach ($fields as $index=>$field) {
  1100. $isMd = ($field["isFileMd"] == 'true') ? true : false;
  1101. $templateField = new CcPlayoutHistoryTemplateField();
  1102. $templateField->setDbName($field["name"]);
  1103. $templateField->setDbLabel($field["label"]);
  1104. $templateField->setDbType($field["type"]);
  1105. $templateField->setDbIsFileMD($isMd);
  1106. $templateField->setDbPosition($index);
  1107. $template->addCcPlayoutHistoryTemplateField($templateField);
  1108. }
  1109. $template->save($this->con);
  1110. if ($doSetDefault) {
  1111. $this->setConfiguredItemTemplate($template->getDbid());
  1112. }
  1113. $this->con->commit();
  1114. return $template->getDbid();
  1115. }
  1116. catch (Exception $e) {
  1117. $this->con->rollback();
  1118. throw $e;
  1119. }
  1120. }
  1121. public function updateItemTemplate($id, $name, $fields, $doSetDefault=false) {
  1122. $this->con->beginTransaction();
  1123. try {
  1124. $template = CcPlayoutHistoryTemplateQuery::create()->findPk($id, $this->con);
  1125. $template->setDbName($name);
  1126. if (count($fields) === 0) {
  1127. $t = $this->defaultItemTemplate();
  1128. $fields = $t["fields"];
  1129. }
  1130. $template->getCcPlayoutHistoryTemplateFields()->delete($this->con);
  1131. foreach ($fields as $index=>$field) {
  1132. $isMd = ($field["isFileMd"] == 'true') ? true : false;
  1133. $templateField = new CcPlayoutHistoryTemplateField();
  1134. $templateField->setDbName($field["name"]);
  1135. $templateField->setDbType($field["type"]);
  1136. $templateField->setDbLabel($field["label"]);
  1137. $templateField->setDbIsFileMD($isMd);
  1138. $templateField->setDbPosition($index);
  1139. $template->addCcPlayoutHistoryTemplateField($templateField);
  1140. }
  1141. $template->save($this->con);
  1142. if ($doSetDefault) {
  1143. $this->setConfiguredItemTemplate($template->getDbid());
  1144. }
  1145. $this->con->commit();
  1146. }
  1147. catch (Exception $e) {
  1148. $this->con->rollback();
  1149. throw $e;
  1150. }
  1151. }
  1152. public function deleteTemplate($id) {
  1153. $this->con->beginTransaction();
  1154. try {
  1155. $template = CcPlayoutHistoryTemplateQuery::create()->findPk($id, $this->con);
  1156. $template->delete($this->con);
  1157. $this->con->commit();
  1158. }
  1159. catch (Exception $e) {
  1160. $this->con->rollback();
  1161. throw $e;
  1162. }
  1163. }
  1164. }